On Tue, Jul 15, 2025 at 08:30:33AM -0400, Jason Merrill wrote:
> > The diagnostic only changed for C++26, and I'm not sure why (the _S_at
> > function isn't constexpr, so why wasn't it failing there before?)
> 
> In C++23, we could see that the outermost thing in the expression is a call
> to _M_error, and it's non-constexpr, so we give up at that point and never
> look at the call to _S_at.

Yeah.  Though, even in GNU++23 we could have
  foo (({ if (x == 42) return 14; 23; }), 12);
with non-constexpr foo, so maybe we could do that regardless of the C++ level.
We've never handled that before during constant evaluation though and now
handle it at least in some (for C++26 hopefully most or all) cases, say
  ({ if (x == 42) return 14; 23 }) + x
etc.

> In C++26, evaluating the arguments to a function (including the object
> argument) might throw before we get to calling the non-constexpr function,
> so we need to evaluate them before giving up.

There can be other reasons for different diagnostics between C++23 and C++26
related to the constexpr exceptions patch, e.g.
potential_constant_expression for C++26 can let some expressions through
as potentially constant because it has to assume some call could throw,
while in C++23 and earlier that would be impossible, and so something can be
diagnosed only later for C++26.

        Jakub

Reply via email to