[Bug c++/125901] Lifting not-yet-instantiated std::vector template gives incorrect result for is_trivially_copyable_type
cvs-commit at gcc dot gnu.org
gcc-bugzilla@gcc.gnu.org
Wed Jul 8 14:01:31 GMT 2026
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=125901
--- Comment #4 from GCC Commits <cvs-commit at gcc dot gnu.org> ---
The releases/gcc-16 branch has been updated by Marek Polacek
<mpolacek@gcc.gnu.org>:
https://gcc.gnu.org/g:46f8550df01af14d2b60321ab11b855284310a1b
commit r16-9246-g46f8550df01af14d2b60321ab11b855284310a1b
Author: Marek Polacek <polacek@redhat.com>
Date: Fri Jun 26 11:32:47 2026 -0400
c++/reflection: check type traits preconditions [PR125901]
This PR laments that our meta::is_trivially_copyable_type gives the wrong
result when its argument is a reflection of an uninstantiated template,
because its TYPE_HAS_* flags haven't been properly set. They are set in
finish_struct_1, called while instantiating the template.
This led to a much broader problem: we're not checking Preconditions in
[meta.unary.prop] and Comments in [meta.rel]. Jason pointed out to me
that check_trait_type and its KIND parameter already does this kind of
checking; our Reflection code just wasn't using it fully. With this patch
we give an error when finish_trait_expr returns an error node.
finish_trait_expr and check_trait_type need a complain parameter. Many
metafuncions weren't using the finish_trait_expr mechanism as they
should. The rest of the patch is adding the extra arguments.
I found PR126073, XFAILd for now.
PR c++/125901
gcc/cp/ChangeLog:
* cp-tree.h (finish_trait_expr): Adjust declaration.
* reflect.cc (eval_constant_of): Adjust the call to
eval_is_array_type.
(eval_reflect_object): Adjust the call to eval_is_object_type.
(eval_type_trait): Emit a diagnostic when finish_trait_expr
returns error_mark_node and set *non_constant_p. Adjust the
call to eval_type_trait.
(eval_is_array_type): Adjust the call to eval_type_trait.
(eval_is_pointer_type): Likewise.
(eval_is_member_object_pointer_type): Likewise.
(eval_is_member_function_pointer_type): Likewise.
(eval_is_enum_type): Likewise.
(eval_is_union_type): Likewise.
(eval_is_class_type): Likewise.
(eval_is_reference_type): Likewise.
(eval_is_member_pointer_type): Likewise.
(eval_is_object_type): Likewise.
(eval_is_trivially_copyable_type): Use eval_type_trait.
(eval_is_standard_layout_type): Likewise.
(eval_is_empty_type): Adjust the call to eval_type_trait.
(eval_is_polymorphic_type): Likewise.
(eval_is_abstract_type): Use eval_type_trait.
(eval_is_final_type): Adjust the call to eval_type_trait.
(eval_is_aggregate_type): Use eval_type_trait.
(eval_is_structural_type): Adjust the call to eval_type_trait.
(eval_is_bounded_array_type): Likewise.
(eval_is_constructible_type): Use eval_type_trait.
(eval_is_default_constructible_type): Likewise.
(eval_is_copy_constructible_type): Likewise.
(eval_is_move_constructible_type): Likewise.
(eval_is_assignable_type): Adjust the call to eval_type_trait.
(eval_is_copy_assignable_type): Use eval_type_trait.
(eval_is_move_assignable_type): Use eval_type_trait.
(eval_is_destructible_type): Adjust the call to eval_type_trait.
(eval_is_trivially_constructible_type): Use eval_type_trait.
(eval_is_trivially_default_constructible_type): Likewise.
(eval_is_trivially_copy_constructible_type): Likewise.
(eval_is_trivially_move_constructible_type): Likewise.
(eval_is_trivially_assignable_type): Adjust the call to
eval_type_trait.
(eval_is_trivially_copy_assignable_type): Use eval_type_trait.
(eval_is_trivially_move_assignable_type): Likewise.
(eval_is_trivially_destructible_type): Adjust the call to
eval_type_trait.
(eval_is_nothrow_constructible_type): Use eval_type_trait.
(eval_is_nothrow_default_constructible_type): Likewise.
(eval_is_nothrow_copy_constructible_type): Likewise.
(eval_is_nothrow_move_constructible_type): Likewise.
(eval_is_nothrow_assignable_type): Adjust the call to
eval_type_trait.
(eval_is_nothrow_copy_assignable_type): Use eval_type_trait.
(eval_is_nothrow_move_assignable_type): Likewise.
(eval_is_nothrow_destructible_type): Adjust the call to
eval_type_trait.
(eval_is_implicit_lifetime_type): Use eval_type_trait.
(eval_has_virtual_destructor): Likewise.
(eval_has_unique_object_representations): Likewise.
(eval_reference_constructs_from_temporary): Adjust the call to
eval_type_trait.
(eval_reference_converts_from_temporary): Likewise.
(eval_extent): Adjust the call to eval_is_bounded_array_type.
Check != boolean_true_node rather than == boolean_false_node when
checking eval_is_bounded_array_type.
(eval_is_same_type): Adjust the call to eval_type_trait.
(eval_is_base_of_type): Likewise.
(eval_is_virtual_base_of_type): Likewise.
(eval_is_convertible_type): Likewise.
(eval_is_nothrow_convertible_type): Likewise.
(eval_is_layout_compatible_type): Likewise.
(eval_is_pointer_interconvertible_base_of_type): Likewise.
(eval_is_invocable_type): Use eval_type_trait.
(eval_is_nothrow_invocable_type): Likewise.
(eval_data_member_spec): Adjust the calls to eval_is_array_type
and eval_is_object_type. Check != boolean_true_node rather than
== boolean_false_node when checking eval_is_object_type.
(eval_extract): Adjust the call to eval_is_reference_type.
(process_metafunction): Adjust the calls to various
metafunctions.
* semantics.cc (check_trait_type): Remove a default argument.
Add a complain parameter. If not emitting error messages, always
return false for incomplete types.
(finish_trait_expr): Add a complain parameter. Use it. Call
complete_type_or_maybe_complain instead of
complete_type_or_else.
gcc/testsuite/ChangeLog:
* g++.dg/reflect/type_trait16.C: New test.
* g++.dg/reflect/type_trait17.C: New test.
* g++.dg/reflect/type_trait18.C: New test.
Reviewed-by: Jason Merrill <jason@redhat.com>
(cherry picked from commit 0114024e4f9c167083607bb23e25aefa6ee14411)
More information about the Gcc-bugs
mailing list