On 3/5/26 7:03 PM, Marek Polacek wrote:
Bootstrapped/regtested on x86_64-pc-linux-gnu, ok for trunk?

-- >8 --
I noticed that we don't issue an error in the test in [dcl.attr.annotation]
for /4: "Substituting into an annotation is not in the immediate context":

   template<class T>
     [[=T::type()]] void f(T t);

   void f(int);

   void g() {
     f(0);         // OK
     f('0');       // error, substituting into the annotation results in an 
invalid expression
   }

        PR c++/124381

gcc/cp/ChangeLog:

        * pt.cc (tsubst_attribute): Always complain for annotations.

gcc/testsuite/ChangeLog:

        * g++.dg/reflect/annotations13.C: New test.
---
  gcc/cp/pt.cc                                 |  5 +++++
  gcc/testsuite/g++.dg/reflect/annotations13.C | 15 +++++++++++++++
  2 files changed, 20 insertions(+)
  create mode 100644 gcc/testsuite/g++.dg/reflect/annotations13.C

diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc
index ddf492b3435..36b9fbeb0b6 100644
--- a/gcc/cp/pt.cc
+++ b/gcc/cp/pt.cc
@@ -12347,6 +12347,11 @@ tsubst_attribute (tree t, tree *decl_p, tree args,
  {
    gcc_assert (ATTR_IS_DEPENDENT (t));
+ /* [dcl.attr.annotation]/4: Substituting into an annotation is not in
+     the immediate context.  */
+  if (annotation_p (t))
+    complain = tf_warning_or_error;
+
    tree val = TREE_VALUE (t);
    if (val == NULL_TREE)
      /* Nothing to do.  */;
diff --git a/gcc/testsuite/g++.dg/reflect/annotations13.C 
b/gcc/testsuite/g++.dg/reflect/annotations13.C
new file mode 100644
index 00000000000..19306956e78
--- /dev/null
+++ b/gcc/testsuite/g++.dg/reflect/annotations13.C
@@ -0,0 +1,15 @@
+// PR c++/124381
+// { dg-do compile { target c++26 } }
+// { dg-additional-options "-freflection" }
+// Test from [dcl.attr.annotation].
+
+template<class T>
+[[=T::type()]] void f(T t);  // { dg-error "not a member" }
+
+void f(int);
+
+void g() {
+  f(0);         // OK
+  f('0');       // error, substituting into the annotation results in an 
invalid expression

What if there's another template that's a better match? I'm concerned that this only works because f(int) is a perfect match for the first call so we never even form the candidate from the template.

We don't want this error until we've chosen the annotated template as the best candidate.

+// { dg-message "required from here" "" { target *-*-* } .-1 }
+}

base-commit: 0970bb8565616f61c6b7a7dd0edbc829b0064703

Reply via email to