It turns out a union without an active member does not violate C++20 core
constant expression rules and r16-8748 was really just a workaround for a
front end bug. The actual underlying problem -- that the constexpr
evaluator treated an explicitly destroyed union member as still active --
has been fixed by r16-8767 which makes this workaround unnecessary for GCC.
Rather than remove the workaround, restrict it to Clang which seems to have
a similar bug making it still needed for e.g. the r16-8748 testcase.
PR c++/124910
libstdc++-v3/ChangeLog:
* include/std/optional (_Optional_payload_base::_M_destroy):
Restrict r16-8748 workaround to Clang, and adjust comment.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
When an optional that contains a value is cleared, _M_destroy invokes the
destructor of the contained value _Storage::_M_value, leaving the union
_Storage without an active member. While this is benign at runtime, a
union suboject with no active member violates core constant expression
requirements and in turn an optional in this state can't be used as a
constant initializer, which Clang and recent GCC (since r16-3022) correctly
diagnose.
To fix this, this patch makes _M_destroy activate the dummy union member
_M_empty after destroying _M_value to ensure that the union always has
an active member throughout its lifetime. We use std::construct_at
instead of simple assignment to work around a front end bug (comment #3
in the PR). Doing so means we don't activate the member in C++17 mode,
which should be fine; I don't think it's possible to disengage an engaged
optional using only the C++17 constexpr optional operations.
PR c++/124910
libstdc++-v3/ChangeLog:
* include/std/optional (_Optional_payload_base::_M_destroy)
[__cpp_lib_optional >= 202106L]: During constant evaluation,
after invoking destructor of _M_value, use construct_at to
activate _M_empty.
* testsuite/20_util/optional/constexpr/124910.cc: New test.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
We don't want to export std::vprint_unicode etc. from libstdc++.so yet,
but we can give users the option of improving compile times by getting
the definitions of the std::print internals from libstdc++exp.a instead.
This commit adds a macro, _GLIBCXX_NO_INLINE_PRINT, which disables the
inline definitions of std::vprint_unicode etc. so that extern
definitions in libstdc++exp.a can be used instead.
With this change compiling a helloworld using std::print goes from 8s to
under 2s with trunk. For release branches with --enable-checking=release
we should see even faster times. The object file size is also
dramatically smaller, because there's just a single call to an extern
function instead of instantiating the entire std::print and std::format
implementation inline.
libstdc++-v3/ChangeLog:
PR libstdc++/124410
* doc/html/*: Regenerate.
* doc/xml/manual/using.xml (_GLIBCXX_NO_INLINE_PRINT): Document
macro.
* include/Makefile.am: Add bits/print.h and bits/ostream_print.h
headers.
* include/Makefile.in: Regenerate.
* include/std/ostream (vprint_nonunicode, vprint_unicode): Move
definitions to new bits/ostream_print.h header.
* include/std/print (__format::_File_sink, vprint_nonunicode)
(vprint_nonunicode_buffered, vprint_unicode)
(vprint_unicode_buffered): Move definitions to new bits/print.h
header.
* src/c++23/print.cc: Include new headers to define symbols for
inline print functions.
* include/bits/ostream_print.h: New file.
* include/bits/print.h: New file.
This patch extracts a __format::__do_vformat_to for the _Sink_iter
(and matching format context) and exports explicit instantiations
of it for char and wchar_t. As every format function is implementing
as delegating to one of these overloads, this significantly reduces
the compilation time.
Instantiating __format::__do_vformat_to triggers specializations of
formatters for types stored in basic_format_arg directly (arithmetic
types, strings). In case when their behavior depends on the TU specific
configuration, only one configuration can be exported from shared
lib. In case of beforementioned formatters:
* ? (debug mode) is accepted in for strings and characters
* multibyte utf-8 encoded character is accepted as fill when the
literal encoding is Unicode.
The first issue is addressed by this patch, by declaring extern
definition only for the C++20. We will need to reconsider how to
handle the specifiers when C++23 becomes stable.
The literal encoding is handled by adding a second template parameter
to __do_vformat_to overload, that is initialized with 1 if literal
encoding is Unicode (the parameter has unsigned type to allow more
information to be encoded). This allows library to export implementation
for Unicode literal encoding (format-inst.cc is compiled with appropriate
flag), by declaring extern specialization only for value 1.
libstdc++-v3/ChangeLog:
* config/abi/pre/gnu.ver (GLIBCXX_3.4): Exclude exports
of std::basic_fo* (matching basic_format_context).
(GLIBCXX_3.4.35): Export __format::__do_vformat_to
specializations for _Sink_iter and char/wchar_t.
* include/std/format: (__format::__do_vformat_to):
Extract overload accepting _Sink_iter and provide extern
explicit specialization for char/wchar_t in C++20 mode.
* src/c++20/Makefile.am: Add format-inst.cc.
* src/c++20/Makefile.in: Regenerate.
* src/c++20/format-inst.cc: New file defining explicit
instantiation.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
The following patch attempts to implement LWG4483. As written in the
approved resolution, some checks are done on strip_array_types (valuet)
rather than on valuet and one is skipped. Tomasz on IRC reasoned why
input_range should otherwise already ensure we see similar type, so just
for the possibility of fuzzed <meta> the patch adds some verification.
And as the array cases are contiguous, instead of actually recursing (for
which we'd need to have lvalue of the *it rather than prvalue) it just
walks the CONSTRUCTORs for the arrays and handles the elts in there
recursively.
The <meta> changes do exactly what the LWG4483 change says to do.
2026-04-15 Jakub Jelinek <jakub@redhat.com>
* reflect.cc (adjust_array_elt): New function.
(get_range_elts): Implement LWG4483 - Multidimensional arrays are not
supported by meta::reflect_constant_array and related functions.
Handle ARRAY_TYPE valuet. Don't unshare_expr in the class valuet case,
get_template_param_object will unshare.
* g++.dg/reflect/reflect_constant_array9.C: New test.
* g++.dg/reflect/reflect_constant_array10.C: New test.
* g++.dg/reflect/reflect_constant_array11.C: New test.
* g++.dg/reflect/define_static_array6.C: New test.
* g++.dg/reflect/define_static_object2.C: Uncomment older tests and
fix them, add tests for unions.
* include/std/meta (define_static_object): Adjust for LWG4483 changes
- handle unions and arrays differently.
Reviewed-by: Jason Merrill <jason@redhat.com>
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
This implements P3886R0: Wording for AT1-057, by defining the
__cpp_lib_replaceable_contract_violation_handler. The macro is defined
only if contracts are supported (i.e. under same conditions as
__cpp_lib_contracts).
GCC supports providing custom violation handler by providing an separate
defintion of handle_contract_violation. This is supported on the targets
that uses ELF format, so the macro is defined for with non-zero value
for them.
libstdc++-v3/ChangeLog:
* include/bits/version.def (replaceable_contract_violation_handler)
[(__cplusplus > 202302L) && (__cpp_contracts >= 202502L)]:
Define to 202603 for ELF targets, and 0 otherwise.
* include/bits/version.h: Regenerate.
* include/std/contracts: Define
__cpp_lib_replaceable_contract_violation_handler.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This patch implements P3828R1: Rename the to_input view to as_input.
The paper suggest renaming the feature test macro without changing the
value and this patch follows.
libstdc++-v3/ChangeLog:
* include/bits/version.def (ranges_to_input): Rename to...
(ranges_as_input): Rename from ranges_as_input.
* include/bits/version.h: Regenerate.
* include/std/ranges (ranges::to_input_view, views::to_input)
(__detail::__can_to_input, views::_ToInput): Rename to...
(ranges::as_input_view, views::as_input, __detail::__can_as_input)
(views::_AsInput): Rename from above...
* src/c++23/std.cc.in: Rename views::to_input and to_input_view
export.
* testsuite/25_algorithms/contains/1.cc: Replace views::to_input
with views::as_input.
* testsuite/std/ranges/adaptors/to_input/1.cc: Move to...
* testsuite/std/ranges/adaptors/as_input/1.cc: ...here, and replace
views::to_input with views::as_input.
gcc/testsuite/ChangeLog:
* g++.dg/reflect/range_args.C: Replace views::to_input with
views::as_input.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This paper removes the try_append_range from inplace_vector and changes the
return type of try_emplace_back and try_push_back to optional<_Tp&> per:
P4022R0: Remove try_append_range from inplace_vector for now.
P3981R2: Better return types in std::inplace_vector and std::exception_ptr_cast.
The test are also expanded to cover type Y, that is convertible to optional<Y&>,
and require return type to be constructed using in_place.
libstdc++-v3/ChangeLog:
* include/bits/version.def (inplace_vector): Bump to 202603.
* include/bits/version.h: Regenerate.
* include/std/inplace_vector (inplace_vector::try_emplace_back)
(inplace_vector::try_push_back): Change return type to optional<_Tp&>
and adjust implementation accordingly.
(inplace_vector::try_append_range): Remove.
* include/debug/inplace_vector (inplace_vector::try_emplace_back)
(inplace_vector::try_push_back, inplace_vector::try_append_range):
Likewise.
* testsuite/23_containers/inplace_vector/modifiers/single_insert.cc:
Updated check for the optional<T&> return. Added test for type
convertible to optional<T&>
* testsuite/23_containers/inplace_vector/debug/invalidation/try_emplace_back.cc:
Use has_value() to check if engaged optional is returned.
* testsuite/23_containers/inplace_vector/debug/invalidation/try_push_back.cc:
Likewise.
* testsuite/23_containers/inplace_vector/modifiers/multi_insert.cc:
Remove try_append_range tests.
* testsuite/23_containers/inplace_vector/debug/invalidation/try_append_range.cc:
Removed.
* testsuite/23_containers/inplace_vector/version.cc: Updated expected
feature test macro value.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This is last change proposed in P3982R2, so we bump submdspan
value.
libstdc++-v3/ChangeLog:
* include/bits/version.def (submdspan): Update to 202603,
and list all papers in comment.
* include/bits/version.h: Regenerate.
* include/std/mdspan: Replaced std::strided_stride to
std::extent_slice, __is_strided_slice to __is_extent_slice,
_SliceKind::__unit_strided_slice to __unit_stride_slice.
* src/c++23/std.cc.in (std::extent_slice): Replaced
std::strided_slice to std::extent_slice.
* testsuite/23_containers/mdspan/submdspan/canonical_slices.cc:
Replaced all occurences of strided_slice to extent_slice.
* testsuite/23_containers/mdspan/submdspan/canonical_slices_neg.cc:
Likewise.
* testsuite/23_containers/mdspan/submdspan/strided_slice.cc: Move to...
* testsuite/23_containers/mdspan/submdspan/extent_slice.cc: ...here
and handle rename.
* testsuite/23_containers/mdspan/submdspan/strided_slice_neg.cc: Move to...
* testsuite/23_containers/mdspan/submdspan/extent_slice_neg.cc: ...here
and handle rename.
* testsuite/23_containers/mdspan/submdspan/selections/testcases.h:
Replaced all occurences of strided_slice to extent_slice.
* testsuite/23_containers/mdspan/submdspan/subextents.cc: Likewise.
* testsuite/23_containers/mdspan/submdspan/subextents_neg.cc:
Likewise.
* testsuite/23_containers/mdspan/submdspan/submdspan_mapping.cc:
Likewise.
* testsuite/23_containers/mdspan/submdspan/submdspan_neg.cc: Likewise.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This patch implements the changes suggested in P3982R2 (and PL007 NB comment)
for C++26, but changing the strided_slice::extent to indicate number of
elements (extent) in the produced (output) mdspan, instead of input.
libstdc++-v3/ChangeLog:
* include/std/mdspan (__mdspan::__static_slice_extent)
(__mdspan::__dynamic_slice_extent): Return unmodified extent
value for strided_slice.
(__mdspan::__substrides_generic, __mdspan::__substrides_standardized):
Multipliy stride, if more than one element is requested.
(__mdspan::__canonical_range_slice): Define.
(__mdspan::__slice_cast): Use __canonical_range_slice for range_slice
and two elements tuples.
(__mdspan::__check_inrange_index): Define.
(__mdspan::__check_valid_slice): Validate if slice.offset +
(slice.extent - 1) * slice.stride fits into extent of given
dimension. Check stride if slice.extent > 1.
* testsuite/23_containers/mdspan/submdspan/canonical_slices.cc:
Add test for range_slice.
* testsuite/23_containers/mdspan/submdspan/canonical_slices_neg.cc:
Add tests validating new conditions.
* testsuite/23_containers/mdspan/submdspan/selections/testcases.h:
Adjusted for change of meaing of strided_slice::extent.
* testsuite/23_containers/mdspan/submdspan/subextents.cc:
Adjusted for change of meaing of strided_slice::extent. And expanded
range_slice tests.
* testsuite/23_containers/mdspan/submdspan/subextents_neg.cc:
Adjusted for change of meaing of strided_slice::extent.
* testsuite/23_containers/mdspan/submdspan/submdspan_neg.cc:
Adjust test for stride value.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This patch add a range_slice a class, and maps it to strided_slice
with the original meanning. This is usefull for benchmark, as effects
of strided_slice remain stable before and after the change.
libstdc++-v3/ChangeLog:
* src/c++23/std.cc.in (range_slice): Export.
* include/std/mdspan (range_slice, __mdspan::__is_range_slice):
Define.
(__mdspan::__slice_cast): Handle strided_slice.
* testsuite/23_containers/mdspan/submdspan/subextents.cc:
Sanity tests for range_slice.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This doesn't matter in practice, but strictly speaking the right value
for defining std::dynamic_format is 202603 not 202311 (which was the
macro value for the old name, std::runtime_format).
libstdc++-v3/ChangeLog:
* include/std/format (dynamic_format): Check new value for
feature test macro.
Reviewed-by: Tomasz Kamiński <tkaminsk@redhat.com>
The following patch attempts to implement
https://cplusplus.github.io/LWG/lwg-active.html#4537
I've also added tests for the returned type.
2026-04-01 Jakub Jelinek <jakub@redhat.com>
* include/std/meta (std::meta::__detail::__statically_sized): New
concept.
(std::meta::define_static_array): Change return type to auto. If
__statically_sized<_Rg>, return span with ranges::size(__r) as
second argument.
* g++.dg/reflect/define_static_array1.C (l): Another variable
with define_static_array test from array<int, 0>.
Add static assertions for types of the define_static_array results.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
These helpers were needed to work around GCC's historically strict
interpretation of friendship for hidden friends whereby they did not
inherit the friends of the containing class. But this has been relaxed
in r13-465 which granted hidden friends the same access as any other
member declaration, and <ranges> additions since then rely on this
relaxed interpretation. (Note that Clang also has this relaxed
interpretation, but MSVC / EDG seem to have the strict interpretation.)
This patch removes these now redundant member functions and inlines
their logic directly into the respective friend operators, making
things simpler and more consistent.
libstdc++-v3/ChangeLog:
* include/std/ranges (iota_view::_Sentinel): Remove _M_equal and
_M_distance_from. Inline logic into friend operators.
(basic_istream_view::_Iterator): Remove _M_at_end. Inline logic
into operator==.
(transform_view::_Sentinel): Remove __distance_from and __equal.
Inline logic into friend operators.
(join_view::_Sentinel): Remove __equal. Inline logic into operator==.
(lazy_split_view::_OuterIter): Remove __at_end. Inline logic into
operator==.
(split_view::_Sentinel): Remove _M_equal. Inline logic into operator==.
(elements_view::_Sentinel): Remove _M_equal and _M_distance_from.
Inline logic into friend operators.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Last week in Croydon we approved P3953R3 to rename std::runtime_format
for C++26. The rationale is that with compile-time std::format, the name
std::runtime_format doesn't make sense. It's std::dynamic_format now
instead.
libstdc++-v3/ChangeLog:
* include/bits/chrono_io.h (__formatter_chrono::_S_empty_fs)
(__formatter_chrono::_M_C_y_Y, __formatter_chrono::_M_D_x)
(__formatter_chrono::_M_F, __formatter_chrono::_M_subsecs)
(__formatter_chrono_info::_M_format_to): Use
_Dynamic_format_string instead of _Runtime_format_string.
* include/bits/version.def (format): Bump value.
* include/bits/version.h: Regenerate.
* include/std/format (_Runtime_format_string): Rename to
_Dynamic_format_string.
(runtime_format): Rename to dynamic_format.
* include/std/print (println): Adjust comment to refer to
dynamic_format instead of runtime_format.
* testsuite/std/format/runtime_format.cc: Move to...
* testsuite/std/format/dynamic_format.cc: ...here.
Reviewed-by: Tomasz Kamiński <tkaminsk@redhat.com>
The following patch attempts to implement another part of P3795R2,
in particular the addition of annotations to data_member_options
and handling it in data_member_spec/define_aggregate etc.
2026-03-31 Jakub Jelinek <jakub@redhat.com>
libstdc++-v3/
* include/std/meta (std::meta::data_member_options): Add annotations
member.
gcc/cp/
* reflect.cc (get_range_elts): If N is negative, just use the tree
as object to extract range from instead of finding Nth argument
of a call.
(eval_is_bit_field, eval_type_of, eval_size_of, eval_alignment_of,
eval_bit_size_of, eval_has_identifier, eval_identifier_of): Adjust
function comments from P3795R2.
(eval_display_string_of): Handle annotations in
REFLECT_DATA_MEMBER_SPEC.
(eval_annotations_of): Adjust function comments from P3795R2.
(eval_data_member_spec): Likewise. Read and diagnose annotations.
(eval_define_aggregate): Adjust function comments from P3795R2.
Create annotations.
(compare_reflections): Compare REFLECT_DATA_MEMBER_SPEC annotations.
* mangle.cc (write_reflection): Mangle REFLECT_DATA_MEMBER_SPEC
annotations.
gcc/testsuite/
* g++.dg/reflect/data_member_spec5.C: New test.
* g++.dg/reflect/data_member_spec6.C: New test.
* g++.dg/reflect/display_string_of1.C: Expect extra ", {}" before
closing paren for empty annotations, otherwise a list of annotations.
* g++.dg/reflect/u8display_string_of1.C: Likewise.
* g++.dg/reflect/define_aggregate9.C: New test.
* g++.dg/reflect/mangle1.C: Test mangling of REFLECT_DATA_MEMBER_SPEC
annotations.
Reviewed-by: Jason Merrill <jason@redhat.com>
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
The following patch implements addition of std::meta::current_function,
std::meta::current_class, std::meta::current_namespace metafunctions
from P3795R2 - Miscellaneous Reflection Cleanup paper.
2026-03-31 Jakub Jelinek <jakub@redhat.com>
gcc/cp/
* metafns.gperf (enum metafn_code): Add METAFN_CURRENT_FUNCTION,
METAFN_CURRENT_CLASS and METAFN_CURRENT_NAMESPACE.
(enum metafn_kind): Add METAFN_KIND_INFO_VOID.
(current_function, current_class, current_namespace): New
metafunctions.
* pt.cc (value_dependent_expression_p): Make current_function(),
current_class() and current_namespace() calls dependent if they
are inside of template.
* reflect.cc (reflect_current_scope, eval_current_function,
eval_current_class, eval_current_namespace): New functions.
(eval_access_context_current): Use reflect_current_scope.
(process_metafunction): Handle METAFN_CURRENT_FUNCTION,
METAFN_CURRENT_CLASS and METAFN_CURRENT_NAMESPACE.
* metafns.h: Regenerate.
gcc/testsuite/
* g++.dg/reflect/current_function1.C: New test.
* g++.dg/reflect/current_function2.C: New test.
* g++.dg/reflect/current_class1.C: New test.
* g++.dg/reflect/current_class2.C: New test.
* g++.dg/reflect/current_namespace1.C: New test.
libstdc++-v3/
* include/std/meta (std::meta::current_function,
std::meta::current_class, std::meta::current_namespace): New
declarations.
* src/c++23/std.cc.in: Export those 3.
Reviewed-by: Jason Merrill <jason@redhat.com>
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Unhappy about the old and new names, as a function type is not a function,
but ces't la vie.
2026-03-30 Jakub Jelinek <jakub@redhat.com>
gcc/cp/
* metafns.gperf (enum metafn_code): Remove
METAFN_HAS_ELLIPSIS_PARAMETER, add METAFN_IS_VARARG_FUNCTION.
(has_ellipsis_parameter): Remove.
(is_vararg_function): Add.
* reflect.cc (eval_has_ellipsis_parameter): Rename to ...
(eval_is_vararg_function): ... this. Adjust function comment.
(process_metafunction): Handle METAFN_IS_VARARG_FUNCTION
instead of METAFN_HAS_ELLIPSIS_PARAMETER.
* metafns.h: Regenerate.
gcc/testsuite/
* g++.dg/reflect/has_ellipsis_parameter1.C: Rename to ...
* g++.dg/reflect/is_vararg_function1.C: this. New test. Rename
has_ellipsis_parameter to is_vararg_function everywhere.
libstdc++-v3/
* include/std/meta (has_ellipsis_parameter): Rename to ...
(is_vararg_function): ... this. New declaration.
* src/c++23/std.cc.in: Remove std::meta::has_ellipsis_parameter
export, add std::meta::is_vararg_function export.
This implementation differs significantly from the
std::experimental::simd implementation. One goal was a reduction in
template instantiations wrt. what std::experimental::simd did.
Design notes:
- bits/vec_ops.h contains concepts, traits, and functions for working
with GNU vector builtins that are mostly independent from std::simd.
These could move from std::simd:: to std::__vec (or similar). However,
we would then need to revisit naming. For now we kept everything in
the std::simd namespace with __vec_ prefix in the names. The __vec_*
functions can be called unqualified because they can never be called
on user-defined types (no ADL). If we ever get simd<UDT> support this
will be implemented via bit_cast to/from integral vector
builtins/intrinsics.
- bits/simd_x86.h extends vec_ops.h with calls to __builtin_ia32_* that
can only be used after uttering the right GCC target pragma.
- basic_vec and basic_mask are built on top of register-size GNU vector
builtins (for now / x86). Any larger vec/mask is a tree of power-of-2
#elements on the "first" branch. Anything non-power-of-2 that is
smaller than register size uses padding elements that participate in
element-wise operations. The library ensures that padding elements
lead to no side effects. The implementation makes no assumption on the
values of these padding elements since the user can bit_cast to
basic_vec/basic_mask.
Implementation status:
- The implementation is prepared for more than x86 but is x86-only for
now.
- Parts of [simd] *not* implemented in this patch:
- std::complex<floating-point> as vectorizable types
- [simd.permute.dynamic]
- [simd.permute.mask]
- [simd.permute.memory]
- [simd.bit]
- [simd.math]
- mixed operations with vec-mask and bit-mask types
- some conversion optimizations (open questions wrt. missed
optimizations in the compiler)
- This patch implements P3844R3 "Restore simd::vec broadcast from int",
which is not part of the C++26 WD draft yet. If the paper does not get
accepted the feature will be reverted.
- This patch implements D4042R0 "incorrect cast between simd::vec and
simd::mask via conversion to and from impl-defined vector types" (to be
published once the reported LWG issue gets a number).
- The standard feature test macro __cpp_lib_simd is not defined yet.
Tests:
- Full coverage requires testing
1. constexpr,
2. constant-propagating inputs, and
3. unknown (to the optimizer) inputs
- for all vectorizable types
* for every supported width (1–64 and higher)
+ for all possible ISA extensions (combinations)
= with different fast-math flags
... leading to a test matrix that's far out of reach for regular
testsuite builds.
- The tests in testsuite/std/simd/ try to cover all of the API. The
tests can be build in every combination listed above. Per default only
a small subset is built and tested.
- Use GCC_TEST_RUN_EXPENSIVE=something to compile the more expensive
tests (constexpr and const-prop testing) and to enable more /
different widths for the test type.
- Tests can still emit bogus -Wpsabi warnings (see PR98734) which are
filtered out via dg-prune-output.
Benchmarks:
- The current implementation has been benchmarked in some aspects on
x86_64 hardware. There is more optimization potential. However, it is
not always clear whether optimizations should be part of the library
if they can be implemented in the compiler.
- No benchmark code is included in this patch.
libstdc++-v3/ChangeLog:
* include/Makefile.am: Add simd headers.
* include/Makefile.in: Regenerate.
* include/bits/version.def (simd): New.
* include/bits/version.h: Regenerate.
* include/bits/simd_alg.h: New file.
* include/bits/simd_details.h: New file.
* include/bits/simd_flags.h: New file.
* include/bits/simd_iterator.h: New file.
* include/bits/simd_loadstore.h: New file.
* include/bits/simd_mask.h: New file.
* include/bits/simd_mask_reductions.h: New file.
* include/bits/simd_reductions.h: New file.
* include/bits/simd_vec.h: New file.
* include/bits/simd_x86.h: New file.
* include/bits/vec_ops.h: New file.
* include/std/simd: New file.
* testsuite/std/simd/arithmetic.cc: New test.
* testsuite/std/simd/arithmetic_expensive.cc: New test.
* testsuite/std/simd/create_tests.h: New file.
* testsuite/std/simd/creation.cc: New test.
* testsuite/std/simd/creation_expensive.cc: New test.
* testsuite/std/simd/loads.cc: New test.
* testsuite/std/simd/loads_expensive.cc: New test.
* testsuite/std/simd/mask2.cc: New test.
* testsuite/std/simd/mask2_expensive.cc: New test.
* testsuite/std/simd/mask.cc: New test.
* testsuite/std/simd/mask_expensive.cc: New test.
* testsuite/std/simd/reductions.cc: New test.
* testsuite/std/simd/reductions_expensive.cc: New test.
* testsuite/std/simd/shift_left.cc: New test.
* testsuite/std/simd/shift_left_expensive.cc: New test.
* testsuite/std/simd/shift_right.cc: New test.
* testsuite/std/simd/shift_right_expensive.cc: New test.
* testsuite/std/simd/simd_alg.cc: New test.
* testsuite/std/simd/simd_alg_expensive.cc: New test.
* testsuite/std/simd/sse_intrin.cc: New test.
* testsuite/std/simd/stores.cc: New test.
* testsuite/std/simd/stores_expensive.cc: New test.
* testsuite/std/simd/test_setup.h: New file.
* testsuite/std/simd/traits_common.cc: New test.
* testsuite/std/simd/traits_impl.cc: New test.
* testsuite/std/simd/traits_math.cc: New test.
Signed-off-by: Matthias Kretz <m.kretz@gsi.de>
The default_initializable concept is defined in terms of some builtins
which should be cheap to evaluate. Check that before instantiating the
allocator_traits class template.
libstdc++-v3/ChangeLog:
* include/std/generator (_Stateless_alloc): Swap order of
constraints.
Reviewed-by: Tomasz Kamiński <tkaminsk@redhat.com>
Reviewed-by: Arsen Arsenović <arsen@aarsen.me>
The _OIndexType template parameter will maybe deduced to reference, when
invoked from constructor and operator[]/at (after r16-7645-g66e60479e97640)
accepting array or span. We need to use forward for class-type and
remove_cvref_t for is_integral checks.
This resolves LWG4020: extents::index-cast weirdness.
libstdc++-v3/ChangeLog:
* include/std/mdspan (__mdspan::__index_type_cast): Handle
forwarding referene and use forward for class types.
* testsuite/23_containers/mdspan/int_like.h (ConstLValueInt)
(CustomIndexKind::ConstLValue): Define.
(CustomIndexType): Handle CustomIndexKind::ConstLValue.
* testsuite/23_containers/mdspan/at.cc: Test with ConstLValueInt.
* testsuite/23_containers/mdspan/extents/custom_integer.cc: Likewise.
* testsuite/23_containers/mdspan/mdspan.cc: Likewise.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
Jakub wrote a plugin which identified some non-reserved names being used
in our headers. The "count" one is actually a reserved name (there's
std::set::count and std::count and std::bitset::count) but we might as
well uglify it when used as a function parameter name. I think the "ext"
ones must have happened when moving function definitions from fs_path.cc
to fs_path.h and I forgot to change them.
The __cond::wait and __cond::wait_recursive member functions are using
non-reserved names, so that should be changed too, but this patch
doesn't fix that. I don't think we use the __gnu_cxx::__cond type in any
headers, so maybe that should just be moved into libsupc++/guard.cc or a
new header which is not installed and only used while building the
library.
libstdc++-v3/ChangeLog:
* include/bits/chrono_io.h (__formatter_duration::_S_subseconds):
Uglify subs variable name.
* include/bits/fs_path.h (path::stem, path::extension)
(path::has_stem, path::has_extension): Uglify ext parameter
name.
* include/ext/concurrence.h (__cond::wait, __cond::wait_recursive):
Uglify mutex parameter names.
* include/pstl/glue_algorithm_defs.h (generate_n): Uglify count
parameter name.
* include/std/ranges (zip_transform_view): Uglify Rs template
parameter name.
(__cartesian_is_sized_sentinel): Uglify FirstSent template
parameter name.
* include/tr1/riemann_zeta.tcc: Uglify max_size variable name.
The stdlib.h header on mingw defines a function-like macro called __max,
which causes an error here:
include/format:3785:55: error: macro '__max' requires 2 arguments, but only 1 given
3785 | iter_difference_t<_OutIter> __max(_M_max);
We have lots of existing variables called __max, but this is the only
case that uses direct-initialization and so interferes with the
function-like macro in stdlib.h
The fix applied here is just to rename the variable. We can't use
direct-list-initialization because the conversion from size_t to the
difference type would be narrowing. We prefer not to use
copy-initialization so that conversion to the difference type is
explicit not implicit.
libstdc++-v3/ChangeLog:
* include/std/format (__format::_Ptr_sink::_M_finish): Rename
__max variable to __m.
* testsuite/17_intro/names.cc (__max): Define function-like
macro.
Reviewed-by: Tomasz Kamiński <tkaminsk@redhat.com>
Your asm -> __asm__ patch made me think that these are perfect
candidates for __builtin_constexpr_diag, the asms were there just
to make it provably non-constant expression (guess *(char*)nullptr = 0;
would do as well). But with __builtin_constexpr_diag we can tell
the user the details.
Additionally, when testing it I've found that the
https://eel.is/c++draft/meta.reflection#access.context-13
Throws: meta::exception unless cls is either the null reflection
or a reflection of a complete class type.
part of via's description was implemented wierdly, it did throw
an exception, but not by telling user that via has been called with
something that is not a null reflection nor reflection of a complete
class type, but that is_class_type has been called on a reflection
of something other than a type.
2026-03-11 Jakub Jelinek <jakub@redhat.com>
* include/std/meta (std::meta::exception::what()): Use
__builtin_constexpr_diag instead of __asm__("") if supported.
(std::meta::access_context::via(info)): Don't call is_class_type
if __cls is not a type. Use __builtin_constexpr_diag instead of
__asm__("") if supported for -fno-exceptions.
* g++.dg/reflect/eh8.C: Expect different diagnostics.
* g++.dg/reflect/no-exceptions2.C: New test.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
LWG 4274 was approved in Kona 2025 but I implemented the resolution back
in 2023 for PR libstdc++/108265. This just adds a comment noting that we
implement the resolution.
libstdc++-v3/ChangeLog:
* include/std/chrono (hh_mm_ss): Add comment about LWG 4274.
Implement the accepted resolution of LWG 4243, approved in Kona 2025.
libstdc++-v3/ChangeLog:
* include/std/span (as_bytes, as_writable_bytes): Add
constraints to disallow volatile elements, as per LWG 4243.
* testsuite/23_containers/span/lwg4243.cc: New test.
Reviewed-by: Tomasz Kamiński <tkaminsk@redhat.com>
Implement proposals adopted for C++23:
P0401R6, "Providing size feedback in the Allocator interface"
P2652R2, "Disallow User Specialization of allocator_traits".
This is the minimal conforming implementation, i.e. without the
useful parts. Useful parts, to come in future patches, would
include giving access to any extra storage reserved, and use of
it in vector, string, and other contiguous containers.
libstdc++-v3/ChangeLog:
PR libstdc++/118030
* include/bits/alloc_traits.h (allocate_at_least (2x)): Define.
* include/bits/allocator.h (allocate_at_least): Define.
* include/std/memory (__glibcxx_want_allocate_at_least): Define.
* include/bits/memoryfwd.h (allocation_result): Define, #include
<bits/version.h> first so that will work.
* include/bits/version.def (allocate_at_least): Add.
* include/bits/version.h: Regenerate.
* testsuite/20_util/allocator/allocate_at_least.cc: New test.
* testsuite/20_util/allocator/allocate_at_least_neg.cc: New test.
This patch replaces the _Iter_sink specialization for contiguous
iterators of _CharT, with separate _Ptr_sink. This allow further
reduce the number of instantiations as single _Ptr_sink<_CharT>
specialization is used for all such iterators.
To make _Ptr_sink independent of iterator type, we no longer store
value of the iterator as _M_first member (the address pointed to is
still stored inside span). To produce the actual iterator position,
_Ptr_sink::_M_finish requires original pointer to be passed. As any
contiguous iterator is copyable, there is no issue in passing them
to both _Ptr_sink constructor and _M_finish method.
The __do_vformat_to method is reworked, to use _Ptr_sink when possible
(__contiguous_char_iterator is true). The implementation approach is
also changed to split the function into three constexpr branches:
_Sink_iter, contiguous char iterator, other iterators. The latter two
wrap iterators in _Ptr_sink and _Iter_sink respectively and forward
to _Sink_iter specialization.
To reduce the duplication, we introduce __do_format_to_n helper function,
that also handles wrapping iterator into _Ptr_sink and _Iter_sink as
appropriate.
libstdc++-v3/ChangeLog:
* include/std/format (__format::_Ptr_sink): Reworked
from _Iter_sink specialization below.
(__format::_Iter_sink<_CharT, contiguous_iterator _OutIter>):
Renamed and reworked to _Ptr_sink.
(__format::__contiguous_char_iter, __format::__do_vformat_to_n):
Define.
(__format::__do_vformat_to): Use _Ptr_sink when appropriate,
and delegate to _Sink_iter specialization.
(std::format_to_n): Delegate to __do_vformat_to_n.
(__format::_Counting_sink): Use _Ptr_sink as base class.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
This patch eliminate the use of __builtin_alloca for non-localized formatting
of integers and pointers.
For integers, the transcoding to _CharT moved from _M_format_int function
to format. This makes the maximum size (that depends on sizeof(_Int)) of the
buffer known (__buf_size) and allows use local array of _CharT (__wbuf) for
the storage. The _M_format_int is modified to accept the string of _CharT.
For pointers, r16-7844-gbfc2b87f8244a1 modified _Pres_p and _Pres_P to have
same value as _Pres_x and _Pres_X, so format specifiers are subset of one
allowed for integers. In consequence we simply delegate to format method
of __formatter_int, reducing the code duplication. The set of allowed
specifiers is still limited per C++ standard by __formatter_ptr::parse.
This patch fix issue in __formatter_ptr::parse, where for 'p' and 'P' the value
of _M_alt was negated for _M_spec (result of previous parse) instead of __spec
(result of current parse), and adjust the __formatter_ptr default constructor
to set _M_spec._M_type and _M_spec._M_alt appropriately.
libstdc++-v3/ChangeLog:
* include/std/format (__formatter_int::format): Handle transcoding
to _CharT before calling _M_format_int.
(__formatter_int::_M_format_int): Accept basic_string_view<_CharT>
and remove transcoding.
(__formatter_ptr::__formatter_ptr): Configure _M_spec member.
(__formatter_ptr::parse): Negate _M_alt for __spec and not _M_spec.
(__formatter_ptr::format): Delegate to __formatter_int.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
We currently only use 'asm' in .cc files (where we control the build
flags) and in the experimental::simd headers. We could just say that
-fno-asm is not compatible with libstdc++ and so using it is not
supported, but we can also just make this small change.
libstdc++-v3/ChangeLog:
* include/std/meta (exception::what, access_context::via): Use
__asm__ instead of asm keyword.
Reviewed-by: Jakub Jelinek <jakub@redhat.com>
C++11 forbids a compound statement, as seen in the definition
of __glibcxx_assert(), in a constexpr function. This patch
open-codes the assertion in `bitset<>::operator[] const` for
C++11 to fix a failure in `g++.old-deja/g++.martin/bitset1.C`.
Also, it adds `{ dg-do compile }` in another test to suppress
a spurious UNRESOLVED complaint.
libstdc++-v3/ChangeLog:
* include/std/bitset (operator[]() const): Customize bounds
check for C++11 case.
* testsuite/20_util/bitset/access/subscript_const_neg.cc:
Suppress UNRESOLVED complaint.
The _Arg_value::_M_set method, initialized the union member, by
assigning to reference to that member produced by _M_get(*this).
However, per language rules, such assignment has undefined behavior,
if alternative was not already active, same as for any object not
within its lifetime.
To address above, we modify _M_set to use placement new for the class
types, and invoke _S_access with two arguments for all other types.
The _S_access (rename of _S_get) is modified to assign the value of
the second parameter (if provided) to the union member. Such direct
assignments are treated specially in the language (see N5032
[class.union.general] p5), and will start lifetime of trivially default
constructible alternative.
libstdc++-v3/ChangeLog:
* include/std/format (_Arg_value::_M_get): Rename to...
(_Arg_value::_M_access): Modified to accept optional
second parameter that is assigned to value.
(_Arg_value::_M_get): Handle rename.
(_Arg_value::_M_set): Use construct_at for basic_string_view,
handle, and two-argument _S_access for other types.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
Signed-off-by: Ivan Lazaric <ivan.lazaric1@gmail.com>
Co-authored-by: Ivan Lazaric <ivan.lazaric1@gmail.com>
This patch changes the type of _M_handle member of __format::_Arg_value
from __format::_HandleBase union member to basic_format_arg<_Context>::handle.
This allows handle to be stored (using placement new) inside _Arg_value at
compile time, as type _M_handle member now matches stored object.
In addition to above, to make handle usable at compile time, we adjust
the _M_func signature to match the stored function, avoiding the need
for reinterpret cast.
To avoid a cycling dependency, where basic_format_arg<_Context> requires
instantiating _Arg_value<_Context> for its _M_val member, that in turn
requires basic_format_arg<_Context>::handle, we define handle as nested
class inside _Arg_value and change basic_format_arg<_Context>::handle
to alias for it.
Finally, the handle(_Tp&) constructor is now constrained to not accept
handle itself, as otherwise it would be used instead of copy-constructor
when constructing from handle&.
As _Arg_value is already templated on _Context, this change should not lead
to additional template instantiations.
libstdc++-v3/ChangeLog:
* include/std/format (__Arg_value::handle): Define, extracted
with modification from basic_format_arg::handle.
(_Arg_value::_Handle_base): Remove.
(_Arg_value::_M_handle): Change type to handle.
(_Arg_value::_M_get, _Arg_value::_M_set): Check for handle
type directly, and return result unmodified.
(basic_format_arg::__formattable): Remove.
(basic_format_arg::handle): Replace with alias to
_Arg_value::handle.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>
I changed the #if in r8-3123-gc6888c62577671 but didn't make the
corresponding change to the #endif.
libstdc++-v3/ChangeLog:
PR libstdc++/124363
* include/std/string_view: Adjust comment on #endif to match #if
condition.
Implements P2353R5 "Extending associative containers with the
remaining heterogeneous overloads". Adds overloads templated on
heterogeneous key types for several members of associative
containers, particularly insertions:
/-- unordered --\
set map mset mmap set map mset mmap
@ . . . @ . . . insert
. @ . . . @ . . op[], at, try_emplace,
insert_or_assign
. . . . @ @ @ @ bucket
(Nothing is added to the multiset or multimap tree containers.)
All the insert*() and try_emplace() members also get a hinted
overload. The at() members get const and non-const overloads.
The new overloads enforce concept __heterogeneous_tree_key or
__heterogeneous_hash_key, as in P2077, to enforce that the
function objects provided meet requirements, and that the key
supplied is not an iterator or the native key. Insertions
implicitly construct the required key_type object from the
argument, by move where permitted.
libstdc++-v3/ChangeLog:
PR libstdc++/117402
* include/bits/stl_map.h (operator[], at (2x), try_emplace (2x),
insert_or_assign (2x)): Add overloads.
* include/bits/unordered_map.h (operator[], at (2x),
try_emplace (2x), insert_or_assign (2x), bucket (2x)): Add overloads.
* include/bits/stl_set.h (insert (2x)): Add overloads.
* include/bits/unordered_set.h (insert (2x), bucket (2x)): Add overloads.
* include/bits/hashtable.h (_M_bucket_tr, _M_insert_tr): Define.
* include/bits/hashtable_policy.h (_M_at_tr (2x)): Define.
* include/bits/stl_tree.h (_M_emplace_here, _M_get_insert_unique_pos_tr,
_M_get_insert_hint_unique_pos_tr): Define new heterogeneous insertion
code path for set and map.
* include/bits/version.def (associative_heterogeneous_insertion):
Define.
* include/bits/version.h: Regenerate.
* include/std/map (__glibcxx_want_associative_heterogeneous_insertion):
Define macro.
* include/std/set: Same.
* include/std/unordered_map: Same.
* include/std/unordered_set: Same.
* testsuite/23_containers/map/modifiers/hetero/insert.cc: New tests.
* testsuite/23_containers/set/modifiers/hetero/insert.cc: Same.
* testsuite/23_containers/unordered_map/modifiers/hetero/insert.cc:
Same.
* testsuite/23_containers/unordered_multimap/modifiers/hetero/insert.cc:
Same.
* testsuite/23_containers/unordered_multiset/modifiers/hetero/insert.cc:
Same.
* testsuite/23_containers/unordered_set/modifiers/hetero/insert.cc:
Same.
The new test includes two lines that currently do not warn because of
GCC compiler bug PR85973; the lines that do warn are the more
important cases.
PR libstdc++/119197
libstdc++-v3/ChangeLog:
* include/std/expected (expected, expected<void, E>): Add
[[nodiscard]] to class.
* testsuite/20_util/expected/119197.cc: New test.
Signed-off-by: Arthur O'Dwyer <arthur.j.odwyer@gmail.com>
Reviewed-by: Nathan Myers <ncm@cantrip.org>