aboutsummaryrefslogtreecommitdiff
path: root/gcc/config/arm/arm.h
diff options
context:
space:
mode:
Diffstat (limited to 'gcc/config/arm/arm.h')
-rw-r--r--gcc/config/arm/arm.h40
1 files changed, 39 insertions, 1 deletions
diff --git a/gcc/config/arm/arm.h b/gcc/config/arm/arm.h
index 0c6131b6d93..3c133a01b0e 100644
--- a/gcc/config/arm/arm.h
+++ b/gcc/config/arm/arm.h
@@ -480,7 +480,25 @@ extern int arm_is_6_or_7;
/* Nonzero if PIC code requires explicit qualifiers to generate
PLT and GOT relocs rather than the assembler doing so implicitly.
Subtargets can override this if required. */
+#ifndef NEED_PLT_GOT
#define NEED_PLT_GOT 0
+#endif
+
+/* Nonzero if we need to refer to the GOT with a PC-relative
+ offset. In other words, generate
+
+ .word _GLOBAL_OFFSET_TABLE_ - [. - (.Lxx + 8)]
+
+ rather than
+
+ .word _GLOBAL_OFFSET_TABLE_ - (.Lxx + 8)
+
+ The default is true, which matches NetBSD. Subtargets can
+ override this if required. */
+#ifndef GOT_PCREL
+#define GOT_PCREL 1
+#endif
+
/* Target machine storage Layout. */
@@ -708,7 +726,7 @@ extern const char * structure_size_string;
if (flag_pic) \
{ \
fixed_regs[PIC_OFFSET_TABLE_REGNUM] = 1; \
- call_used_regs[PIC_OFFSET_TABLE_REGNUM] = 0; \
+ call_used_regs[PIC_OFFSET_TABLE_REGNUM] = 1; \
} \
else if (TARGET_APCS_STACK) \
{ \
@@ -1245,6 +1263,9 @@ do { \
for (regno = 0; regno <= 10; regno++) \
if (regs_ever_live[regno] && ! call_used_regs[regno]) \
saved_hard_reg = 1, offset += 4; \
+ /* PIC register is a fixed reg, so call_used_regs set. */ \
+ if (flag_pic && regs_ever_live[PIC_OFFSET_TABLE_REGNUM]) \
+ saved_hard_reg = 1, offset += 4; \
for (regno = 16; regno <=23; regno++) \
if (regs_ever_live[regno] && ! call_used_regs[regno]) \
offset += 12; \
@@ -1799,6 +1820,10 @@ extern int arm_pic_register;
&& (! CONSTANT_POOL_ADDRESS_P (X) \
|| ! symbol_mentioned_p (get_pool_constant (X))))
+/* We need to know when we are making a constant pool; this determines
+ whether data needs to be in the GOT or can be referenced via a GOT
+ offset. */
+extern int making_const_table;
/* Condition code information. */
@@ -2031,6 +2056,19 @@ extern struct rtx_def *arm_compare_op0, *arm_compare_op1;
fputs(")", STREAM); \
} \
else output_addr_const(STREAM, X); \
+ \
+ /* Mark symbols as position independent. We only do this in the \
+ .text segment, not in the .data segment. */ \
+ if (NEED_PLT_GOT && flag_pic && making_const_table && \
+ (GET_CODE(X) == SYMBOL_REF || GET_CODE(X) == LABEL_REF)) \
+ { \
+ if (GET_CODE(X) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P(X)) \
+ fprintf(STREAM, "(GOTOFF)"); \
+ else if (GET_CODE (X) == LABEL_REF) \
+ fprintf(STREAM, "(GOTOFF)"); \
+ else \
+ fprintf(STREAM, "(GOT)"); \
+ } \
}
/* Output code to add DELTA to the first argument, and then jump to FUNCTION.