aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorRichard Henderson <rth@redhat.com>2001-05-22 09:57:40 -0700
committerRichard Henderson <rth@gcc.gnu.org>2001-05-22 09:57:40 -0700
commit1066e2b58d90fb2bde0af778dd67136b41f067fc (patch)
treef3a57d110a686d95d437a43f194144c18a10751a /gcc
parenteac8c4b0410083e16d48633b84aa1d61d44712c7 (diff)
downloadgcc-1066e2b58d90fb2bde0af778dd67136b41f067fc.zip
gcc-1066e2b58d90fb2bde0af778dd67136b41f067fc.tar.gz
gcc-1066e2b58d90fb2bde0af778dd67136b41f067fc.tar.bz2
crtstuff.c (__register_frame_info_bases): Declare.
* crtstuff.c (__register_frame_info_bases): Declare. (frame_dummy): Use it, if CRT_GET_RFIB_TEXT or CRT_GET_RFIB_DATA. (__do_global_dtors_aux, __do_global_dtors): Streamline. * config/i386/linux.h (ASM_MAYBE_OUTPUT_ENCODED_ADDR_RTX): New. (CRT_GET_RFIB_DATA): New. * config/i386/sysv4.h: Likewise. * config/i386/sco5.h: Likewise. (ASM_PREFERRED_EH_DATA_FORMAT): New. From-SVN: r42453
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog12
-rw-r--r--gcc/config/i386/linux.h33
-rw-r--r--gcc/config/i386/sco5.h41
-rw-r--r--gcc/config/i386/sysv4.h33
-rw-r--r--gcc/crtstuff.c35
5 files changed, 146 insertions, 8 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 86dedd1..148f682 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,17 @@
2001-05-22 Richard Henderson <rth@redhat.com>
+ * crtstuff.c (__register_frame_info_bases): Declare.
+ (frame_dummy): Use it, if CRT_GET_RFIB_TEXT or CRT_GET_RFIB_DATA.
+ (__do_global_dtors_aux, __do_global_dtors): Streamline.
+
+ * config/i386/linux.h (ASM_MAYBE_OUTPUT_ENCODED_ADDR_RTX): New.
+ (CRT_GET_RFIB_DATA): New.
+ * config/i386/sysv4.h: Likewise.
+ * config/i386/sco5.h: Likewise.
+ (ASM_PREFERRED_EH_DATA_FORMAT): New.
+
+2001-05-22 Richard Henderson <rth@redhat.com>
+
* rtl.c (read_string): Break out from ...
(read_rtx): ... here.
diff --git a/gcc/config/i386/linux.h b/gcc/config/i386/linux.h
index 108a6fb..c80a3fe 100644
--- a/gcc/config/i386/linux.h
+++ b/gcc/config/i386/linux.h
@@ -194,6 +194,39 @@ Boston, MA 02111-1307, USA. */
while (0)
#endif
+/* Handle special EH pointer encodings. Absolute, pc-relative, and
+ indirect are handled automatically. */
+#define ASM_MAYBE_OUTPUT_ENCODED_ADDR_RTX(FILE, ENCODING, SIZE, ADDR, DONE) \
+ do { \
+ if ((SIZE) == 4 && ((ENCODING) & 0x70) == DW_EH_PE_datarel) \
+ { \
+ fputs (UNALIGNED_INT_ASM_OP, FILE); \
+ assemble_name (FILE, XSTR (ADDR, 0)); \
+ fputs (((ENCODING) & DW_EH_PE_indirect ? "@GOT" : "@GOTOFF"), FILE); \
+ goto DONE; \
+ } \
+ } while (0)
+
+/* Used by crtstuff.c to initialize the base of data-relative relocations.
+ These are GOT relative on x86, so return the pic register. */
+#ifdef __PIC__
+#define CRT_GET_RFIB_DATA(BASE) \
+ { \
+ register void *ebx_ __asm__("ebx"); \
+ BASE = ebx_; \
+ }
+#else
+#define CRT_GET_RFIB_DATA(BASE) \
+ __asm__ ("call\t.LPR%=\n" \
+ ".LPR%=:\n\t" \
+ "popl\t%0\n\t" \
+ /* Due to a GAS bug, this cannot use EAX. That encodes \
+ smaller than the traditional EBX, which results in the \
+ offset being off by one. */ \
+ "addl\t$_GLOBAL_OFFSET_TABLE_+[.-.LPR%=],%0" \
+ : "=d"(BASE))
+#endif
+
/* Do code reading to identify a signal frame, and set the frame
state data appropriately. See unwind-dw2.c for the structs. */
diff --git a/gcc/config/i386/sco5.h b/gcc/config/i386/sco5.h
index 33a512d..19cbcf1 100644
--- a/gcc/config/i386/sco5.h
+++ b/gcc/config/i386/sco5.h
@@ -951,3 +951,44 @@ do { \
} while (0)
# endif /* ! _SCO_ELF */
#endif /* CRT_BEGIN !! CRT_END */
+
+/* Handle special EH pointer encodings. Absolute, pc-relative, and
+ indirect are handled automatically. */
+#define ASM_MAYBE_OUTPUT_ENCODED_ADDR_RTX(FILE, ENCODING, SIZE, ADDR, DONE) \
+ do { \
+ if ((SIZE) == 4 && ((ENCODING) & 0x70) == DW_EH_PE_datarel) \
+ { \
+ fputs (UNALIGNED_INT_ASM_OP, FILE); \
+ assemble_name (FILE, XSTR (ADDR, 0)); \
+ fputs (((ENCODING) & DW_EH_PE_indirect ? "@GOT" : "@GOTOFF"), FILE); \
+ goto DONE; \
+ } \
+ } while (0)
+
+/* Used by crtstuff.c to initialize the base of data-relative relocations.
+ These are GOT relative on x86, so return the pic register. */
+#ifdef __PIC__
+#define CRT_GET_RFIB_DATA(BASE) \
+ { \
+ register void *ebx_ __asm__("ebx"); \
+ BASE = ebx_; \
+ }
+#else
+#define CRT_GET_RFIB_DATA(BASE) \
+ __asm__ ("call\t.LPR%=\n" \
+ ".LPR%=:\n\t" \
+ "popl\t%0\n\t" \
+ /* Due to a GAS bug, this cannot use EAX. That encodes \
+ smaller than the traditional EBX, which results in the \
+ offset being off by one. */ \
+ "addl\t$_GLOBAL_OFFSET_TABLE_+[.-.LPR%=],%0" \
+ : "=d"(BASE))
+#endif
+
+/* Select a format to encode pointers in exception handling data. CODE
+ is 0 for data, 1 for code labels, 2 for function pointers. GLOBAL is
+ true if the symbol may be affected by dynamic relocations. */
+#undef ASM_PREFERRED_EH_DATA_FORMAT
+#define ASM_PREFERRED_EH_DATA_FORMAT(CODE,GLOBAL) \
+ (flag_pic ? (GLOBAL ? DW_EH_PE_indirect : 0) | DW_EH_PE_datarel \
+ : DW_EH_PE_absptr)
diff --git a/gcc/config/i386/sysv4.h b/gcc/config/i386/sysv4.h
index a610188..f56d583 100644
--- a/gcc/config/i386/sysv4.h
+++ b/gcc/config/i386/sysv4.h
@@ -179,3 +179,36 @@ do { long value[3]; \
#define ASM_OUTPUT_ALIGNED_BSS(FILE, DECL, NAME, SIZE, ALIGN) \
asm_output_aligned_bss (FILE, DECL, NAME, SIZE, ALIGN)
+
+/* Handle special EH pointer encodings. Absolute, pc-relative, and
+ indirect are handled automatically. */
+#define ASM_MAYBE_OUTPUT_ENCODED_ADDR_RTX(FILE, ENCODING, SIZE, ADDR, DONE) \
+ do { \
+ if ((SIZE) == 4 && ((ENCODING) & 0x70) == DW_EH_PE_datarel) \
+ { \
+ fputs (UNALIGNED_INT_ASM_OP, FILE); \
+ assemble_name (FILE, XSTR (ADDR, 0)); \
+ fputs (((ENCODING) & DW_EH_PE_indirect ? "@GOT" : "@GOTOFF"), FILE); \
+ goto DONE; \
+ } \
+ } while (0)
+
+/* Used by crtstuff.c to initialize the base of data-relative relocations.
+ These are GOT relative on x86, so return the pic register. */
+#ifdef __PIC__
+#define CRT_GET_RFIB_DATA(BASE) \
+ { \
+ register void *ebx_ __asm__("ebx"); \
+ BASE = ebx_; \
+ }
+#else
+#define CRT_GET_RFIB_DATA(BASE) \
+ __asm__ ("call\t.LPR%=\n" \
+ ".LPR%=:\n\t" \
+ "popl\t%0\n\t" \
+ /* Due to a GAS bug, this cannot use EAX. That encodes \
+ smaller than the traditional EBX, which results in the \
+ offset being off by one. */ \
+ "addl\t$_GLOBAL_OFFSET_TABLE_+[.-.LPR%=],%0" \
+ : "=d"(BASE))
+#endif
diff --git a/gcc/crtstuff.c b/gcc/crtstuff.c
index b8f6df58..1897185 100644
--- a/gcc/crtstuff.c
+++ b/gcc/crtstuff.c
@@ -90,7 +90,9 @@ Boston, MA 02111-1307, USA. */
be weak in this file if at all possible. */
extern void __register_frame_info (void *, struct object *)
TARGET_ATTRIBUTE_WEAK;
-
+extern void __register_frame_info_bases (void *, struct object *,
+ void *, void *)
+ TARGET_ATTRIBUTE_WEAK;
extern void *__deregister_frame_info (void *)
TARGET_ATTRIBUTE_WEAK;
@@ -190,9 +192,10 @@ static void
__do_global_dtors_aux (void)
{
static func_ptr *p = __DTOR_LIST__ + 1;
- static int completed = 0;
+ static int completed;
+ func_ptr f;
- if (completed)
+ if (__builtin_expect (completed, 0))
return;
#ifdef CRTSTUFFS_O
@@ -200,10 +203,10 @@ __do_global_dtors_aux (void)
__cxa_finalize (__dso_handle);
#endif
- while (*p)
+ while ((f = *p))
{
p++;
- (*(p-1)) ();
+ f ();
}
#ifdef EH_FRAME_SECTION_ASM_OP
@@ -236,8 +239,24 @@ static void
frame_dummy (void)
{
static struct object object;
+#if defined(CRT_GET_RFIB_TEXT) || defined(CRT_GET_RFIB_DATA)
+ void *tbase, *dbase;
+#ifdef CRT_GET_RFIB_TEXT
+ CRT_GET_RFIB_TEXT (tbase);
+#else
+ tbase = 0;
+#endif
+#ifdef CRT_GET_RFIB_DATA
+ CRT_GET_RFIB_DATA (dbase);
+#else
+ dbase = 0;
+#endif
+ if (__register_frame_info_bases)
+ __register_frame_info_bases (__EH_FRAME_BEGIN__, &object, tbase, dbase);
+#else
if (__register_frame_info)
__register_frame_info (__EH_FRAME_BEGIN__, &object);
+#endif
}
static void __attribute__ ((__unused__))
@@ -317,9 +336,9 @@ static func_ptr __DTOR_LIST__[];
void
__do_global_dtors (void)
{
- func_ptr *p;
- for (p = __DTOR_LIST__ + 1; *p; p++)
- (*p) ();
+ func_ptr *p, f;
+ for (p = __DTOR_LIST__ + 1; (f = *p); p++)
+ f ();
#ifdef EH_FRAME_SECTION_ASM_OP
if (__deregister_frame_info)