re PR debug/19406 (ICE: in force_decl_die, at dwarf2out.c:12442)
authorJakub Jelinek <jakub@redhat.com>
Fri, 1 Apr 2005 07:47:27 +0000 (09:47 +0200)
committerJakub Jelinek <jakub@gcc.gnu.org>
Fri, 1 Apr 2005 07:47:27 +0000 (09:47 +0200)
PR c++/19406
* dwarf2out.c (gen_type_die_for_member): Handle FIELD_DECL.
(dwarf2out_imported_module_or_decl): Use gen_type_die_for_member
for FIELD_DECLs.

* g++.dg/debug/using1.C: New test.

From-SVN: r97373

gcc/ChangeLog
gcc/dwarf2out.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/debug/using1.C [new file with mode: 0644]

index dce673830de5cd2a0998f5fcf95582014d92fdf3..e3902558415d049edb787761426f411253a48ade 100644 (file)
@@ -1,3 +1,10 @@
+2005-04-01  Jakub Jelinek  <jakub@redhat.com>
+
+       PR c++/19406
+       * dwarf2out.c (gen_type_die_for_member): Handle FIELD_DECL.
+       (dwarf2out_imported_module_or_decl): Use gen_type_die_for_member
+       for FIELD_DECLs.
+
 2005-04-01  Kazu Hirata  <kazu@cs.umass.edu>
 
        * doc/contrib.texi, doc/invoke.texi, doc/tm.texi: Fix typos.
index 5f1d6313f4c0808578b594e985ba865645b189eb..bf761130e6a440d52bbb13d6e4606c1ca4f44420 100644 (file)
@@ -11222,13 +11222,27 @@ gen_type_die_for_member (tree type, tree member, dw_die_ref context_die)
   if (TYPE_DECL_SUPPRESS_DEBUG (TYPE_STUB_DECL (type))
       && ! lookup_decl_die (member))
     {
+      dw_die_ref type_die;
       gcc_assert (!decl_ultimate_origin (member));
 
       push_decl_scope (type);
+      type_die = lookup_type_die (type);
       if (TREE_CODE (member) == FUNCTION_DECL)
-       gen_subprogram_die (member, lookup_type_die (type));
+       gen_subprogram_die (member, type_die);
+      else if (TREE_CODE (member) == FIELD_DECL)
+       {
+         /* Ignore the nameless fields that are used to skip bits but handle
+            C++ anonymous unions and structs.  */
+         if (DECL_NAME (member) != NULL_TREE
+             || TREE_CODE (TREE_TYPE (member)) == UNION_TYPE
+             || TREE_CODE (TREE_TYPE (member)) == RECORD_TYPE)
+           {
+             gen_type_die (member_declared_type (member), type_die);
+             gen_field_die (member, type_die);
+           }
+       }
       else
-       gen_variable_die (member, lookup_type_die (type));
+       gen_variable_die (member, type_die);
 
       pop_decl_scope ();
     }
@@ -12935,7 +12949,29 @@ dwarf2out_imported_module_or_decl (tree decl, tree context)
   if (TREE_CODE (decl) == TYPE_DECL || TREE_CODE (decl) == CONST_DECL)
     at_import_die = force_type_die (TREE_TYPE (decl));
   else
-    at_import_die = force_decl_die (decl);
+    {
+      at_import_die = lookup_decl_die (decl);
+      if (!at_import_die)
+       {
+         /* If we're trying to avoid duplicate debug info, we may not have
+            emitted the member decl for this field.  Emit it now.  */
+         if (TREE_CODE (decl) == FIELD_DECL)
+           {
+             tree type = DECL_CONTEXT (decl);
+             dw_die_ref type_context_die;
+
+             if (TYPE_CONTEXT (type))
+               if (TYPE_P (TYPE_CONTEXT (type)))
+                 type_context_die = force_type_die (TYPE_CONTEXT (type));
+             else
+               type_context_die = force_decl_die (TYPE_CONTEXT (type));
+             else
+               type_context_die = comp_unit_die;
+             gen_type_die_for_member (type, decl, type_context_die);
+           }
+         at_import_die = force_decl_die (decl);
+       }
+    }
 
   /* OK, now we have DIEs for decl as well as scope. Emit imported die.  */
   if (TREE_CODE (decl) == NAMESPACE_DECL)
index 8de0c4426ae7f832b0ab3dc34daa820d863bdd23..a08f51c35db5d26b0eb120eecc7aa45a0d64373b 100644 (file)
@@ -1,3 +1,8 @@
+2005-04-01  Jakub Jelinek  <jakub@redhat.com>
+
+       PR c++/19406
+       * g++.dg/debug/using1.C: New test.
+
 2005-04-01  Hans-Peter Nilsson  <hp@axis.com>
 
        PR middle-end/20524
diff --git a/gcc/testsuite/g++.dg/debug/using1.C b/gcc/testsuite/g++.dg/debug/using1.C
new file mode 100644 (file)
index 0000000..d3168fc
--- /dev/null
@@ -0,0 +1,15 @@
+// PR c++/19406
+// { dg-do compile }
+
+struct A
+{
+  virtual int foo();
+  double d;
+};
+
+struct B : public A
+{
+  A::d;
+};
+
+B b;