===========================================
Libc++ 20.0.0 (In-Progress) Release Notes
===========================================

.. contents::
   :local:
   :depth: 2

Written by the `Libc++ Team <https://libcxx.llvm.org>`_

.. warning::

   These are in-progress notes for the upcoming libc++ 20.0.0 release.
   Release notes for previous releases can be found on
   `the Download Page <https://releases.llvm.org/download.html>`_.

Introduction
============

This document contains the release notes for the libc++ C++ Standard Library,
part of the LLVM Compiler Infrastructure, release 20.0.0. Here we describe the
status of libc++ in some detail, including major improvements from the previous
release and new feature work. For the general LLVM release notes, see `the LLVM
documentation <https://llvm.org/docs/ReleaseNotes.html>`_. All LLVM releases may
be downloaded from the `LLVM releases web site <https://llvm.org/releases/>`_.

For more information about libc++, please see the `Libc++ Web Site
<https://libcxx.llvm.org>`_ or the `LLVM Web Site <https://llvm.org>`_.

Note that if you are reading this file from a Git checkout or the
main Libc++ web page, this document applies to the *next* release, not
the current one. To see the release notes for a specific release, please
see the `releases page <https://llvm.org/releases/>`_.

What's New in Libc++ 20.0.0?
==============================

Implemented Papers
------------------

- P2747R2: ``constexpr`` placement new (`Github <https://github.com/llvm/llvm-project/issues/105427>`__)
- P2609R3: Relaxing Ranges Just A Smidge (`Github <https://github.com/llvm/llvm-project/issues/105253>`__)
- P2985R0: A type trait for detecting virtual base classes (`Github <https://github.com/llvm/llvm-project/issues/105432>`__)
- ``std::jthread`` and ``<stop_token>`` are not guarded behind ``-fexperimental-library`` anymore
- P2674R1: A trait for implicit lifetime types (`Github <https://github.com/llvm/llvm-project/issues/105259>`__)

Improvements and New Features
-----------------------------

- The ``lexicographical_compare`` and ``ranges::lexicographical_compare`` algorithms have been optimized for trivially
  equality comparable types, resulting in a performance improvement of up to 40x.

- The ``_LIBCPP_ENABLE_CXX20_REMOVED_TEMPORARY_BUFFER`` macro has been added to make ``std::get_temporary_buffer`` and
  ``std::return_temporary_buffer`` available.

- The ``_LIBCPP_ENABLE_CXX20_REMOVED_UNCAUGHT_EXCEPTION`` macro has been added to make ``std::uncaught_exception``
  available in C++20 and later modes.

- The internal structure ``__compressed_pair`` has been replaced with ``[[no_unique_address]]``, resulting in reduced
  compile times and smaller debug information as well as better code generation if optimizations are disabled.
  The Chromium project measured a 5% reduction in object file and debug information size.

Deprecations and Removals
-------------------------

- TODO: The ``LIBCXX_ENABLE_ASSERTIONS`` CMake variable and the ``_LIBCPP_ENABLE_ASSERTIONS`` macro that were used to
  enable the safe mode will be removed in LLVM 20.

- Support for the C++20 synchronization library (``<barrier>``, ``<latch>``, ``atomic::wait``, etc.) has been
  removed in language modes prior to C++20. If you are using these features prior to C++20, you will need to
  update to ``-std=c++20``.

- TODO: The relational operators for ``std::chrono::weekday`` will be removed entirely, and the
  ``_LIBCPP_ENABLE_REMOVED_WEEKDAY_RELATIONAL_OPERATORS`` macro that was used to re-enable this extension will be
  ignored in LLVM 20.

- The ``_LIBCPP_ENABLE_REMOVED_ALLOCATOR_CONST`` macro no longer has any effect. ``std::allocator<const T>`` is not
  supported as an extension anymore, please migrate any code that uses e.g. ``std::vector<const T>`` to be
  standards conforming.

- Non-conforming member typedefs ``base``, ``iterator`` and ``const_iterator`` of ``std::bitset``, and member typedef
  ``base`` of ``std::forward_list`` and ``std::list`` are removed. Previously, they were private but could cause
  ambiguity in name lookup. Code that expects such ambiguity will possibly not compile in LLVM 20.

- The function ``__libcpp_verbose_abort()`` is now ``noexcept``, to match ``std::terminate()``. (The combination of
  ``noexcept`` and ``[[noreturn]]`` has special significance for function effects analysis.)

Upcoming Deprecations and Removals
----------------------------------

LLVM 20
~~~~~~~

- TODO


LLVM 21
~~~~~~~

- The status of the C++03 implementation will be frozen after the LLVM 21 release. This means that starting in LLVM 22,
  non-critical bug fixes may not be back-ported to C++03, including LWG issues. C++03 is a legacy platform, where most
  projects are no longer actively maintained. To reduce the amount of fixes required to keep such legacy projects
  compiling with up-to-date toolchains, libc++ will aim to freeze the status of the headers in C++03 mode to avoid
  unintended breaking changes. See https://discourse.llvm.org/t/rfc-freezing-c-03-headers-in-libc for more details.

  If you are using C++03 in your project, you should consider moving to a newer version of the Standard to get the most
  out of libc++.


ABI Affecting Changes
---------------------

- The ABI breaks for removing undefined behaviour in ``std::forward_list``, ``std::list``, ``std::map``, ``std::set``,
  ``std::multimap``, ``std::multiset``, ``std::unordered_map``, ``std::unordered_set``, ``std::unordered_multimap`` and
  ``std::unordered_multiset`` are now applied unconditionally. This only affects fancy pointers which have a different
  value representation when pointing at the base of an internal node type instead of the type itself. A size or
  alignment difference is diagnosed, but more subtle ABI breaks may result in unexpected behaviour.

- The internal structure ``__compressed_pair`` has been replaced with ``[[no_unique_address]]``. The ABI impact is:

  - When using the Itanium ABI (most non-MSVC platforms), empty types are now placed at the beginning of the enclosing
    object instead of where the beginning of the ``__compressed_pair`` subobject was. This is only observable by
    checking the address of the empty allocator, equality comparator or hasher.
  - Additionally, using an overaligned empty type as an allocator, comparator or hasher in the associative containers
    (and only those containers) may result in the container's object object size and data layout changing beyond only
    the address of the empty member.
  - When using the MSVC ABI, this change results in some classes having a completely different memory layout, so this is
    a genuine ABI break. However, the library does not currently guarantee ABI stability on MSVC platforms.

Build System Changes
--------------------

- TODO
