This PR complains about g++ not diagnosing return from [[noreturn]]
function (which is UB) during constant evaluation.
This patch diagnoses that.
I haven't included the [[noreturn]] function name in the diagnostics
as it is printed in the context:
/home/jakub/src/gcc/gcc/testsuite/g++.dg/cpp1y/pr126354.C:18:24: in 'constexpr' expansion of 'bar()'
/home/jakub/src/gcc/gcc/testsuite/g++.dg/cpp1y/pr126354.C:15:7: in 'constexpr' expansion of 'foo(false)'
/home/jakub/src/gcc/gcc/testsuite/g++.dg/cpp1y/pr126354.C:15:7: error: '[[noreturn]]' call returns
But if you think it is better to emit
error ("%<[[noreturn]]%> %qD call returns", fun);
instead, I can certainly do that.
2026-07-23 Jakub Jelinek <jakub@redhat.com>
PR c++/126354
* constexpr.cc (cxx_eval_call_expression): Diagnose return from
[[noreturn]] function.
* g++.dg/cpp1y/pr126354.C: New test.
* g++.dg/cpp26/pr126354.C: New test.
Reviewed-by: Jason Merrill <jason@redhat.com>
cacheable = false;
*jump_target = jmp_target;
}
+ else if (!*non_constant_p && TREE_THIS_VOLATILE (fun))
+ {
+ /* Return from a [[noreturn]] function. */
+ if (!ctx->quiet)
+ error ("%<[[noreturn]]%> call returns");
+ *non_constant_p = true;
+ }
else if (DECL_CONSTRUCTOR_P (fun))
/* This can be null for a subobject constructor call, in
which case what we care about is the initialization
--- /dev/null
+// PR c++/126354
+// { dg-do compile { target c++14 } }
+
+[[noreturn]] constexpr void
+foo (bool x)
+{
+ if (x)
+ for (;;)
+ ;
+}
+
+constexpr bool
+bar ()
+{
+ foo (false); // { dg-error "'\\\[\\\[noreturn\\\]\\\]' call returns" }
+}
+
+constexpr bool a = bar ();
--- /dev/null
+// PR c++/126354
+// { dg-do compile { target c++26 } }
+
+[[noreturn]] constexpr void
+foo (bool x)
+{
+ if (x)
+ throw 42;
+}
+
+consteval {
+ try
+ {
+ foo (true);
+ throw nullptr;
+ }
+ catch (int x)
+ {
+ if (x != 42)
+ throw nullptr;
+ return;
+ }
+ throw nullptr;
+}
+
+consteval {
+ foo (false); // { dg-error "'\\\[\\\[noreturn\\\]\\\]' call returns" }
+}