[gcc r16-9282] c++: Fix up __builtin_is_implicit_lifetime [PR126007]

Jakub Jelinek via Gcc-cvs <[email protected]>
Newsgroups gmane.comp.gcc.cvs
Message-ID <[email protected]>
https://gcc.gnu.org/g:1ff3918285512fb3571424c2519aff07939b8af2

commit r16-9282-g1ff3918285512fb3571424c2519aff07939b8af2
Author: Jakub Jelinek <[email protected]>
Date:   Tue Jun 30 09:26:29 2026 +0200

    c++: Fix up __builtin_is_implicit_lifetime [PR126007]
    
    https://eel.is/c++draft/class.prop#8.2 says that implicit lifetime
    class shall have at least one trivial eligible constructor.
    We currently walk all ctors and if it is default/copy/move ctor
    which is trivial and not deleted, return true, but as the following testcase
    shows, we should check also for unsatisfied constraints.
    
    2026-06-30  Jakub Jelinek  <[email protected]>
    
            PR c++/126007
            * tree.cc (eligible_special_member_function_p): New function.
            (implicit_lifetime_type_p): Use true instead of 1 in function comment.
            Add some further comments.  Use eligible_special_member_function_p
            instead of !DECL_DELETED_FN.
    
            * g++.dg/ext/is_implicit_lifetime3.C: New test.
    
    Reviewed-by: Jason Merrill <[email protected]>
    (cherry picked from commit 2be174f14c0bea9c0fe979467104d7d9027fe093)

Diff:
---
 gcc/cp/tree.cc                                   | 25 ++++++++++++++++++++++--
 gcc/testsuite/g++.dg/ext/is_implicit_lifetime3.C | 11 +++++++++++
 2 files changed, 34 insertions(+), 2 deletions(-)

diff --git a/gcc/cp/tree.cc b/gcc/cp/tree.cc
index 1da3e7d6fc2a..f2ecc2df0d77 100644
--- a/gcc/cp/tree.cc
+++ b/gcc/cp/tree.cc
@@ -4907,7 +4907,25 @@ trivial_type_p (const_tree t)
     return scalarish_type_p (t);
 }
 
-/* Returns 1 iff type T is an implicit-lifetime type, as defined in
+/* Returns true iff FN (which is a special member function) is
+   an eligible special member function, as defined in [special]/6.
+   The "no special member function of the same kind whose associated
+   constraints, if any, are satisfied is more constrained" condition
+   is not checked, this is checked during add_method instead.  */
+
+static bool
+eligible_special_member_function_p (tree fn)
+{
+  /* The function is not deleted.  */
+  if (DECL_DELETED_FN (fn))
+    return false;
+  /* The associated constraints, if any, are satisfied.  */
+  if (!constraints_satisfied_p (fn))
+    return false;
+  return true;
+}
+
+/* Returns true iff type T is an implicit-lifetime type, as defined in
    [basic.types.general] and [class.prop].  */
 
 bool
@@ -4922,6 +4940,7 @@ implicit_lifetime_type_p (tree t)
   if (!CLASS_TYPE_P (t))
     return false;
   t = TYPE_MAIN_VARIANT (t);
+  /* It is an aggregate whose destructor is not user-provided.  */
   if (CP_AGGREGATE_TYPE_P (t)
       && (!CLASSTYPE_DESTRUCTOR (t)
 	  || !user_provided_p (CLASSTYPE_DESTRUCTOR (t))))
@@ -4934,6 +4953,8 @@ implicit_lifetime_type_p (tree t)
     return false;
   if (CLASSTYPE_LAZY_DESTRUCTOR (t))
     lazily_declare_fn (sfk_destructor, t);
+  /* It has at least one trivial eligible constructor and a trivial,
+     non-deleted destructor.  */
   tree fn = CLASSTYPE_DESTRUCTOR (t);
   if (!fn || DECL_DELETED_FN (fn))
     return false;
@@ -4943,7 +4964,7 @@ implicit_lifetime_type_p (tree t)
       fn = *iter;
       if ((default_ctor_p (fn) || copy_fn_p (fn) || move_fn_p (fn))
 	  && trivial_fn_p (fn)
-	  && !DECL_DELETED_FN (fn))
+	  && eligible_special_member_function_p (fn))
 	return true;
     }
   return false;
diff --git a/gcc/testsuite/g++.dg/ext/is_implicit_lifetime3.C b/gcc/testsuite/g++.dg/ext/is_implicit_lifetime3.C
new file mode 100644
index 000000000000..c3b734e9d06e
--- /dev/null
+++ b/gcc/testsuite/g++.dg/ext/is_implicit_lifetime3.C
@@ -0,0 +1,11 @@
+// PR c++/126007
+// { dg-do compile { target c++20 } }
+
+template <bool B>
+struct S {
+  S () requires B = default;
+  S (const S &) {}
+};
+
+static_assert (!__builtin_is_implicit_lifetime (S<false>));
+static_assert (__builtin_is_implicit_lifetime (S<true>));
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.