Hi!

{,u8}display_string_of was printing any unnamed FIELD_DECL as
%T::<unnamed bit-field>, but anon union member is also unnamed and
is not a bit-field.

Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for
trunk?

2026-03-07  Jakub Jelinek  <[email protected]>

        PR c++/124388
        * reflect.cc (eval_display_string_of): Only print <unnmamed bit-field>
        for DECL_UNNAMED_BIT_FIELD, otherwise print <unnamed member>.

        * g++.dg/reflect/display_string_of1.C (S, NS5::S): Add
        union { int a; }.  Add static_assertions that the unnamed non-static
        data member is printed as <unnamed member>.
        * g++.dg/reflect/u8display_string_of1.C (S, NS5::S): Add
        union { int a; }.  Add static_assertions that the unnamed non-static
        data member is printed as <unnamed member>.

--- gcc/cp/reflect.cc.jj        2026-03-05 09:19:22.173774816 +0100
+++ gcc/cp/reflect.cc   2026-03-06 11:52:58.021949635 +0100
@@ -3604,7 +3604,12 @@ eval_display_string_of (location_t loc,
   else if (DECL_P (r) && (DECL_NAME (r) || TREE_CODE (r) == NAMESPACE_DECL))
     pp_printf (&pp, "%D", r);
   else if (TREE_CODE (r) == FIELD_DECL)
-    pp_printf (&pp, "%T::<unnamed bit-field>", DECL_CONTEXT (r));
+    {
+      if (DECL_UNNAMED_BIT_FIELD (r))
+       pp_printf (&pp, "%T::<unnamed bit-field>", DECL_CONTEXT (r));
+      else
+       pp_printf (&pp, "%T::<unnamed member>", DECL_CONTEXT (r));
+    }
   else if (kind == REFLECT_BASE)
     {
       tree d = direct_base_derived (r);
--- gcc/testsuite/g++.dg/reflect/display_string_of1.C.jj        2026-01-15 
16:33:47.007097959 +0100
+++ gcc/testsuite/g++.dg/reflect/display_string_of1.C   2026-03-06 
11:51:46.572128144 +0100
@@ -17,6 +17,7 @@ struct B {};
 struct S : B {
   int mem;
   int : 0;
+  union { int a; };
 };
 struct T {
   T () {}
@@ -106,6 +107,7 @@ foo (int a, const long b, T c, int d[4],
   static_assert (display_string_of (^^S) == "S");
   static_assert (display_string_of (^^S::mem) == "S::mem");
   static_assert (display_string_of (members_of (^^S, ctx)[1]) == "S::<unnamed 
bit-field>");
+  static_assert (display_string_of (nonstatic_data_members_of (^^S, ctx)[1]) 
== "S::<unnamed member>");
   static_assert (display_string_of (^^TCls) == "template<auto <anonymous> > 
struct TCls");
   static_assert (display_string_of (^^TFn) == "template<auto <anonymous> > 
void TFn()");
   static_assert (display_string_of (^^TVar) == "template<auto <anonymous> > 
int TVar<<anonymous> >");
@@ -145,6 +147,7 @@ namespace NS5 {
   struct S : B {
     int mem;
     int : 0;
+    union { int a; };
   };
   struct T {
     T () {}
@@ -212,6 +215,7 @@ namespace NS5 {
     static_assert (display_string_of (^^S) == "NS5::S");
     static_assert (display_string_of (^^S::mem) == "NS5::S::mem");
     static_assert (display_string_of (members_of (^^S, ctx)[1]) == 
"NS5::S::<unnamed bit-field>");
+    static_assert (display_string_of (nonstatic_data_members_of (^^S, ctx)[1]) 
== "NS5::S::<unnamed member>");
     static_assert (display_string_of (^^TCls) == "template<auto <anonymous> > 
struct NS5::TCls");
     static_assert (display_string_of (^^TFn) == "template<auto <anonymous> > 
void NS5::TFn()");
     static_assert (display_string_of (^^TVar) == "template<auto <anonymous> > 
int NS5::TVar<<anonymous> >");
--- gcc/testsuite/g++.dg/reflect/u8display_string_of1.C.jj      2026-01-15 
16:33:47.017097789 +0100
+++ gcc/testsuite/g++.dg/reflect/u8display_string_of1.C 2026-03-06 
11:37:31.895312350 +0100
@@ -17,6 +17,7 @@ struct B {};
 struct S : B {
   int mem;
   int : 0;
+  union { int a; };
 };
 struct T {
   T () {}
@@ -106,6 +107,7 @@ foo (int a, const long b, T c, int d[4],
   static_assert (u8display_string_of (^^S) == u8"S");
   static_assert (u8display_string_of (^^S::mem) == u8"S::mem");
   static_assert (u8display_string_of (members_of (^^S, ctx)[1]) == 
u8"S::<unnamed bit-field>");
+  static_assert (u8display_string_of (nonstatic_data_members_of (^^S, ctx)[1]) 
== u8"S::<unnamed member>");
   static_assert (u8display_string_of (^^TCls) == u8"template<auto <anonymous> 
> struct TCls");
   static_assert (u8display_string_of (^^TFn) == u8"template<auto <anonymous> > 
void TFn()");
   static_assert (u8display_string_of (^^TVar) == u8"template<auto <anonymous> 
> int TVar<<anonymous> >");
@@ -145,6 +147,7 @@ namespace NS5 {
   struct S : B {
     int mem;
     int : 0;
+    union { int a; };
   };
   struct T {
     T () {}
@@ -212,6 +215,7 @@ namespace NS5 {
     static_assert (u8display_string_of (^^S) == u8"NS5::S");
     static_assert (u8display_string_of (^^S::mem) == u8"NS5::S::mem");
     static_assert (u8display_string_of (members_of (^^S, ctx)[1]) == 
u8"NS5::S::<unnamed bit-field>");
+    static_assert (u8display_string_of (nonstatic_data_members_of (^^S, 
ctx)[1]) == u8"NS5::S::<unnamed member>");
     static_assert (u8display_string_of (^^TCls) == u8"template<auto 
<anonymous> > struct NS5::TCls");
     static_assert (u8display_string_of (^^TFn) == u8"template<auto <anonymous> 
> void NS5::TFn()");
     static_assert (u8display_string_of (^^TVar) == u8"template<auto 
<anonymous> > int NS5::TVar<<anonymous> >");

        Jakub

Reply via email to