1 /* Assembler macros for ARM.
2 Copyright (C) 1997-2014 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library. If not, see
17 <http://www.gnu.org/licenses/>. */
19 #include <sysdeps/generic/sysdep.h>
22 /* The __ARM_ARCH define is provided by gcc 4.8. Construct it otherwise. */
24 # ifdef __ARM_ARCH_2__
26 # elif defined (__ARM_ARCH_3__) || defined (__ARM_ARCH_3M__)
28 # elif defined (__ARM_ARCH_4__) || defined (__ARM_ARCH_4T__)
30 # elif defined (__ARM_ARCH_5__) || defined (__ARM_ARCH_5E__) \
31 || defined(__ARM_ARCH_5T__) || defined(__ARM_ARCH_5TE__) \
32 || defined(__ARM_ARCH_5TEJ__)
34 # elif defined (__ARM_ARCH_6__) || defined(__ARM_ARCH_6J__) \
35 || defined (__ARM_ARCH_6Z__) || defined(__ARM_ARCH_6ZK__) \
36 || defined (__ARM_ARCH_6K__) || defined(__ARM_ARCH_6T2__)
38 # elif defined (__ARM_ARCH_7__) || defined(__ARM_ARCH_7A__) \
39 || defined(__ARM_ARCH_7R__) || defined(__ARM_ARCH_7M__) \
40 || defined(__ARM_ARCH_7EM__)
43 # error unknown arm architecture
47 #if __ARM_ARCH > 4 || defined (__ARM_ARCH_4T__)
53 #if __ARM_ARCH > 6 || defined (__ARM_ARCH_6K__) || defined (__ARM_ARCH_6ZK__)
54 # define ARCH_HAS_HARD_TP
56 #if __ARM_ARCH > 6 || defined (__ARM_ARCH_6T2__)
62 /* Syntactic details of assembler. */
64 #define ALIGNARG(log2) log2
65 #define ASM_SIZE_DIRECTIVE(name) .size name,.-name
67 #define PLTJMP(_x) _x##(PLT)
71 # define BXC(C, R) bx##C R
75 # define BLX(R) mov lr, pc; bx R
78 # define BX(R) mov pc, R
79 # define BXC(C, R) mov##C pc, R
80 # define BLX(R) mov lr, pc; mov pc, R
83 #define DO_RET(R) BX(R)
84 #define RETINSTR(C, R) BXC(C, R)
86 /* Define an entry point visible from C. */
88 .globl C_SYMBOL_NAME(name); \
89 .type C_SYMBOL_NAME(name),%function; \
96 #define CFI_SECTIONS \
97 .cfi_sections .debug_frame
102 ASM_SIZE_DIRECTIVE(name)
104 /* If compiled for profiling, call `mcount' at the start of each function. */
106 /* Call __gnu_mcount_nc if GCC >= 4.4. */
107 #if __GNUC_PREREQ(4,4)
108 #define CALL_MCOUNT \
110 cfi_adjust_cfa_offset (4); \
111 cfi_rel_offset (lr, 0); \
113 cfi_adjust_cfa_offset (-4); \
115 #else /* else call _mcount */
116 #define CALL_MCOUNT \
118 cfi_adjust_cfa_offset (4); \
119 cfi_rel_offset (lr, 0); \
122 cfi_adjust_cfa_offset (-4); \
126 #define CALL_MCOUNT /* Do nothing. */
129 /* Since C identifiers are not normally prefixed with an underscore
130 on this system, the asm identifier `syscall_error' intrudes on the
131 C name space. Make sure we use an innocuous name. */
132 #define syscall_error __syscall_error
133 #if __GNUC_PREREQ(4,4)
134 #define mcount __gnu_mcount_nc
136 #define mcount _mcount
139 /* Tag_ABI_align8_preserved: This code preserves 8-byte
140 alignment in any callee. */
141 .eabi_attribute
25, 1
142 /* Tag_ABI_align8_needed: This code may require 8-byte alignment from
144 .eabi_attribute
24, 1
146 /* The thumb2 encoding is reasonably complete. Unless suppressed, use it. */
148 # if defined(__thumb2__) && !defined(NO_THUMB)
156 /* Load or store to/from a pc-relative EXPR into/from R, using T. */
158 # define LDST_PCREL(OP, R, T, EXPR) \
161 98: .word EXPR - 99f - PC_OFS; \
166 # define LDST_PCREL(OP, R, T, EXPR) \
169 98: .word EXPR - 99f - PC_OFS; \
174 /* Load or store to/from a global EXPR into/from R, using T. */
175 # define LDST_GLOBAL(OP, R, T, EXPR) \
181 99: .word _GLOBAL_OFFSET_TABLE_ - 98b - PC_OFS; \
182 100: .word EXPR##(GOT); \
186 /* Cope with negative memory offsets, which thumb can't encode.
187 Use NEGOFF_ADJ_BASE to (conditionally) alter the base register,
188 and then NEGOFF_OFF1 to use 0 for thumb and the offset for arm,
189 or NEGOFF_OFF2 to use A-B for thumb and A for arm. */
191 # define NEGOFF_ADJ_BASE(R, OFF) add R, R, $OFF
192 # define NEGOFF_ADJ_BASE2(D, S, OFF) add D, S, $OFF
193 # define NEGOFF_OFF1(R, OFF) [R]
194 # define NEGOFF_OFF2(R, OFFA, OFFB) [R, $((OFFA) - (OFFB))]
196 # define NEGOFF_ADJ_BASE(R, OFF)
197 # define NEGOFF_ADJ_BASE2(D, S, OFF) mov D, S
198 # define NEGOFF_OFF1(R, OFF) [R, $OFF]
199 # define NEGOFF_OFF2(R, OFFA, OFFB) [R, $OFFA]
202 /* Helper to get the TLS base pointer. The interface is that TMP is a
203 register that may be used to hold the LR, if necessary. TMP may be
204 LR itself to indicate that LR need not be saved. The base pointer
205 is returned in R0. Only R0 and TMP are modified. */
207 # ifdef ARCH_HAS_HARD_TP
208 /* If the cpu has cp15 available, use it. */
209 # define GET_TLS(TMP) mrc p15, 0, r0, c13, c0, 3
211 /* At this generic level we have no tricks to pull. Call the ABI routine. */
212 # define GET_TLS(TMP) \
213 push { r1, r2, r3, lr }; \
214 cfi_remember_state; \
215 cfi_adjust_cfa_offset (16); \
216 cfi_rel_offset (r1, 0); \
217 cfi_rel_offset (r2, 4); \
218 cfi_rel_offset (r3, 8); \
219 cfi_rel_offset (lr, 12); \
220 bl __aeabi_read_tp; \
221 pop { r1, r2, r3, lr }; \
223 # endif /* ARCH_HAS_HARD_TP */
225 # ifndef ARM_SFI_MACROS
226 # define ARM_SFI_MACROS 1
227 /* This assembly macro is prepended to any load/store instruction,
228 pulling the base register out of the addressing mode syntax and
229 making it the first operand of the macro. For example:
232 sfi_breg r1, ldr r0, [\B]
233 The \B stands in for the base register that is the first operand
234 to the macro, so we can avoid error-prone repetition of the base
235 register in two places on the line.
237 This is used for all memory access through a base register other
238 than PC or SP. It's intended to support SFI schemes such as
239 Native Client, where the OS will enforce that all load/store
240 instructions use a special form. In any such configuration,
241 another sysdep.h file will have defined ARM_SFI_MACROS and
242 provided its own assembly macros with the same interface. */
244 .macro sfi_breg basereg
, insn
, operands
:vararg
245 .macro _sfi_breg_doit B
248 _sfi_breg_doit
\basereg
249 .purgem _sfi_breg_doit
252 /* This assembly macro replaces the "pld" instruction.
254 sfi_pld REGISTER, #OFFSET
255 is exactly equivalent to:
256 sfi_breg REGISTER, pld [\B, #OFFSET]
257 (and ", #OFFSET" is optional). We have a separate macro
258 only to work around a bug in GAS versions prior to 2.23.2,
259 that misparses the sfi_breg macro expansion in this case. */
261 .macro sfi_pld basereg
, offset
=#0
262 pld
[\basereg
, \offset
]
265 /* This macro precedes any instruction that directly changes the SP.
266 It's not needed for push/pop or for any kind of load or store that
267 implicitly changes the SP via the ! syntax. */
268 # define sfi_sp /* Nothing to do. */
272 /* These are the directives used for EABI unwind info.
273 Wrap them in macros so another configuration's sysdep.h
274 file can define them away if it doesn't use EABI unwind info. */
275 # define eabi_fnstart .fnstart
276 # define eabi_fnend .fnend
277 # define eabi_save(...) .save __VA_ARGS__
278 # define eabi_cantunwind .cantunwind
279 # define eabi_pad(n) .pad n
281 #endif /* __ASSEMBLER__ */
283 /* This number is the offset from the pc at the current location. */