https://gcc.gnu.org/bugzilla/show_bug.cgi?id=127493

Jakub Jelinek <jakub at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Assignee|unassigned at gcc dot gnu.org      |jakub at gcc dot gnu.org
   Last reconfirmed|                            |2026-09-19
             Status|UNCONFIRMED                 |ASSIGNED
                 CC|                            |jakub at gcc dot gnu.org
     Ever confirmed|0                           |1

--- Comment #2 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
Untested fix:

2026-09-19  Jakub Jelinek  <[email protected]>

        PR c++/127493
        * reflect.cc (eval_source_location_of): Call maybe_get_first_fn.

        * g++.dg/reflect/source_location_of1.C (struct G, struct H): New
        types.  Add asserts for source_location_of of member function and
        member function template.
        * g++.dg/reflect/source_location_of2.C: Expect implicitEqLine rather
        than 0 for line of ^^ImplicitEq::operator==.

--- a/gcc/cp/reflect.cc 2026-09-14 10:37:36.873105036 +0200
+++ b/gcc/cp/reflect.cc 2026-09-19 14:15:16.752981782 +0200
@@ -2715,6 +2715,8 @@ eval_source_location_of (location_t loc,
        for now use location_t of the base parent (i.e. the derived
        class).  */
     r = direct_base_derived (r);
+  else
+    r = maybe_get_first_fn (r);
   if (OVERLOAD_TYPE_P (r) || (TYPE_P (r) && typedef_variant_p (r)))
     rloc = DECL_SOURCE_LOCATION (TYPE_NAME (r));
   else if (DECL_P (r) && r != global_namespace)
--- a/gcc/testsuite/g++.dg/reflect/source_location_of1.C        2026-03-27
10:17:16.141297989 +0100
+++ b/gcc/testsuite/g++.dg/reflect/source_location_of1.C        2026-09-19
14:22:09.005482072 +0200
@@ -23,6 +23,10 @@ union U {};
 static_assert (source_location_of (^^U).line () ==
std::source_location::current ().line () - 1);
 void foo (int, int) {}
 static_assert (source_location_of (^^foo).line () ==
std::source_location::current ().line () - 1);
+struct G { void foo (int, int) {} };
+static_assert (source_location_of (^^G::foo).line () ==
std::source_location::current ().line () - 1);
+struct H { template <typename T> void foo (T, T) {} };
+static_assert (source_location_of (^^H::foo).line () ==
std::source_location::current ().line () - 1);
 namespace N { namespace O {} }
 static_assert (source_location_of (^^N).line () ==
std::source_location::current ().line () - 1);
 static_assert (source_location_of (^^N::O).line () ==
std::source_location::current ().line () - 2);
--- a/gcc/testsuite/g++.dg/reflect/source_location_of2.C        2026-03-27
10:17:16.000000000 +0100
+++ b/gcc/testsuite/g++.dg/reflect/source_location_of2.C        2026-09-19
14:23:41.258270427 +0200
@@ -38,7 +38,6 @@ struct ImplicitEq
   auto operator<=> (const ImplicitEq&) const = default;
 };

-// Would expect either class head, or operator<=> line
-static_assert (source_location_of (^^ImplicitEq::operator==).line () == 0);
+static_assert (source_location_of (^^ImplicitEq::operator==).line () ==
implicitEqLine);
 static_assert (source_location_of (select_mem (^^ImplicitEq, is_operator
(op_equals_equals))).line () == implicitEqLine);
 static_assert (source_location_of (select_mem (^^ImplicitEq, is_operator
(op_spaceship))).line () == implicitEqLine);

Reply via email to