]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
arm.c (TARGET_ASM_TRAMPOLINE_TEMPLATE): New.
authorRichard Henderson <rth@redhat.com>
Tue, 22 Sep 2009 15:12:02 +0000 (08:12 -0700)
committerRichard Henderson <rth@gcc.gnu.org>
Tue, 22 Sep 2009 15:12:02 +0000 (08:12 -0700)
        * config/arm/arm.c (TARGET_ASM_TRAMPOLINE_TEMPLATE): New.
        (TARGET_TRAMPOLINE_INIT, TARGET_TRAMPOLINE_ADJUST_ADDRESS): New.
        (arm_asm_trampoline_template): New.
        (arm_trampoline_init, arm_trampoline_adjust_address): New.
        * config/arm/arm.h (TRAMPOLINE_TEMPLATE,
        * ARM_TRAMPOLINE_TEMPLATE,
        THUMB2_TRAMPOLINE_TEMPLATE, THUMB1_TRAMPOLINE_TEMPLATE): Move all
        code to arm_asm_trampoline_template.
        (TRAMPOLINE_ADJUST_ADDRESS): Move code to
        arm_trampoline_adjust_address.
        (INITIALIZE_TRAMPOLINE): Move code to arm_trampoline_init;
        adjust for target hook parameters.

From-SVN: r151986

gcc/ChangeLog
gcc/config/arm/arm.c
gcc/config/arm/arm.h

index a852c4ae5500dce23c3c2108f3778ef3bbce66a7..4dd20d4d4be35db6ad65bc977e6f698e52804cc3 100644 (file)
        * config/arc/arc.c (arc_trampoline_init): ... here.
        (TARGET_TRAMPOLINE_INIT): New.
 
+       * config/arm/arm.c (TARGET_ASM_TRAMPOLINE_TEMPLATE): New.
+       (TARGET_TRAMPOLINE_INIT, TARGET_TRAMPOLINE_ADJUST_ADDRESS): New.
+       (arm_asm_trampoline_template): New.
+       (arm_trampoline_init, arm_trampoline_adjust_address): New.
+       * config/arm/arm.h (TRAMPOLINE_TEMPLATE, ARM_TRAMPOLINE_TEMPLATE,
+       THUMB2_TRAMPOLINE_TEMPLATE, THUMB1_TRAMPOLINE_TEMPLATE): Move all
+       code to arm_asm_trampoline_template.
+       (TRAMPOLINE_ADJUST_ADDRESS): Move code to
+       arm_trampoline_adjust_address.
+       (INITIALIZE_TRAMPOLINE): Move code to arm_trampoline_init;
+       adjust for target hook parameters.
+
 2009-09-22  Richard Guenther  <rguenther@suse.de>
 
        PR middle-end/41395
index 1cc9557361a242237089392277b6a0ed920c1746..efc329b823bf015b469cd0765535d8a3f42649c2 100644 (file)
@@ -219,6 +219,9 @@ static tree arm_convert_to_type (tree type, tree expr);
 static bool arm_scalar_mode_supported_p (enum machine_mode);
 static bool arm_frame_pointer_required (void);
 static bool arm_can_eliminate (const int, const int);
+static void arm_asm_trampoline_template (FILE *);
+static void arm_trampoline_init (rtx, tree, rtx);
+static rtx arm_trampoline_adjust_address (rtx);
 
 \f
 /* Table of machine attributes.  */
@@ -366,6 +369,13 @@ static const struct attribute_spec arm_attribute_table[] =
 #undef TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS
 #define TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS arm_allocate_stack_slots_for_args
 
+#undef TARGET_ASM_TRAMPOLINE_TEMPLATE
+#define TARGET_ASM_TRAMPOLINE_TEMPLATE arm_asm_trampoline_template
+#undef TARGET_TRAMPOLINE_INIT
+#define TARGET_TRAMPOLINE_INIT arm_trampoline_init
+#undef TARGET_TRAMPOLINE_ADJUST_ADDRESS
+#define TARGET_TRAMPOLINE_ADJUST_ADDRESS arm_trampoline_adjust_address
+
 #undef TARGET_DEFAULT_SHORT_ENUMS
 #define TARGET_DEFAULT_SHORT_ENUMS arm_default_short_enums
 
@@ -1985,6 +1995,84 @@ arm_allocate_stack_slots_for_args (void)
   return !IS_NAKED (arm_current_func_type ());
 }
 
