C++ Logo

std-proposals

Advanced search

Re: [std-proposals] The Lakos rule, undefined behaviour and noexcept

From: Jonathan Grant <jgrantonline_at_[hidden]>
Date: Sat, 26 Sep 2026 16:20:28 +0100
On 26/09/2026 07:41, Simon Schröder via Std-Proposals wrote:
>
>
>> On Sep 25, 2026, at 5:10 PM, Frederick Virchanza Gotham via Std-Proposals <std-proposals_at_[hidden]> wrote:
>>
>> Where the ISO C++ Standard says that a particular thing results
>> in undefined behaviour, is it okay for a particular compiler to say
>> that the behaviour is well-defined and that the entire program must
>> continue to function as normal?
>
> You are right that the standard does not say that. However, I believe there is no compiler out there that shows well-defined behavior. Sometimes the compiler detects UB and uses it to its “advantage”. It might depend on the optimization level. And in the next version of the compiler someone rearranges the optimization steps or new ones are added and the behavior changes once more. In order to make UB well-defined in a specific compiler (and not just one compiler version) great care would need to be taken. And once UB is well-defined programmers will start relying on it. It is not a good idea to rely on well-defined outcome of specific UB on a specific compiler.
>
> C++ is also about speed. The only way of throwing an exception on a null dereference is to check every single dereference. Branches are potentially expensive on all CPUs. Just don’t do this. A library solution is much better! Take something like gsl::not_null, for example. Write your own types that check for nullptr on every dereference and throws an exception. Use raw pointer on the hot paths. Don’t overload operator+ to avoid pointer arithmetic or also check for nullptr. Write another class for non-null parameters that checks for non-null in their constructors (and deletes its copy and move constructors!). No compiler changes necessary! And it completely avoids UB in the first place! And the programmer decides what he wants where. Maybe you could also have some coding guidelines automatically checking for this. Only disadvantage is that the std math functions don’t have these checks by default (so, write some wrappers).

That is a good point, no special compiler features are needed if the pointer is simply in a safe container. If the checks are within a library, that makes the library add checks to handle. I may be more informative to add the checks in user code where it knows more about the situation giving rise to the nullptr, as Simon says, the programmer can decide what he wants where.

I modified gsl::not_null to enforce checks at compile-time. It uses the same approach as P4021 compile_assert(), maybe you could try it out Frederick?

It has some advantages over modifying the compiler to throw (requires software changes to catch, need to identify handling of that).
For context, here is the discussion from 2023:

https://github.com/microsoft/GSL/issues/1102

https://godbolt.org/z/vbGhcn968

Re The approach used by this and compile_assert(), it relies on the compiler to verify whether unreachable or invalid code paths are triggered. A static analysis tool could achieve the same result. The latest compile_assert() on github distinguishes "fail" and "unproven"

Regards
Jonathan

Received on 2026-09-26 15:20:35