This is a major change on how we represent nested name qualifications in
the AST.
* The nested name specifier itself and how it's stored is changed. The
prefixes for types are handled within the type hierarchy, which makes
canonicalization for them super cheap, no memory allocation required.
Also translating a type into nested name specifier form becomes a no-op.
An identifier is stored as a DependentNameType. The nested name
specifier gains a lightweight handle class, to be used instead of
passing around pointers, which is similar to what is implemented for
TemplateName. There is still one free bit available, and this handle can
be used within a PointerUnion and PointerIntPair, which should keep
bit-packing aficionados happy.
* The ElaboratedType node is removed, all type nodes in which it could
previously apply to can now store the elaborated keyword and name
qualifier, tail allocating when present.
* TagTypes can now point to the exact declaration found when producing
these, as opposed to the previous situation of there only existing one
TagType per entity. This increases the amount of type sugar retained,
and can have several applications, for example in tracking module
ownership, and other tools which care about source file origins, such as
IWYU. These TagTypes are lazily allocated, in order to limit the
increase in AST size.
This patch offers a great performance benefit.
It greatly improves compilation time for
[stdexec](https://github.com/NVIDIA/stdexec). For one datapoint, for
`test_on2.cpp` in that project, which is the slowest compiling test,
this patch improves `-c` compilation time by about 7.2%, with the
`-fsyntax-only` improvement being at ~12%.
This has great results on compile-time-tracker as well:

This patch also further enables other optimziations in the future, and
will reduce the performance impact of template specialization resugaring
when that lands.
It has some other miscelaneous drive-by fixes.
About the review: Yes the patch is huge, sorry about that. Part of the
reason is that I started by the nested name specifier part, before the
ElaboratedType part, but that had a huge performance downside, as
ElaboratedType is a big performance hog. I didn't have the steam to go
back and change the patch after the fact.
There is also a lot of internal API changes, and it made sense to remove
ElaboratedType in one go, versus removing it from one type at a time, as
that would present much more churn to the users. Also, the nested name
specifier having a different API avoids missing changes related to how
prefixes work now, which could make existing code compile but not work.
How to review: The important changes are all in
`clang/include/clang/AST` and `clang/lib/AST`, with also important
changes in `clang/lib/Sema/TreeTransform.h`.
The rest and bulk of the changes are mostly consequences of the changes
in API.
PS: TagType::getDecl is renamed to `getOriginalDecl` in this patch, just
for easier to rebasing. I plan to rename it back after this lands.
Fixes#136624
Fixes https://github.com/llvm/llvm-project/issues/43179
Fixes https://github.com/llvm/llvm-project/issues/68670
Fixes https://github.com/llvm/llvm-project/issues/92757
According to `[mem.poly.allocator.ctor]` the pointer contained in
`polymorphic_allocator` can never be null. The default constructor uses
`get_default_resource()`, which never returns null and the constructor
taking a pointer explicitly has a precondition that the pointer is
non-null.
This patch adds a warning and an assertion in case a user passes a null
pointer to `polymorphic_allocator` as well as marking `resource()` to
never return null.
This also fixes some tests which contained UB.
Fixes#148420
This makes it clearer what the functions actually do. As a nice
side-effect it also avoids a function call. If the C++03 header split is
successful we could drop `__get_pair` entirely.
This patch makes instantiation of `pair` in CTAD a bit lazier to avoid
instantiating invalid `pair` specialization before the decaying explicit
deduction guide works.
The existing using _ForwardLike declaration already fails with a
subsitution failure. The LWG issue was filed to clarify what should
happen for non-referencable types.
Added test to verify libc++ is already enforcing the new Mandates.
Implements:
- LWG3757 What's the effect of std::forward_like<void>(x)
Closes: #105026
The current implementation already have an __initial_descriptor which
saves the initial state. When release() is called, we will reset the
__initial_descriptor.__cur_ pointer.
This patch also updates the status of LWG3120.
Closes#104274
---------
Co-authored-by: Louis Dionne <ldionne.2@gmail.com>
* libcxx/test/support/min_allocator.h
+ Fix `tiny_size_allocator::rebind` which mistakenly said `T` instead of
`U`.
*
libcxx/test/std/algorithms/alg.modifying.operations/alg.partitions/stable_partition.pass.cpp
+ `std::stable_partition` requires bidirectional iterators.
* libcxx/test/std/containers/sequences/vector.bool/max_size.pass.cpp
+ Fix allocator type given to `std::vector<bool>`. The element types are
required to match, [N5008](https://isocpp.org/files/papers/N5008.pdf)
\[container.alloc.reqmts\]/5: "*Mandates:* `allocator_type::value_type`
is the same as `X::value_type`."
* libcxx/test/std/time/time.clock/time.clock.utc/types.compile.pass.cpp
+ Mark `is_steady` as `[[maybe_unused]]`, as it appears within
`LIBCPP_STATIC_ASSERT` only.
*
libcxx/test/std/algorithms/alg.modifying.operations/alg.rotate/rotate.pass.cpp
*
libcxx/test/std/algorithms/alg.modifying.operations/alg.swap/swap_ranges.pass.cpp
* libcxx/test/std/utilities/utility/utility.swap/swap_array.pass.cpp
+ Fix MSVC warning C4127 "conditional expression is constant".
`TEST_STD_AT_LEAST_23_OR_RUNTIME_EVALUATED` was introduced for this
purpose, so it should be used consistently.
* libcxx/test/std/numerics/numeric.ops/numeric.ops.gcd/gcd.pass.cpp
+ Fix `gcd()` precondition violation for `signed char`. This test case
was causing `-128` to be passed as a `signed char` to `gcd()`, which is
forbidden.
* libcxx/test/std/containers/sequences/array/assert.iterators.pass.cpp
*
libcxx/test/std/containers/sequences/vector/vector.modifiers/assert.push_back.invalidation.pass.cpp
*
libcxx/test/std/input.output/iostream.format/print.fun/no_file_description.pass.cpp
+ Split some REQUIRES and XFAIL lines. This is a "nice to have" for
MSVC's internal test harness, which is extremely simple and looks for
exact comment matches to skip tests. We can recognize the specific lines
"REQUIRES: has-unix-headers" and "XFAIL: msvc", but it's a headache to
maintain if they're chained with other conditions.
* libcxx/test/support/sized_allocator.h
+ Fix x86 truncation warnings. `std::allocator` takes `std::size_t`, so
we need to `static_cast`.
*
libcxx/test/std/input.output/file.streams/fstreams/ifstream.members/offset_range.pass.cpp
+ Fix x86 truncation warning. `std::min()` is returning
`std::streamoff`, which was being unnecessarily narrowed to
`std::size_t`.
*
libcxx/test/std/algorithms/alg.sorting/alg.merge/inplace_merge_comp.pass.cpp
+ Fix MSVC warning C4127 "conditional expression is constant" for an
always-true branch. This was very recently introduced by #129008 making
`N` constexpr. As it's a local constant just nine lines above, we don't
need to test whether 100 is greater than 0.
This patch adds a large number of missing includes in the libc++ headers
and the test suite. Those were found as part of the effort to move
towards a mostly monolithic top-level std module.
The polymorphic_allocator was added in C++17.
This issue was filed in 2022 so well after C++20. This issue adds an
operator==.
Starting with C++20 this adds a compiler generated operator!=. To have
the same behaviour in C++17 and C++20 (and later) a manual operator!= is
defined in C++17.
Implements
- LWG3683 operator== for polymorphic_allocator cannot deduce template
argument in common cases
These operators were deprecated in
P0768R1 Library Support for the Spaceship (Comparison) Operator
This was discovered while investigating the paper's implementation
status.
https://cplusplus.github.io/CWG/issues/2137.html
This change was previously made as part of
924701311aa79180e86ad8ce43d253f27d25ec7d (#77768) and later reverted in
6e4930c67508a90bdfd756f6e45417b5253cd741
This change is still needed because the comment is still true: A
standards-conformant compiler is currently supposed to fail this test.
This also means that any future work on CWG2137 with Clang would not
need to modify the libc++ test suite
Closes#77638, #24186
Rebased from <https://reviews.llvm.org/D156032>, see there for more
information.
Implements wording change in [CWG2137](https://wg21.link/CWG2137) in the
first commit.
This also implements an approach to [CWG2311](https://wg21.link/CWG2311)
in the second commit, because too much code that relies on `T{ T_prvalue}`
being an elision would break. Because that issue is still open and
the CWG issue doesn't provide wording to fix the issue, there may be
different behaviours on other compilers.
Also introduce `_LIBCPP_ASSERT_PEDANTIC` for assertions violating which
results in a no-op or other benign behavior, but which may nevertheless
indicate a bug in the invoking code.
I've structured this into a series of commits for even easier reviewing,
if that helps. I could easily split this up into separate PRs if
desired, but as this is low-risk with simple edits, I thought one PR
would be easiest.
* Drop unnecessary semicolons after function definitions.
* Cleanup comment typos.
* Cleanup `static_assert` typos.
* Cleanup test code typos.
+ There should be no functional changes, assuming I've changed all
occurrences.
* ~~Fix massive test code typos.~~
+ This was a real problem, but needed more surgery. I reverted those
changes here, and @philnik777 is fixing this properly with #73444.
* clang-formatting as requested by the CI.
1. Instead of using individual "boolean" macros, have an "enum" macro
`_LIBCPP_HARDENING_MODE`. This avoids issues with macros being
mutually exclusive and makes overriding the hardening mode within a TU
more straightforward.
2. Rename the safe mode to debug-lite.
This brings the code in line with the RFC:
https://discourse.llvm.org/t/rfc-hardening-in-libc/73925Fixes#65101
The helper function `__pair_like_explicit_wknd` is only SFINAE-ed with
`tuple_size<remove_cvref_t<_PairLike>>::value == 2`, but its function
body assumes `std::get` being valid.
Fixes#65620
The safe mode is in-between the hardened and the debug modes, extending
the checks contained in the hardened mode with certain checks that are
relatively cheap and prevent common sources of errors but aren't
security-critical. Thus, the safe mode trades off some performance for
a wider set of checks, but unlike the debug mode, it can still be used
in production.
Differential Revision: https://reviews.llvm.org/D158823
Make it a multichoice string to closer mirror the CMake variable. This
allows writing `UNSUPPORTED: libcpp-hardening-mode=unchecked` rather
than `UNSUPPORTED: !libcpp-has-hardened-mode && !libcpp-has-debug-mode`.
Differential Revision: https://reviews.llvm.org/D155906
The hardened mode is intended to only include security-critical,
relatively low-overhead checks that are intended to be usable in
production. By default, assertions are excluded from this mode.
Differential Revision: https://reviews.llvm.org/D155866
`_LIBCPP_ENABLE_ASSERTIONS` was used to enable the "safe" mode in
libc++. Libc++ now provides the hardened mode and the debug mode that
replace the safe mode.
For backward compatibility, enabling `_LIBCPP_ENABLE_ASSERTIONS` now
enables the hardened mode. Note that the hardened mode provides
a narrower set of checks than the previous "safe" mode (only
security-critical checks that are performant enough to be used in
production).
Differential Revision: https://reviews.llvm.org/D154997
I made sure they all had some expected-error output in them. Many of
these tests would be better implemented as a positive test using SFINAE,
but this is beyond the scope of this patch.
Differential Revision: https://reviews.llvm.org/D153980
This fixes rdar://110330781, which asked for the feature-test macro
for std::pmr to take into account the deployment target. It doesn't
fix https://llvm.org/PR62212, though, because the availability markup
itself must be disabled until some Clang bugs have been fixed.
This is pretty vexing, however at least everything should work once
those Clang bugs have been fixed. In the meantime, this patch at least
adds the required markup (as disabled) and ensures that the feature-test
macro for std::pmr is aware of the deployment target requirement.
Differential Revision: https://reviews.llvm.org/D135813
A few tests were also straightforward to translate to SFINAE tests
instead, so in a few cases I did that and removed the .fail.cpp test
entirely.
Differential Revision: https://reviews.llvm.org/D153149
During the ISO C++ Committee meeting plenary session the C++23 Standard
has been voted as technical complete.
This updates the reference to c++2b to c++23 and updates the __cplusplus
macro.
Note since we use clang-tidy 16 a small work-around is needed. Clang
knows -std=c++23 but clang-tidy not so for now force the lit compiler
flag to use -std=c++2b instead of -std=c++23.
Reviewed By: #libc, philnik, jloser, ldionne
Differential Revision: https://reviews.llvm.org/D150795
This adds an extension to std::pair in C++03 mode where we provide an
assignment operator from a pair<U, V>. Previously, any code trying to
trigger such an assignment operator would have tried using the
`operator=(pair const&)` copy assignment operator, which would then
have tried creating a `pair const&` by using the unconstrained
pair<U, V> constructor.
After this patch, pair will instead go through operator= directly if
its member types are assignable. If they are not assignable, the extension
operator= is disabled with SFINAE and the pair(pair<U, V>) constructor
will be used. Since that constructor is unconstrained, that will either
work or give a hard error.
This should be pretty transparent to users, but this is technically a
behavior change in C++03. Indeed, if a type has both a valid cross-type
assignment operator *and* a valid cross-type constructor, the library
will now prefer the cross-type assignment instead of going through the
cross-type constructor and then using the copy-constructor. Since this
is the mandated behavior in C++11, however, one could argue that any user
broken by that needs to change their code.
The motivation for this change is to allow simplifying the definition
of std::map's value_type, which requires handling assignment to a pair
of references properly. This patch will allow removing complexity from
https://llvm.org/D121485 instead of adding complexity in that patch.
Differential Revision: https://reviews.llvm.org/D150119
This patch makes std::pair's constructors and assignment operators
closer to conforming in C++23. The only missing bit I am aware of
now is `reference_constructs_from_temporary_v` checks, which we
don't have the tools for yet.
This patch also refactors a long-standing non-standard extension where
we'd provide constructors for tuple-like types in all standard modes. The
criteria for being a tuple-like type are different from pair-like types
as introduced recently in the standard, leading to a lot of complexity
when trying to implement recent papers that touch the pair constructors.
After this patch, the pre-C++23 extension is provided in a self-contained
block so that we can easily deprecate and eventually remove the extension
in future releases.
Differential Revision: https://reviews.llvm.org/D143914
Instead of writing something like `XFAIL: use_system_cxx_lib && target=...`
to XFAIL back-deployment tests, introduce named Lit features like
`availability-shared_mutex-missing` to represent those. This makes the
XFAIL annotations leaner, and solves the problem of XFAIL comments
potentially getting out of sync. This would also make it easier for
another vendor to add their own annotations to the test suite by simply
changing how the feature is defined for their OS releases, instead
of having to modify hundreds of tests to add repetitive annotations.
This doesn't touch *all* annotations -- only annotations that were widely
duplicated are given named features (e.g. when filesystem or shared_mutex
were introduced). I still think it probably doesn't make sense to have a
named feature for every single fix we make to the dylib.
This is in essence a revert of 2659663, but since then the test suite
has changed significantly. Back when I did 2659663, the configuration
files we have for the test suite right now were being bootstrapped and
it wasn't clear how to provide these features for back-deployment in
that context. Since then, we have a streamlined way of defining these
features in `features.py` and that doesn't impact the ability for a
configuration file to stay minimal.
The original motivation for this change was that I am about to propose
a change that would touch essentially all XFAIL annotations for back-deployment
in the test suite, and this greatly reduces the number of lines changed
by that upcoming change, in addition to making the test suite generally
better.
Differential Revision: https://reviews.llvm.org/D146359