[gcc r17-2567] c++: Make contract assertions have side effects [PR125904]

Ville Voutilainen via Gcc-cvs <[email protected]>
Newsgroups gmane.comp.gcc.cvs
Message-ID <[email protected]>
https://gcc.gnu.org/g:f9d1e2285ac37051915437ba461ac4987588e7ab

commit r17-2567-gf9d1e2285ac37051915437ba461ac4987588e7ab
Author: Ville Voutilainen <[email protected]>
Date:   Sun Jul 5 18:07:07 2026 +0300

    c++: Make contract assertions have side effects [PR125904]
    
    gcc/cp/ChangeLog:
            PR c++/125904
            * contracts.cc (build_contract_check): Set TREE_SIDE_EFFECTS.
    
    gcc/testsuite/ChangeLog:
            PR c++/125904
            * g++.dg/contracts/cpp26/pr125904.C: New test.

Diff:
---
 gcc/cp/contracts.cc                             |  1 +
 gcc/testsuite/g++.dg/contracts/cpp26/pr125904.C | 55 +++++++++++++++++++++++++
 2 files changed, 56 insertions(+)

diff --git a/gcc/cp/contracts.cc b/gcc/cp/contracts.cc
index bc9f23ba4cfa..25da963d0b4e 100644
--- a/gcc/cp/contracts.cc
+++ b/gcc/cp/contracts.cc
@@ -3048,6 +3048,7 @@ build_contract_check (tree contract)
   finish_then_clause (do_check);
   finish_if_stmt (do_check);
 
+  TREE_SIDE_EFFECTS (cc_bind) = true;
   BIND_EXPR_BODY (cc_bind) = pop_stmt_list (BIND_EXPR_BODY (cc_bind));
   return cc_bind;
 }
diff --git a/gcc/testsuite/g++.dg/contracts/cpp26/pr125904.C b/gcc/testsuite/g++.dg/contracts/cpp26/pr125904.C
new file mode 100644
index 000000000000..d0aa1b478b97
--- /dev/null
+++ b/gcc/testsuite/g++.dg/contracts/cpp26/pr125904.C
@@ -0,0 +1,55 @@
+// { dg-do run { target c++26 } }
+// { dg-additional-options "-fcontracts -fcontract-evaluation-semantic=observe" }
+// { dg-skip-if "requires hosted libstdc++ for stdc++exp" { ! hostedlib } }
+
+#include <iostream>
+#include <contracts>
+
+#define VERIFY_ASSERT(statement, asserts)  \
+	{ \
+		bool violation = false;\
+		try{ \
+			statement; \
+		} catch(int &ex) { \
+			violation = true; \
+		} \
+		if ((asserts && !violation) || (!(asserts) && violation)) __builtin_abort(); \
+	} \
+
+static_assert (__cpp_contracts >= 202502L);
+
+void handle_contract_violation(const std::contracts::contract_violation &violation) {
+  std::cerr << "custom std::handle_contract_violation called:"
+    << " " << violation.location().line()
+    << " " << violation.location().file_name()
+    << std::endl;
+  throw -(int)violation.location().line();
+}
+
+void f1()
+{
+  for (int i = 0; i < 10; ++i)
+    contract_assert(false);
+}
+
+void f2()
+{
+  do {
+    contract_assert(false);
+  } while (false);
+}
+
+void f3()
+{
+  int i = 1;
+  while (i--)
+    contract_assert(false);
+}
+
+int main()
+{
+  VERIFY_ASSERT(f1(), true);
+  VERIFY_ASSERT(f2(), true);
+  VERIFY_ASSERT(f3(), true);
+  return 0;
+}
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.