dwarf2out.c (output_call_frame_info): The CIE pointer is now a 32 bit PC-relative...
authorJason Merrill <jason@yorick.cygnus.com>
Sun, 26 Oct 1997 19:54:42 +0000 (19:54 +0000)
committerJason Merrill <jason@gcc.gnu.org>
Sun, 26 Oct 1997 19:54:42 +0000 (14:54 -0500)
* dwarf2out.c (output_call_frame_info): The CIE pointer is now a 32
  bit PC-relative offset.  The exception range table pointer is now in
  the CIE.
* frame.c (dwarf_cie, dwarf_fde): Rename CIE_pointer to CIE_delta.
(count_fdes, add_fdes, get_cie): Adjust.
(cie_info, extract_cie_info, __frame_state_for): Adjust eh_ptr uses.

From H.J. Lu:
* frame.c (count_fdes, add_fdes): Skip linked once FDE entries.

From-SVN: r16192

gcc/ChangeLog
gcc/dwarf2out.c
gcc/frame.c

index 8d95d6c3ca015a81e5111d3e91e3b04c6735a637..88005429c9c3bf36504b1feba26c1d2808680ea9 100644 (file)
@@ -1,3 +1,15 @@
+Sun Oct 26 11:41:49 1997  Jason Merrill  <jason@yorick.cygnus.com>
+
+       * dwarf2out.c (output_call_frame_info): The CIE pointer is now a 32
+       bit PC-relative offset.  The exception range table pointer is now in
+       the CIE.
+       * frame.c (dwarf_cie, dwarf_fde): Rename CIE_pointer to CIE_delta.
+       (count_fdes, add_fdes, get_cie): Adjust.
+       (cie_info, extract_cie_info, __frame_state_for): Adjust eh_ptr uses.
+
+       From H.J. Lu:
+       * frame.c (count_fdes, add_fdes): Skip linked once FDE entries.
+
 Sun Oct 26 11:52:01 1997  Richard Henderson  <rth@cygnus.com>
 
        * alias.c (memrefs_conflict_p): Treat arg_pointer_rtx just
index eebac520cac490f439b8b321a93e27880b44d1cf..45b60d6e11b1c01c617ab996e5211b2499223869 100644 (file)
@@ -1532,12 +1532,18 @@ output_call_frame_info (for_eh)
   fputc ('\n', asm_out_file);
   ASM_OUTPUT_LABEL (asm_out_file, l1);
 
-  ASM_OUTPUT_DWARF_DATA4 (asm_out_file, DW_CIE_ID);
+  if (for_eh)
+    /* Now that the CIE pointer is PC-relative for EH,
+       use 0 to identify the CIE.  */
+    ASM_OUTPUT_DWARF_DATA4 (asm_out_file, 0);
+  else
+    ASM_OUTPUT_DWARF_DATA4 (asm_out_file, DW_CIE_ID);
+
   if (flag_debug_asm)
     fprintf (asm_out_file, "\t%s CIE Identifier Tag", ASM_COMMENT_START);
 
   fputc ('\n', asm_out_file);
