Re: System llvm18 libc++: what will the FreeBSD LIBCXX_HARDENING_MODE be set to (one of: none, fast, extensive, debug)?

From: Dimitry Andric <dim_at_FreeBSD.org>
Date: Thu, 07 Mar 2024 18:18:24 UTC
On 7 Mar 2024, at 05:32, Mark Millard <marklmi@yahoo.com> wrote:
> 
> 2 of the notes for libc++ 18 for the harding mode are:
> 
> QUOTE
> Enabling hardening has no impact on the ABI.
> . .
> Since the static and shared library components of libc++ are built by the vendor, setting this macro will have no impact on the hardening mode for the pre-built components. Most libc++ code is header-based, so a user-provided value for _LIBCPP_HARDENING_MODE will be mostly respected.
> END QUOTE
> 
> The modes are described by:
> 
> QUOTE
>    • Unchecked mode/none, which disables all hardening checks.
>    • Fast mode, which contains a set of security-critical checks that can be done with relatively little overhead in constant time and are intended to be used in production. We recommend most projects adopt this.
>    • Extensive mode, which contains all the checks from fast mode and some additional checks for undefined behavior that incur relatively little overhead but aren’t security-critical. Production builds requiring a broader set of checks than fast mode should consider enabling extensive mode. The additional rigour impacts performance more than fast mode: we recommend benchmarking to determine if that is acceptable for your program.
>    • Debug mode, which enables all the available checks in the library, including internal assertions, some of which might be very expensive. This mode is intended to be used for testing, not in production.
> END QUOTE
> 
> Technically, DEBUG builds and non-DEBUG world builds could have different FreeBSD settings for LIBCXX_HARDENING_MODE I suppose.
> 
> QUOTE (relative to non-prebuilt components)
> Users wishing for a different hardening level to their vendor default are able to control the level by passing one of the following options to the compiler:
> 
> -D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_NONE
> -D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_FAST
> -D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_EXTENSIVE
> -D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_DEBUG
> END QUOTE

In the llvm-18-update branch, I have updated the libc++ __config_site file to use the upstream defaults for when assertions are enabled:

https://github.com/DimitryAndric/freebsd-src/blob/llvm-18-update/lib/libc%2B%2B/__config_site#L39

This is emitted by upstream's CMakeLists.txt for libcxx:

https://github.com/llvm/llvm-project/blob/release/18.x/libcxx/CMakeLists.txt#L784

The comment there says LIBCXX_ENABLE_ASSERTIONS will be deprecated, but I think having the extensive option on by default is fine, certainly for -CURRENT.

Note, I have no particular objection if we would "crank down" the level to "fast" for -STABLE or -RELEASE branches. But I don't know any specific performance difference statistics for these various levels.

Note also that our earlier libc++ builds did not have assertions enabled, so it may be worth some discussion whether it is desirable at all.

-Dimitry