+\f
+/* Output assembler code for a block containing the constant parts
+   of a trampoline, leaving space for the variable parts.
+
+   On the ARM, (if r8 is the static chain regnum, and remembering that
+   referencing pc adds an offset of 8) the trampoline looks like:
+          ldr          r8, [pc, #0]
+          ldr          pc, [pc]
+          .word        static chain value
+          .word        function's address
+   XXX FIXME: When the trampoline returns, r8 will be clobbered.  */
+
+static void
+arm_asm_trampoline_template (FILE *f)
+{
+  if (TARGET_ARM)
+    {
+      asm_fprintf (f, "\tldr\t%r, [%r, #0]\n", STATIC_CHAIN_REGNUM, PC_REGNUM);
+      asm_fprintf (f, "\tldr\t%r, [%r, #0]\n", PC_REGNUM, PC_REGNUM);
+    }
+  else if (TARGET_THUMB2)
+    {
+      /* The Thumb-2 trampoline is similar to the arm implementation.
+        Unlike 16-bit Thumb, we enter the stub in thumb mode.  */
+      asm_fprintf (f, "\tldr.w\t%r, [%r, #4]\n",
+                  STATIC_CHAIN_REGNUM, PC_REGNUM);
+      asm_fprintf (f, "\tldr.w\t%r, [%r, #4]\n", PC_REGNUM, PC_REGNUM);
+    }
+  else
+    {
+      ASM_OUTPUT_ALIGN (f, 2);
+      fprintf (f, "\t.code\t16\n");
+      fprintf (f, ".Ltrampoline_start:\n");
+      asm_fprintf (f, "\tpush\t{r0, r1}\n");
+      asm_fprintf (f, "\tldr\tr0, [%r, #8]\n", PC_REGNUM);
+      asm_fprintf (f, "\tmov\t%r, r0\n", STATIC_CHAIN_REGNUM);
+      asm_fprintf (f, "\tldr\tr0, [%r, #8]\n", PC_REGNUM);
+      asm_fprintf (f, "\tstr\tr0, [%r, #4]\n", SP_REGNUM);
+      asm_fprintf (f, "\tpop\t{r0, %r}\n", PC_REGNUM);
+    }
+  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);
+  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);
+}
+
+/* Emit RTL insns to initialize the variable parts of a trampoline.  */
+
+static void
+arm_trampoline_init (rtx m_tramp, tree fndecl, rtx chain_value)
+{
+  rtx fnaddr, mem, a_tramp;
+
+  emit_block_move (m_tramp, assemble_trampoline_template (),
+                  GEN_INT (TRAMPOLINE_SIZE), BLOCK_OP_NORMAL);
+
+  mem = adjust_address (m_tramp, SImode, TARGET_32BIT ? 8 : 12);
+  emit_move_insn (mem, chain_value);
+
+  mem = adjust_address (m_tramp, SImode, TARGET_32BIT ? 12 : 16);
+  fnaddr = XEXP (DECL_RTL (fndecl), 0);
+  emit_move_insn (mem, fnaddr);
+
+  a_tramp = XEXP (m_tramp, 0);
+  emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__clear_cache"),
+                    LCT_NORMAL, VOIDmode, 2, a_tramp, Pmode,
+                    plus_constant (a_tramp, TRAMPOLINE_SIZE), Pmode);
+}
+
+/* Thumb trampolines should be entered in thumb mode, so set
+   the bottom bit of the address.  */
+
+static rtx
+arm_trampoline_adjust_address (rtx addr)
+{
+  if (TARGET_THUMB)
+    addr = expand_simple_binop (Pmode, IOR, addr, const1_rtx,
+                               NULL, 0, OPTAB_LIB_WIDEN);
+  return addr;
+}
 \f
 /* Return 1 if it is possible to return using a single instruction.
    If SIBLING is non-null, this is a test for a return before a sibling
index 215c9fba789b5188f1af06a3f227baf2d6bfb42f..9272ca51cbadf1d34800d43665a268d8991f0a99 100644 (file)
@@ -1861,102 +1861,11 @@ typedef struct
    once for every function before code is generated.  */
 #define INIT_EXPANDERS  arm_init_expanders ()
 
