Update copyright notices with scripts/update-copyrights.
[jlayton/glibc.git] / ports / sysdeps / unix / sysv / linux / arm / sysdep.h
1 /* Copyright (C) 1992-2013 Free Software Foundation, Inc.
2    This file is part of the GNU C Library.
3    Contributed by Ulrich Drepper, <drepper@gnu.ai.mit.edu>, August 1995.
4    ARM changes by Philip Blundell, <pjb27@cam.ac.uk>, May 1997.
5
6    The GNU C Library 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    The GNU C Library 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 the GNU C Library.  If not, see
18    <http://www.gnu.org/licenses/>.  */
19
20 #ifndef _LINUX_ARM_SYSDEP_H
21 #define _LINUX_ARM_SYSDEP_H 1
22
23 /* There is some commonality.  */
24 #include <sysdeps/unix/arm/sysdep.h>
25
26 /* Defines RTLD_PRIVATE_ERRNO and USE_DL_SYSINFO.  */
27 #include <dl-sysdep.h>
28
29 #include <tls.h>
30
31 /* In order to get __set_errno() definition in INLINE_SYSCALL.  */
32 #ifndef __ASSEMBLER__
33 #include <errno.h>
34 #endif
35
36 /* For Linux we can use the system call table in the header file
37         /usr/include/asm/unistd.h
38    of the kernel.  But these symbols do not follow the SYS_* syntax
39    so we have to redefine the `SYS_ify' macro here.  */
40 #undef SYS_ify
41 #define SYS_ify(syscall_name)   (__NR_##syscall_name)
42
43 #define _SYS_AUXV_H 1
44 #include <bits/hwcap.h>
45
46 #ifdef __ASSEMBLER__
47
48 /* Linux uses a negative return value to indicate syscall errors,
49    unlike most Unices, which use the condition codes' carry flag.
50
51    Since version 2.1 the return value of a system call might be
52    negative even if the call succeeded.  E.g., the `lseek' system call
53    might return a large offset.  Therefore we must not anymore test
54    for < 0, but test for a real error by making sure the value in R0
55    is a real error number.  Linus said he will make sure the no syscall
56    returns a value in -1 .. -4095 as a valid result so we can safely
57    test with -4095.  */
58
59 #undef  PSEUDO
60 #define PSEUDO(name, syscall_name, args)                                      \
61   .text;                                                                      \
62   ENTRY (name);                                                               \
63     DO_CALL (syscall_name, args);                                             \
64     cmn r0, $4096;
65
66 #define PSEUDO_RET                                                            \
67     RETINSTR(cc, lr);                                                         \
68     b PLTJMP(SYSCALL_ERROR)
69 #undef ret
70 #define ret PSEUDO_RET
71
72 #undef  PSEUDO_END
73 #define PSEUDO_END(name)                                                      \
74   SYSCALL_ERROR_HANDLER;                                                      \
75   END (name)
76
77 #undef  PSEUDO_NOERRNO
78 #define PSEUDO_NOERRNO(name, syscall_name, args)                              \
79   .text;                                                                      \
80   ENTRY (name);                                                               \
81     DO_CALL (syscall_name, args);
82
83 #define PSEUDO_RET_NOERRNO                                                    \
84     DO_RET (lr);
85
86 #undef ret_NOERRNO
87 #define ret_NOERRNO PSEUDO_RET_NOERRNO
88
89 #undef  PSEUDO_END_NOERRNO
90 #define PSEUDO_END_NOERRNO(name)                                              \
91   END (name)
92
93 /* The function has to return the error code.  */
94 #undef  PSEUDO_ERRVAL
95 #define PSEUDO_ERRVAL(name, syscall_name, args) \
96   .text;                                                                      \
97   ENTRY (name)                                                                \
98     DO_CALL (syscall_name, args);                                             \
99     rsb r0, r0, #0
100
101 #undef  PSEUDO_END_ERRVAL
102 #define PSEUDO_END_ERRVAL(name) \
103   END (name)
104
105 #define ret_ERRVAL PSEUDO_RET_NOERRNO
106
107 #if NOT_IN_libc
108 # define SYSCALL_ERROR __local_syscall_error
109 # if RTLD_PRIVATE_ERRNO
110 #  define SYSCALL_ERROR_HANDLER                                 \
111 __local_syscall_error:                                          \
112        ldr     r1, 1f;                                          \
113        rsb     r0, r0, #0;                                      \
114 0:     str     r0, [pc, r1];                                    \
115        mvn     r0, #0;                                          \
116        DO_RET(lr);                                              \
117 1:     .word C_SYMBOL_NAME(rtld_errno) - 0b - 8;
118 # else
119 #  if defined(__ARM_ARCH_4T__) && defined(__THUMB_INTERWORK__)
120 #   define POP_PC \
121   ldr lr, [sp], #4; \
122   cfi_adjust_cfa_offset (-4); \
123   cfi_restore (lr); \
124   bx lr
125 #  else
126 #   define POP_PC  \
127   ldr pc, [sp], #4
128 #  endif
129 #  define SYSCALL_ERROR_HANDLER                                 \
130 __local_syscall_error:                                          \
131         str     lr, [sp, #-4]!;                                 \
132         cfi_adjust_cfa_offset (4);                              \
133         cfi_rel_offset (lr, 0);                                 \
134         str     r0, [sp, #-4]!;                                 \
135         cfi_adjust_cfa_offset (4);                              \
136         bl      PLTJMP(C_SYMBOL_NAME(__errno_location));        \
137         ldr     r1, [sp], #4;                                   \
138         cfi_adjust_cfa_offset (-4);                             \
139         rsb     r1, r1, #0;                                     \
140         str     r1, [r0];                                       \
141         mvn     r0, #0;                                         \
142         POP_PC;
143 # endif
144 #else
145 # define SYSCALL_ERROR_HANDLER  /* Nothing here; code in sysdep.S is used.  */
146 # define SYSCALL_ERROR __syscall_error
147 #endif
148
149 /* The ARM EABI user interface passes the syscall number in r7, instead
150    of in the swi.  This is more efficient, because the kernel does not need
151    to fetch the swi from memory to find out the number; which can be painful
152    with separate I-cache and D-cache.  Make sure to use 0 for the SWI
153    argument; otherwise the (optional) compatibility code for APCS binaries
154    may be invoked.  */
155
156 /* Linux takes system call args in registers:
157         arg 1           r0
158         arg 2           r1
159         arg 3           r2
160         arg 4           r3
161         arg 5           r4      (this is different from the APCS convention)
162         arg 6           r5
163         arg 7           r6
164
165    The compiler is going to form a call by coming here, through PSEUDO, with
166    arguments
167         syscall number  in the DO_CALL macro
168         arg 1           r0
169         arg 2           r1
170         arg 3           r2
171         arg 4           r3
172         arg 5           [sp]
173         arg 6           [sp+4]
174         arg 7           [sp+8]
175
176    We need to shuffle values between R4..R6 and the stack so that the
177    caller's v1..v3 and stack frame are not corrupted, and the kernel
178    sees the right arguments.
179
180 */
181
182 /* We must save and restore r7 (call-saved) for the syscall number.
183    We never make function calls from inside here (only potentially
184    signal handlers), so we do not bother with doubleword alignment.
185
186    Just like the APCS syscall convention, the EABI syscall convention uses
187    r0 through r6 for up to seven syscall arguments.  None are ever passed to
188    the kernel on the stack, although incoming arguments are on the stack for
189    syscalls with five or more arguments.
190
191    The assembler will convert the literal pool load to a move for most
192    syscalls.  */
193
194 #undef  DO_CALL
195 #define DO_CALL(syscall_name, args)             \
196     DOARGS_##args;                              \
197     ldr r7, =SYS_ify (syscall_name);            \
198     swi 0x0;                                    \
199     UNDOARGS_##args
200
201 #undef  DOARGS_0
202 #define DOARGS_0 \
203   .fnstart; \
204   str r7, [sp, #-4]!; \
205   cfi_adjust_cfa_offset (4); \
206   cfi_rel_offset (r7, 0); \
207   .save { r7 }
208 #undef  DOARGS_1
209 #define DOARGS_1 DOARGS_0
210 #undef  DOARGS_2
211 #define DOARGS_2 DOARGS_0
212 #undef  DOARGS_3
213 #define DOARGS_3 DOARGS_0
214 #undef  DOARGS_4
215 #define DOARGS_4 DOARGS_0
216 #undef  DOARGS_5
217 #define DOARGS_5 \
218   .fnstart; \
219   stmfd sp!, {r4, r7}; \
220   cfi_adjust_cfa_offset (8); \
221   cfi_rel_offset (r4, 0); \
222   cfi_rel_offset (r7, 4); \
223   .save { r4, r7 }; \
224   ldr r4, [sp, #8]
225 #undef  DOARGS_6
226 #define DOARGS_6 \
227   .fnstart; \
228   mov ip, sp; \
229   stmfd sp!, {r4, r5, r7}; \
230   cfi_adjust_cfa_offset (12); \
231   cfi_rel_offset (r4, 0); \
232   cfi_rel_offset (r5, 4); \
233   cfi_rel_offset (r7, 8); \
234   .save { r4, r5, r7 }; \
235   ldmia ip, {r4, r5}
236 #undef  DOARGS_7
237 #define DOARGS_7 \
238   .fnstart; \
239   mov ip, sp; \
240   stmfd sp!, {r4, r5, r6, r7}; \
241   cfi_adjust_cfa_offset (16); \
242   cfi_rel_offset (r4, 0); \
243   cfi_rel_offset (r5, 4); \
244   cfi_rel_offset (r6, 8); \
245   cfi_rel_offset (r7, 12); \
246   .save { r4, r5, r6, r7 }; \
247   ldmia ip, {r4, r5, r6}
248
249 #undef  UNDOARGS_0
250 #define UNDOARGS_0 \
251   ldr r7, [sp], #4; \
252   cfi_adjust_cfa_offset (-4); \
253   cfi_restore (r7); \
254   .fnend
255 #undef  UNDOARGS_1
256 #define UNDOARGS_1 UNDOARGS_0
257 #undef  UNDOARGS_2
258 #define UNDOARGS_2 UNDOARGS_0
259 #undef  UNDOARGS_3
260 #define UNDOARGS_3 UNDOARGS_0
261 #undef  UNDOARGS_4
262 #define UNDOARGS_4 UNDOARGS_0
263 #undef  UNDOARGS_5
264 #define UNDOARGS_5 \
265   ldmfd sp!, {r4, r7}; \
266   cfi_adjust_cfa_offset (-8); \
267   cfi_restore (r4); \
268   cfi_restore (r7); \
269   .fnend
270 #undef  UNDOARGS_6
271 #define UNDOARGS_6 \
272   ldmfd sp!, {r4, r5, r7}; \
273   cfi_adjust_cfa_offset (-12); \
274   cfi_restore (r4); \
275   cfi_restore (r5); \
276   cfi_restore (r7); \
277   .fnend
278 #undef  UNDOARGS_7
279 #define UNDOARGS_7 \
280   ldmfd sp!, {r4, r5, r6, r7}; \
281   cfi_adjust_cfa_offset (-16); \
282   cfi_restore (r4); \
283   cfi_restore (r5); \
284   cfi_restore (r6); \
285   cfi_restore (r7); \
286   .fnend
287
288 #else /* not __ASSEMBLER__ */
289
290 /* Define a macro which expands into the inline wrapper code for a system
291    call.  */
292 #undef INLINE_SYSCALL
293 #define INLINE_SYSCALL(name, nr, args...)                               \
294   ({ unsigned int _sys_result = INTERNAL_SYSCALL (name, , nr, args);    \
295      if (__builtin_expect (INTERNAL_SYSCALL_ERROR_P (_sys_result, ), 0))        \
296        {                                                                \
297          __set_errno (INTERNAL_SYSCALL_ERRNO (_sys_result, ));          \
298          _sys_result = (unsigned int) -1;                               \
299        }                                                                \
300      (int) _sys_result; })
301
302 #undef INTERNAL_SYSCALL_DECL
303 #define INTERNAL_SYSCALL_DECL(err) do { } while (0)
304
305 #if defined(__thumb__)
306 /* We can not expose the use of r7 to the compiler.  GCC (as
307    of 4.5) uses r7 as the hard frame pointer for Thumb - although
308    for Thumb-2 it isn't obviously a better choice than r11.
309    And GCC does not support asms that conflict with the frame
310    pointer.
311
312    This would be easier if syscall numbers never exceeded 255,
313    but they do.  For the moment the LOAD_ARGS_7 is sacrificed.
314    We can't use push/pop inside the asm because that breaks
315    unwinding (i.e. thread cancellation) for this frame.  We can't
316    locally save and restore r7, because we do not know if this
317    function uses r7 or if it is our caller's r7; if it is our caller's,
318    then unwinding will fail higher up the stack.  So we move the
319    syscall out of line and provide its own unwind information.  */
320 # undef INTERNAL_SYSCALL_RAW
321 # define INTERNAL_SYSCALL_RAW(name, err, nr, args...)           \
322   ({                                                            \
323       register int _a1 asm ("a1");                              \
324       int _nametmp = name;                                      \
325       LOAD_ARGS_##nr (args)                                     \
326       register int _name asm ("ip") = _nametmp;                 \
327       asm volatile ("bl      __libc_do_syscall"                 \
328                     : "=r" (_a1)                                \
329                     : "r" (_name) ASM_ARGS_##nr                 \
330                     : "memory", "lr");                          \
331       _a1; })
332 #else /* ARM */
333 # undef INTERNAL_SYSCALL_RAW
334 # define INTERNAL_SYSCALL_RAW(name, err, nr, args...)           \
335   ({                                                            \
336        register int _a1 asm ("r0"), _nr asm ("r7");             \
337        LOAD_ARGS_##nr (args)                                    \
338        _nr = name;                                              \
339        asm volatile ("swi       0x0     @ syscall " #name       \
340                      : "=r" (_a1)                               \
341                      : "r" (_nr) ASM_ARGS_##nr                  \
342                      : "memory");                               \
343        _a1; })
344 #endif
345
346 #undef INTERNAL_SYSCALL
347 #define INTERNAL_SYSCALL(name, err, nr, args...)                \
348         INTERNAL_SYSCALL_RAW(SYS_ify(name), err, nr, args)
349
350 #undef INTERNAL_SYSCALL_ARM
351 #define INTERNAL_SYSCALL_ARM(name, err, nr, args...)            \
352         INTERNAL_SYSCALL_RAW(__ARM_NR_##name, err, nr, args)
353
354 #undef INTERNAL_SYSCALL_ERROR_P
355 #define INTERNAL_SYSCALL_ERROR_P(val, err) \
356   ((unsigned int) (val) >= 0xfffff001u)
357
358 #undef INTERNAL_SYSCALL_ERRNO
359 #define INTERNAL_SYSCALL_ERRNO(val, err)        (-(val))
360
361 #define LOAD_ARGS_0()
362 #define ASM_ARGS_0
363 #define LOAD_ARGS_1(a1)                         \
364   int _a1tmp = (int) (a1);                      \
365   LOAD_ARGS_0 ()                                \
366   _a1 = _a1tmp;
367 #define ASM_ARGS_1      ASM_ARGS_0, "r" (_a1)
368 #define LOAD_ARGS_2(a1, a2)                     \
369   int _a2tmp = (int) (a2);                      \
370   LOAD_ARGS_1 (a1)                              \
371   register int _a2 asm ("a2") = _a2tmp;
372 #define ASM_ARGS_2      ASM_ARGS_1, "r" (_a2)
373 #define LOAD_ARGS_3(a1, a2, a3)                 \
374   int _a3tmp = (int) (a3);                      \
375   LOAD_ARGS_2 (a1, a2)                          \
376   register int _a3 asm ("a3") = _a3tmp;
377 #define ASM_ARGS_3      ASM_ARGS_2, "r" (_a3)
378 #define LOAD_ARGS_4(a1, a2, a3, a4)             \
379   int _a4tmp = (int) (a4);                      \
380   LOAD_ARGS_3 (a1, a2, a3)                      \
381   register int _a4 asm ("a4") = _a4tmp;
382 #define ASM_ARGS_4      ASM_ARGS_3, "r" (_a4)
383 #define LOAD_ARGS_5(a1, a2, a3, a4, a5)         \
384   int _v1tmp = (int) (a5);                      \
385   LOAD_ARGS_4 (a1, a2, a3, a4)                  \
386   register int _v1 asm ("v1") = _v1tmp;
387 #define ASM_ARGS_5      ASM_ARGS_4, "r" (_v1)
388 #define LOAD_ARGS_6(a1, a2, a3, a4, a5, a6)     \
389   int _v2tmp = (int) (a6);                      \
390   LOAD_ARGS_5 (a1, a2, a3, a4, a5)              \
391   register int _v2 asm ("v2") = _v2tmp;
392 #define ASM_ARGS_6      ASM_ARGS_5, "r" (_v2)
393 #ifndef __thumb__
394 # define LOAD_ARGS_7(a1, a2, a3, a4, a5, a6, a7)        \
395   int _v3tmp = (int) (a7);                              \
396   LOAD_ARGS_6 (a1, a2, a3, a4, a5, a6)                  \
397   register int _v3 asm ("v3") = _v3tmp;
398 # define ASM_ARGS_7     ASM_ARGS_6, "r" (_v3)
399 #endif
400
401 /* For EABI, non-constant syscalls are actually pretty easy...  */
402 #undef INTERNAL_SYSCALL_NCS
403 #define INTERNAL_SYSCALL_NCS(number, err, nr, args...)          \
404   INTERNAL_SYSCALL_RAW (number, err, nr, args)
405
406 #endif  /* __ASSEMBLER__ */
407
408 /* Pointer mangling is not yet supported for ARM.  */
409 #define PTR_MANGLE(var) (void) (var)
410 #define PTR_DEMANGLE(var) (void) (var)
411
412 #endif /* linux/arm/sysdep.h */