-  if (for_eh ? PTR_SIZE == 8 : DWARF_OFFSET_SIZE == 8)
+  if (! for_eh && DWARF_OFFSET_SIZE == 8)
     {
       ASM_OUTPUT_DWARF_DATA4 (asm_out_file, DW_CIE_ID);
       fputc ('\n', asm_out_file);
@@ -1550,11 +1556,19 @@ output_call_frame_info (for_eh)
   fputc ('\n', asm_out_file);
   if (eh_ptr)
     {
-      /* The FDE contains a pointer
-        to the exception region info for the frame.  */
-      ASM_OUTPUT_DWARF_STRING (asm_out_file, "e");
+      /* The CIE contains a pointer to the exception region info for the
+         frame.  Make the augmentation string three bytes (including the
+         trailing null) so the pointer is 4-byte aligned.  The Solaris ld
+         can't handle unaligned relocs.  */
+      ASM_OUTPUT_DWARF_STRING (asm_out_file, "eh");
       if (flag_debug_asm)
        fprintf (asm_out_file, "\t%s CIE Augmentation", ASM_COMMENT_START);
+      fputc ('\n', asm_out_file);
+
+      ASM_OUTPUT_DWARF_ADDR (asm_out_file, "__EXCEPTION_TABLE__");
+      if (flag_debug_asm)
+       fprintf (asm_out_file, "\t%s pointer to exception region info",
+                ASM_COMMENT_START);
     }
   else
     {
@@ -1605,7 +1619,7 @@ output_call_frame_info (for_eh)
       ASM_OUTPUT_LABEL (asm_out_file, l1);
 
       if (for_eh)
-       ASM_OUTPUT_DWARF_ADDR (asm_out_file, "__FRAME_BEGIN__");
+       ASM_OUTPUT_DWARF_DELTA (asm_out_file, ".", "__FRAME_BEGIN__");
       else
        ASM_OUTPUT_DWARF_OFFSET (asm_out_file, stripattributes (FRAME_SECTION));
       if (flag_debug_asm)
@@ -1623,16 +1637,6 @@ output_call_frame_info (for_eh)
        fprintf (asm_out_file, "\t%s FDE address range", ASM_COMMENT_START);
 
       fputc ('\n', asm_out_file);
-      if (eh_ptr)
-       {
-         /* For now, a pointer to the translation unit's info will do.
-            ??? Eventually this should point to the function's info.  */
-         ASM_OUTPUT_DWARF_ADDR (asm_out_file, "__EXCEPTION_TABLE__");
-         if (flag_debug_asm)
-           fprintf (asm_out_file, "\t%s pointer to exception region info",
-                    ASM_COMMENT_START);
-         fputc ('\n', asm_out_file);
-       }
 
       /* Loop through the Call Frame Instructions associated with
         this FDE.  */
index b13167e62a26a06e6c283db36ada2ab9da50e458..ca0bb39de80221de1bcbd88fc74db34fa4245cf4 100644 (file)
@@ -46,9 +46,10 @@ Boston, MA 02111-1307, USA.  */
 
 /* Some types used by the DWARF 2 spec.  */
 
-typedef unsigned int uword __attribute__ ((mode (SI)));
-typedef unsigned int uaddr __attribute__ ((mode (pointer)));
-typedef int saddr __attribute__ ((mode (pointer)));
+typedef          int  sword __attribute__ ((mode (SI)));
+typedef unsigned int  uword __attribute__ ((mode (SI)));
+typedef unsigned int  uaddr __attribute__ ((mode (pointer)));
+typedef          int  saddr __attribute__ ((mode (pointer)));
 typedef unsigned char ubyte;
 
 /* The first few fields of a CIE.  The CIE_id field is 0xffffffff for a CIE,
@@ -57,7 +58,7 @@ typedef unsigned char ubyte;
 
 struct dwarf_cie {
   uword length;
-  uaddr CIE_id;
+  sword CIE_id;
   ubyte version;
   char augmentation[0];
 } __attribute__ ((packed, aligned (__alignof__ (void *))));
@@ -66,7 +67,7 @@ struct dwarf_cie {
 
 struct dwarf_fde {
   uword length;
-  struct dwarf_cie* CIE_pointer;
+  sword CIE_delta;
   void* pc_begin;
   uaddr pc_range;
 } __attribute__ ((packed, aligned (__alignof__ (void *))));
@@ -92,6 +93,7 @@ static struct object *objects;
 
 struct cie_info {
   char *augmentation;
+  void *eh_ptr;
   int code_align;
   int data_align;
   unsigned ra_regno;
@@ -217,8 +219,8 @@ count_fdes (fde *this_fde)
 
   for (count = 0; this_fde->length != 0; this_fde = next_fde (this_fde))
     {
-      /* Skip CIEs.  */
-      if ((uaddr)(this_fde->CIE_pointer) == (uaddr)-1)
+      /* Skip CIEs and linked once FDE entries.  */
+      if (this_fde->CIE_delta == 0 || this_fde->pc_range == 0)
        continue;
 
       ++count;
@@ -237,8 +239,8 @@ add_fdes (fde *this_fde, fde **array, size_t *i_ptr,
 
   for (; this_fde->length != 0; this_fde = next_fde (this_fde))
     {
-      /* Skip CIEs.  */
-      if ((uaddr)(this_fde->CIE_pointer) == (uaddr)-1)
+      /* Skip CIEs and linked once FDE entries.  */
+      if (this_fde->CIE_delta == 0 || this_fde->pc_range == 0)
        continue;
 
       fde_insert (array, i++, this_fde);
@@ -332,6 +334,12 @@ find_fde (void *pc)
   return 0;
 }
 \f
+static inline struct dwarf_cie *
+get_cie (fde *f)
+{
+  return ((void *)&f->CIE_delta) - f->CIE_delta;
+}
+
 /* Extract any interesting information from the CIE for the translation
    unit F belongs to.  */
 
@@ -341,15 +349,23 @@ extract_cie_info (fde *f, struct cie_info *c)
   void *p;
   int i;
 
-  c->augmentation = f->CIE_pointer->augmentation;
+  c->augmentation = get_cie (f)->augmentation;
 
   if (strcmp (c->augmentation, "") != 0
-      && strcmp (c->augmentation, "e") != 0
+      && strcmp (c->augmentation, "eh") != 0
       && c->augmentation[0] != 'z')
     return 0;
 
   p = c->augmentation + strlen (c->augmentation) + 1;
 
+  if (strcmp (c->augmentation, "eh") == 0)
+    {
+      c->eh_ptr = read_pointer (p);
+      p += sizeof (void *);
+    }
+  else
+    c->eh_ptr = 0;
+
   p = decode_uleb128 (p, &c->code_align);
   p = decode_sleb128 (p, &c->data_align);
   c->ra_regno = *(unsigned char *)p++;
@@ -576,9 +592,10 @@ __frame_state_for (void *pc_target, struct frame_state *state_in)
 
   memset (&state, 0, sizeof (state));
   state.s.retaddr_column = info.ra_regno;
+  state.s.eh_ptr = info.eh_ptr;
 
   /* First decode all the insns in the CIE.  */
-  end = next_fde ((fde*) f->CIE_pointer);
+  end = next_fde ((fde*) get_cie (f));
   while (insn < end)
     insn = execute_cfa_insn (insn, &state, &info, 0);
 
@@ -590,11 +607,6 @@ __frame_state_for (void *pc_target, struct frame_state *state_in)
       insn = decode_uleb128 (insn, &i);
       insn += i;
     }
-  else if (strcmp (info.augmentation, "e") == 0)
-    {
-      state.s.eh_ptr = read_pointer (insn);
-      insn += sizeof (void *);
-    }
 
   /* Then the insns in the FDE up to our target PC.  */
   end = next_fde (f);