-/* Output assembler code for a block containing the constant parts
-   of a trampoline, leaving space for the variable parts.
-
-   On the ARM, (if r8 is the static chain regnum, and remembering that
-   referencing pc adds an offset of 8) the trampoline looks like:
-          ldr          r8, [pc, #0]
-          ldr          pc, [pc]
-          .word        static chain value
-          .word        function's address
-   XXX FIXME: When the trampoline returns, r8 will be clobbered.  */
-#define ARM_TRAMPOLINE_TEMPLATE(FILE)                          \
-{                                                              \
-  asm_fprintf (FILE, "\tldr\t%r, [%r, #0]\n",                  \
-              STATIC_CHAIN_REGNUM, PC_REGNUM);                 \
-  asm_fprintf (FILE, "\tldr\t%r, [%r, #0]\n",                  \
-              PC_REGNUM, PC_REGNUM);                           \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-}
-
-/* The Thumb-2 trampoline is similar to the arm implementation.
-   Unlike 16-bit Thumb, we enter the stub in thumb mode.  */
-#define THUMB2_TRAMPOLINE_TEMPLATE(FILE)                       \
-{                                                              \
-  asm_fprintf (FILE, "\tldr.w\t%r, [%r, #4]\n",                        \
-              STATIC_CHAIN_REGNUM, PC_REGNUM);                 \
-  asm_fprintf (FILE, "\tldr.w\t%r, [%r, #4]\n",                        \
-              PC_REGNUM, PC_REGNUM);                           \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-}
-
-#define THUMB1_TRAMPOLINE_TEMPLATE(FILE)       \
-{                                              \
-  ASM_OUTPUT_ALIGN(FILE, 2);                   \
-  fprintf (FILE, "\t.code\t16\n");             \
-  fprintf (FILE, ".Ltrampoline_start:\n");     \
-  asm_fprintf (FILE, "\tpush\t{r0, r1}\n");    \
-  asm_fprintf (FILE, "\tldr\tr0, [%r, #8]\n",  \
-              PC_REGNUM);                      \
-  asm_fprintf (FILE, "\tmov\t%r, r0\n",                \
-              STATIC_CHAIN_REGNUM);            \
-  asm_fprintf (FILE, "\tldr\tr0, [%r, #8]\n",  \
-              PC_REGNUM);                      \
-  asm_fprintf (FILE, "\tstr\tr0, [%r, #4]\n",  \
-              SP_REGNUM);                      \
-  asm_fprintf (FILE, "\tpop\t{r0, %r}\n",      \
-              PC_REGNUM);                      \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-  assemble_aligned_integer (UNITS_PER_WORD, const0_rtx);       \
-}
-
-#define TRAMPOLINE_TEMPLATE(FILE)              \
-  if (TARGET_ARM)                              \
-    ARM_TRAMPOLINE_TEMPLATE (FILE)             \
-  else if (TARGET_THUMB2)                      \
-    THUMB2_TRAMPOLINE_TEMPLATE (FILE)          \
-  else                                         \
-    THUMB1_TRAMPOLINE_TEMPLATE (FILE)
-
-/* Thumb trampolines should be entered in thumb mode, so set the bottom bit
-   of the address.  */
-#define TRAMPOLINE_ADJUST_ADDRESS(ADDR) do                                 \
-{                                                                          \
-  if (TARGET_THUMB)                                                        \
-    (ADDR) = expand_simple_binop (Pmode, IOR, (ADDR), GEN_INT(1),          \
-                                 gen_reg_rtx (Pmode), 0, OPTAB_LIB_WIDEN); \
-} while(0)
-
 /* Length in units of the trampoline for entering a nested function.  */
 #define TRAMPOLINE_SIZE  (TARGET_32BIT ? 16 : 20)
 
 /* Alignment required for a trampoline in bits.  */
 #define TRAMPOLINE_ALIGNMENT  32
-
-
-/* Emit RTL insns to initialize the variable parts of a trampoline.
-   FNADDR is an RTX for the address of the function's pure code.
-   CXT is an RTX for the static chain value for the function.  */
-#ifndef INITIALIZE_TRAMPOLINE
-#define INITIALIZE_TRAMPOLINE(TRAMP, FNADDR, CXT)                      \
-{                                                                      \
-  emit_move_insn (gen_rtx_MEM (SImode,                                 \
-                              plus_constant (TRAMP,                    \
-                                             TARGET_32BIT ? 8 : 12)),  \
-                 CXT);                                                 \
-  emit_move_insn (gen_rtx_MEM (SImode,                                 \
-                              plus_constant (TRAMP,                    \
-                                             TARGET_32BIT ? 12 : 16)), \
-                 FNADDR);                                              \
-  emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__clear_cache"),      \
-                    LCT_NORMAL, VOIDmode, 2, TRAMP, Pmode,             \
-                    plus_constant (TRAMP, TRAMPOLINE_SIZE), Pmode);    \
-}
-#endif
-
 \f
 /* Addressing modes, and classification of registers for them.  */
 #define HAVE_POST_INCREMENT   1