build: check if AS supports the '.func' directive
[libav.git] / libavutil / arm / asm.S
1 /*
2  * Copyright (c) 2008 Mans Rullgard <mans@mansr.com>
3  *
4  * This file is part of Libav.
5  *
6  * Libav is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * Libav is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with Libav; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20
21 #include "config.h"
22
23 #ifdef __ELF__
24 #   define ELF
25 #else
26 #   define ELF @
27 #endif
28
29 #if CONFIG_THUMB
30 #   define A @
31 #   define T
32 #else
33 #   define A
34 #   define T @
35 #endif
36
37 #if HAVE_AS_FUNC
38 #   define FUNC
39 #else
40 #   define FUNC @
41 #endif
42
43 #if   HAVE_NEON
44         .arch           armv7-a
45 #elif HAVE_ARMV6T2
46         .arch           armv6t2
47 #elif HAVE_ARMV6
48         .arch           armv6
49 #elif HAVE_ARMV5TE
50         .arch           armv5te
51 #endif
52
53 #if   HAVE_NEON
54         .fpu            neon
55 #elif HAVE_VFP
56         .fpu            vfp
57 #endif
58
59         .syntax unified
60 T       .thumb
61 ELF     .eabi_attribute 25, 1           @ Tag_ABI_align_preserved
62 ELF     .section .note.GNU-stack,"",%progbits @ Mark stack as non-executable
63
64 .macro  function name, export=0, align=2
65         .set            .Lpic_idx, 0
66         .set            .Lpic_gp, 0
67     .macro endfunc
68       .if .Lpic_idx
69         .align          2
70         .altmacro
71         put_pic         %(.Lpic_idx - 1)
72         .noaltmacro
73       .endif
74 ELF     .size   \name, . - \name
75 FUNC    .endfunc
76         .purgem endfunc
77     .endm
78         .text
79         .align          \align
80     .if \export
81         .global EXTERN_ASM\name
82 ELF     .type   EXTERN_ASM\name, %function
83 FUNC    .func   EXTERN_ASM\name
84 EXTERN_ASM\name:
85     .else
86 ELF     .type   \name, %function
87 FUNC    .func   \name
88 \name:
89     .endif
90 .endm
91
92 .macro  const   name, align=2
93     .macro endconst
94 ELF     .size   \name, . - \name
95         .purgem endconst
96     .endm
97         .section        .rodata
98         .align          \align
99 \name:
100 .endm
101
102 #if !HAVE_ARMV6T2_EXTERNAL
103 .macro  movw    rd, val
104         mov     \rd, \val &  255
105         orr     \rd, \val & ~255
106 .endm
107 #endif
108
109 .macro  mov32   rd, val
110 #if HAVE_ARMV6T2_EXTERNAL
111         movw            \rd, #(\val) & 0xffff
112     .if (\val) >> 16
113         movt            \rd, #(\val) >> 16
114     .endif
115 #else
116         ldr             \rd, =\val
117 #endif
118 .endm
119
120 .macro  put_pic         num
121         put_pic_\num
122 .endm
123
124 .macro  do_def_pic      num, val, label
125     .macro put_pic_\num
126       .if \num
127         .altmacro
128         put_pic         %(\num - 1)
129         .noaltmacro
130       .endif
131 \label: .word           \val
132         .purgem         put_pic_\num
133     .endm
134 .endm
135
136 .macro  def_pic         val, label
137         .altmacro
138         do_def_pic      %.Lpic_idx, \val, \label
139         .noaltmacro
140         .set            .Lpic_idx, .Lpic_idx + 1
141 .endm
142
143 .macro  ldpic           rd,  val, indir=0
144         ldr             \rd, .Lpicoff\@
145 .Lpic\@:
146     .if \indir
147 A       ldr             \rd, [pc, \rd]
148 T       add             \rd, pc
149 T       ldr             \rd, [\rd]
150     .else
151         add             \rd, pc
152     .endif
153         def_pic         \val - (.Lpic\@ + (8 >> CONFIG_THUMB)), .Lpicoff\@
154 .endm
155
156 .macro  movrel rd, val
157 #if CONFIG_PIC
158         ldpic           \rd, \val
159 #elif HAVE_ARMV6T2_EXTERNAL && !defined(__APPLE__)
160         movw            \rd, #:lower16:\val
161         movt            \rd, #:upper16:\val
162 #else
163         ldr             \rd, =\val
164 #endif
165 .endm
166
167 .macro  movrelx         rd,  val, gp
168 #if CONFIG_PIC && defined(__ELF__)
169     .ifnb \gp
170       .if .Lpic_gp
171         .unreq          gp
172       .endif
173         gp      .req    \gp
174         ldpic           gp,  _GLOBAL_OFFSET_TABLE_
175     .elseif !.Lpic_gp
176         gp      .req    r12
177         ldpic           gp,  _GLOBAL_OFFSET_TABLE_
178     .endif
179         .set            .Lpic_gp, 1
180         ldr             \rd, .Lpicoff\@
181         ldr             \rd, [gp, \rd]
182         def_pic         \val(GOT), .Lpicoff\@
183 #elif CONFIG_PIC && defined(__APPLE__)
184         ldpic           \rd, .Lpic\@, indir=1
185         .non_lazy_symbol_pointer
186 .Lpic\@:
187         .indirect_symbol \val
188         .word           0
189         .text
190 #else
191         movrel          \rd, \val
192 #endif
193 .endm
194
195 .macro  add_sh          rd,  rn,  rm,  sh:vararg
196 A       add             \rd, \rn, \rm, \sh
197 T       mov             \rm, \rm, \sh
198 T       add             \rd, \rn, \rm
199 .endm
200
201 .macro  ldr_pre         rt,  rn,  rm:vararg
202 A       ldr             \rt, [\rn, \rm]!
203 T       add             \rn, \rn, \rm
204 T       ldr             \rt, [\rn]
205 .endm
206
207 .macro  ldr_dpre        rt,  rn,  rm:vararg
208 A       ldr             \rt, [\rn, -\rm]!
209 T       sub             \rn, \rn, \rm
210 T       ldr             \rt, [\rn]
211 .endm
212
213 .macro  ldr_nreg        rt,  rn,  rm:vararg
214 A       ldr             \rt, [\rn, -\rm]
215 T       sub             \rt, \rn, \rm
216 T       ldr             \rt, [\rt]
217 .endm
218
219 .macro  ldr_post        rt,  rn,  rm:vararg
220 A       ldr             \rt, [\rn], \rm
221 T       ldr             \rt, [\rn]
222 T       add             \rn, \rn, \rm
223 .endm
224
225 .macro  ldrc_pre        cc,  rt,  rn,  rm:vararg
226 A       ldr\cc          \rt, [\rn, \rm]!
227 T       itt             \cc
228 T       add\cc          \rn, \rn, \rm
229 T       ldr\cc          \rt, [\rn]
230 .endm
231
232 .macro  ldrd_reg        rt,  rt2, rn,  rm
233 A       ldrd            \rt, \rt2, [\rn, \rm]
234 T       add             \rt, \rn, \rm
235 T       ldrd            \rt, \rt2, [\rt]
236 .endm
237
238 .macro  ldrd_post       rt,  rt2, rn,  rm
239 A       ldrd            \rt, \rt2, [\rn], \rm
240 T       ldrd            \rt, \rt2, [\rn]
241 T       add             \rn, \rn, \rm
242 .endm
243
244 .macro  ldrh_pre        rt,  rn,  rm
245 A       ldrh            \rt, [\rn, \rm]!
246 T       add             \rn, \rn, \rm
247 T       ldrh            \rt, [\rn]
248 .endm
249
250 .macro  ldrh_dpre       rt,  rn,  rm
251 A       ldrh            \rt, [\rn, -\rm]!
252 T       sub             \rn, \rn, \rm
253 T       ldrh            \rt, [\rn]
254 .endm
255
256 .macro  ldrh_post       rt,  rn,  rm
257 A       ldrh            \rt, [\rn], \rm
258 T       ldrh            \rt, [\rn]
259 T       add             \rn, \rn, \rm
260 .endm
261
262 .macro  ldrb_post       rt,  rn,  rm
263 A       ldrb            \rt, [\rn], \rm
264 T       ldrb            \rt, [\rn]
265 T       add             \rn, \rn, \rm
266 .endm
267
268 .macro  str_post       rt,  rn,  rm:vararg
269 A       str             \rt, [\rn], \rm
270 T       str             \rt, [\rn]
271 T       add             \rn, \rn, \rm
272 .endm
273
274 .macro  strb_post       rt,  rn,  rm:vararg
275 A       strb            \rt, [\rn], \rm
276 T       strb            \rt, [\rn]
277 T       add             \rn, \rn, \rm
278 .endm
279
280 .macro  strd_post       rt,  rt2, rn,  rm
281 A       strd            \rt, \rt2, [\rn], \rm
282 T       strd            \rt, \rt2, [\rn]
283 T       add             \rn, \rn, \rm
284 .endm
285
286 .macro  strh_pre        rt,  rn,  rm
287 A       strh            \rt, [\rn, \rm]!
288 T       add             \rn, \rn, \rm
289 T       strh            \rt, [\rn]
290 .endm
291
292 .macro  strh_dpre       rt,  rn,  rm
293 A       strh            \rt, [\rn, -\rm]!
294 T       sub             \rn, \rn, \rm
295 T       strh            \rt, [\rn]
296 .endm
297
298 .macro  strh_post       rt,  rn,  rm
299 A       strh            \rt, [\rn], \rm
300 T       strh            \rt, [\rn]
301 T       add             \rn, \rn, \rm
302 .endm
303
304 .macro  strh_dpost       rt,  rn,  rm
305 A       strh            \rt, [\rn], -\rm
306 T       strh            \rt, [\rn]
307 T       sub             \rn, \rn, \rm
308 .endm
309
310 #if HAVE_VFP_ARGS
311 ELF     .eabi_attribute 28, 1
312 #   define VFP
313 #   define NOVFP @
314 #else
315 #   define VFP   @
316 #   define NOVFP
317 #endif
318
319 #define GLUE(a, b) a ## b
320 #define JOIN(a, b) GLUE(a, b)
321 #define X(s) JOIN(EXTERN_ASM, s)