1
2/*--------------------------------------------------------------------*/
3/*--- Platform-specific syscalls stuff.      syswrap-arm-linux.c -----*/
4/*--------------------------------------------------------------------*/
5
6/*
7   This file is part of Valgrind, a dynamic binary instrumentation
8   framework.
9
10   Copyright (C) 2000-2013 Nicholas Nethercote
11      njn@valgrind.org
12   Copyright (C) 2008-2013 Evan Geller
13      gaze@bea.ms
14
15   This program is free software; you can redistribute it and/or
16   modify it under the terms of the GNU General Public License as
17   published by the Free Software Foundation; either version 2 of the
18   License, or (at your option) any later version.
19
20   This program is distributed in the hope that it will be useful, but
21   WITHOUT ANY WARRANTY; without even the implied warranty of
22   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
23   General Public License for more details.
24
25   You should have received a copy of the GNU General Public License
26   along with this program; if not, write to the Free Software
27   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
28   02111-1307, USA.
29
30   The GNU General Public License is contained in the file COPYING.
31*/
32
33#if defined(VGP_arm_linux)
34
35#include "pub_core_basics.h"
36#include "pub_core_vki.h"
37#include "pub_core_vkiscnums.h"
38#include "pub_core_threadstate.h"
39#include "pub_core_aspacemgr.h"
40#include "pub_core_debuglog.h"
41#include "pub_core_libcbase.h"
42#include "pub_core_libcassert.h"
43#include "pub_core_libcprint.h"
44#include "pub_core_libcproc.h"
45#include "pub_core_libcsignal.h"
46#include "pub_core_options.h"
47#include "pub_core_scheduler.h"
48#include "pub_core_sigframe.h"      // For VG_(sigframe_destroy)()
49#include "pub_core_signals.h"
50#include "pub_core_syscall.h"
51#include "pub_core_syswrap.h"
52#include "pub_core_tooliface.h"
53#include "pub_core_transtab.h"      // VG_(discard_translations)
54
55#include "priv_types_n_macros.h"
56#include "priv_syswrap-generic.h"   /* for decls of generic wrappers */
57#include "priv_syswrap-linux.h"     /* for decls of linux-ish wrappers */
58#include "priv_syswrap-main.h"
59
60
61/* ---------------------------------------------------------------------
62   clone() handling
63   ------------------------------------------------------------------ */
64
65/* Call f(arg1), but first switch stacks, using 'stack' as the new
66   stack, and use 'retaddr' as f's return-to address.  Also, clear all
67   the integer registers before entering f.*/
68__attribute__((noreturn))
69void ML_(call_on_new_stack_0_1) ( Addr stack,
70                                  Addr retaddr,
71                                  void (*f)(Word),
72                                  Word arg1 );
73//    r0 = stack
74//    r1 = retaddr
75//    r2 = f
76//    r3 = arg1
77asm(
78".text\n"
79".globl vgModuleLocal_call_on_new_stack_0_1\n"
80"vgModuleLocal_call_on_new_stack_0_1:\n"
81"   mov    sp,r0\n\t" /* Stack pointer */
82"   mov    lr,r1\n\t" /* Return address */
83"   mov    r0,r3\n\t" /* First argument */
84"   push   {r2}\n\t"  /* So we can ret to the new dest */
85"   mov    r1, #0\n\t" /* Clear our GPRs */
86"   mov    r2, #0\n\t"
87"   mov    r3, #0\n\t"
88"   mov    r4, #0\n\t"
89"   mov    r5, #0\n\t"
90"   mov    r6, #0\n\t"
91"   mov    r7, #0\n\t"
92"   mov    r8, #0\n\t"
93"   mov    r9, #0\n\t"
94"   mov    r10, #0\n\t"
95"   mov    r11, #0\n\t"
96"   mov    r12, #0\n\t"
97"   pop    {pc}\n\t"  /* Herrre we go! */
98".previous\n"
99);
100
101
102#define __NR_CLONE        VG_STRINGIFY(__NR_clone)
103#define __NR_EXIT         VG_STRINGIFY(__NR_exit)
104
105extern
106ULong do_syscall_clone_arm_linux   ( Word (*fn)(void *),
107                                     void* stack,
108                                     Int   flags,
109                                     void* arg,
110                                     Int*  child_tid,
111                                     Int*  parent_tid,
112                                     void* tls );
113asm(
114".text\n"
115".globl do_syscall_clone_arm_linux\n"
116"do_syscall_clone_arm_linux:\n"
117
118/*Setup child stack */
119"   str     r0, [r1, #-4]!\n"
120"   str     r3, [r1, #-4]!\n"
121"   push {r4,r7}\n"
122"   mov r0, r2\n" /* arg1: flags */
123/* r1 (arg2) is already our child's stack */
124"   ldr r2, [sp, #12]\n" // parent tid
125"   ldr r3, [sp, #16]\n" // tls
126"   ldr r4, [sp, #8]\n" // Child tid
127"   mov r7, #"__NR_CLONE"\n"
128"   svc 0x00000000\n"
129"   cmp r0, #0\n"
130"   beq 1f\n"
131
132/* Parent */
133"   pop {r4,r7}\n"
134"   bx lr\n"
135
136"1:\n" /*child*/
137"   mov     lr, pc\n"
138"   pop     {r0,pc}\n"
139/* Retval from child is already in r0 */
140"   mov r7, #"__NR_EXIT"\n"
141"   svc 0x00000000\n"
142/* Urh.. why did exit return? */
143"   .long 0\n"
144"   .previous\n"
145);
146
147#undef __NR_CLONE
148#undef __NR_EXIT
149
150// forward declarations
151static void setup_child ( ThreadArchState*, ThreadArchState* );
152static void assign_guest_tls(ThreadId ctid, Addr tlsptr);
153static SysRes sys_set_tls ( ThreadId tid, Addr tlsptr );
154
155/*
156   When a client clones, we need to keep track of the new thread.  This means:
157   1. allocate a ThreadId+ThreadState+stack for the the thread
158
159   2. initialize the thread's new VCPU state
160
161   3. create the thread using the same args as the client requested,
162   but using the scheduler entrypoint for IP, and a separate stack
163   for SP.
164 */
165static SysRes do_clone ( ThreadId ptid,
166                         UInt flags, Addr sp,
167                         Int *parent_tidptr,
168                         Int *child_tidptr,
169                         Addr child_tls)
170{
171   ThreadId ctid = VG_(alloc_ThreadState)();
172   ThreadState* ptst = VG_(get_ThreadState)(ptid);
173   ThreadState* ctst = VG_(get_ThreadState)(ctid);
174   UInt r0;
175   UWord *stack;
176   SysRes res;
177   vki_sigset_t blockall, savedmask;
178
179   VG_(sigfillset)(&blockall);
180
181   vg_assert(VG_(is_running_thread)(ptid));
182   vg_assert(VG_(is_valid_tid)(ctid));
183
184   stack = (UWord*)ML_(allocstack)(ctid);
185
186   if(stack == NULL) {
187      res = VG_(mk_SysRes_Error)( VKI_ENOMEM );
188      goto out;
189   }
190
191   setup_child( &ctst->arch, &ptst->arch );
192
193   ctst->arch.vex.guest_R0 = 0;
194   if(sp != 0)
195      ctst->arch.vex.guest_R13 = sp;
196
197   ctst->os_state.parent = ptid;
198
199   ctst->sig_mask = ptst->sig_mask;
200   ctst->tmp_sig_mask = ptst->sig_mask;
201
202   /* Start the child with its threadgroup being the same as the
203      parent's.  This is so that any exit_group calls that happen
204      after the child is created but before it sets its
205      os_state.threadgroup field for real (in thread_wrapper in
206      syswrap-linux.c), really kill the new thread.  a.k.a this avoids
207      a race condition in which the thread is unkillable (via
208      exit_group) because its threadgroup is not set.  The race window
209      is probably only a few hundred or a few thousand cycles long.
210      See #226116. */
211   ctst->os_state.threadgroup = ptst->os_state.threadgroup;
212
213   ML_(guess_and_register_stack) (sp, ctst);
214
215   vg_assert(VG_(owns_BigLock_LL)(ptid));
216   VG_TRACK ( pre_thread_ll_create, ptid, ctid );
217
218   if (flags & VKI_CLONE_SETTLS) {
219      /* Just assign the tls pointer in the guest TPIDRURO. */
220      assign_guest_tls(ctid, child_tls);
221   }
222
223   flags &= ~VKI_CLONE_SETTLS;
224
225   VG_(sigprocmask)(VKI_SIG_SETMASK, &blockall, &savedmask);
226
227   r0 = do_syscall_clone_arm_linux(
228      ML_(start_thread_NORETURN), stack, flags, &VG_(threads)[ctid],
229      child_tidptr, parent_tidptr, NULL
230   );
231   //VG_(printf)("AFTER SYSCALL, %x and %x  CHILD: %d PARENT: %d\n",child_tidptr, parent_tidptr,*child_tidptr,*parent_tidptr);
232
233   res = VG_(mk_SysRes_arm_linux)( r0 );
234
235   VG_(sigprocmask)(VKI_SIG_SETMASK, &savedmask, NULL);
236
237out:
238   if (sr_isError(res)) {
239      VG_(cleanup_thread)(&ctst->arch);
240      ctst->status = VgTs_Empty;
241      VG_TRACK( pre_thread_ll_exit, ctid );
242   }
243
244   return res;
245}
246
247
248
249/* ---------------------------------------------------------------------
250   More thread stuff
251   ------------------------------------------------------------------ */
252
253// ARM doesn't have any architecture specific thread stuff that
254// needs to be cleaned up
255void VG_(cleanup_thread) ( ThreadArchState* arch )
256{
257}
258
259void setup_child ( /*OUT*/ ThreadArchState *child,
260                   /*IN*/  ThreadArchState *parent )
261{
262   child->vex = parent->vex;
263   child->vex_shadow1 = parent->vex_shadow1;
264   child->vex_shadow2 = parent->vex_shadow2;
265}
266
267static void assign_guest_tls(ThreadId tid, Addr tlsptr)
268{
269   VG_(threads)[tid].arch.vex.guest_TPIDRURO = tlsptr;
270}
271
272/* Assigns tlsptr to the guest TPIDRURO.
273   If needed for the specific hardware, really executes
274   the set_tls syscall.
275*/
276static SysRes sys_set_tls ( ThreadId tid, Addr tlsptr )
277{
278   assign_guest_tls(tid, tlsptr);
279
280   if (KernelVariantiS(KernelVariant_android_no_hw_tls,
281                       VG_(clo_kernel_variant))) {
282      /* Android emulator does not provide an hw tls register.
283         So, the tls register is emulated by the kernel.
284         This emulated value is set by the __NR_ARM_set_tls syscall.
285         The emulated value must be read by the kernel helper function
286         located at 0xffff0fe0.
287
288         The emulated tlsptr is located at 0xffff0ff0
289         (so slightly after the kernel helper function).
290         Note that applications are not supposed to read this directly.
291
292         For compatibility : if there is a hw tls register, the kernel
293         will put at 0xffff0fe0 the instructions to read it, so
294         as to have old applications calling the kernel helper
295         working properly.
296
297         For having emulated guest TLS working correctly with
298         Valgrind, it is needed to execute the syscall to set
299         the emulated TLS value in addition to the assignment
300         of TPIDRURO.
301
302         Note: the below means that if we need thread local storage
303         for Valgrind host, then there will be a conflict between
304         the need of the guest tls and of the host tls.
305         If all the guest code would cleanly call 0xffff0fe0,
306         then we might maybe intercept this. However, at least
307         __libc_preinit reads directly 0xffff0ff0.
308      */
309      /* ??? might call the below if auxv->u.a_val & VKI_HWCAP_TLS ???
310         Unclear if real hardware having tls hw register sets
311         VKI_HWCAP_TLS. */
312      return VG_(do_syscall1) (__NR_ARM_set_tls, tlsptr);
313   } else {
314      return VG_(mk_SysRes_Success)( 0 );
315   }
316}
317
318/* ---------------------------------------------------------------------
319   PRE/POST wrappers for arm/Linux-specific syscalls
320   ------------------------------------------------------------------ */
321
322#define PRE(name)       DEFN_PRE_TEMPLATE(arm_linux, name)
323#define POST(name)      DEFN_POST_TEMPLATE(arm_linux, name)
324
325/* Add prototypes for the wrappers declared here, so that gcc doesn't
326   harass us for not having prototypes.  Really this is a kludge --
327   the right thing to do is to make these wrappers 'static' since they
328   aren't visible outside this file, but that requires even more macro
329   magic. */
330
331DECL_TEMPLATE(arm_linux, sys_mmap2);
332DECL_TEMPLATE(arm_linux, sys_stat64);
333DECL_TEMPLATE(arm_linux, sys_lstat64);
334DECL_TEMPLATE(arm_linux, sys_fstatat64);
335DECL_TEMPLATE(arm_linux, sys_fstat64);
336DECL_TEMPLATE(arm_linux, sys_clone);
337DECL_TEMPLATE(arm_linux, sys_sigreturn);
338DECL_TEMPLATE(arm_linux, sys_rt_sigreturn);
339DECL_TEMPLATE(arm_linux, sys_sigsuspend);
340DECL_TEMPLATE(arm_linux, sys_set_tls);
341DECL_TEMPLATE(arm_linux, sys_cacheflush);
342DECL_TEMPLATE(arm_linux, sys_ptrace);
343
344PRE(sys_mmap2)
345{
346   SysRes r;
347
348   // Exactly like old_mmap() except:
349   //  - all 6 args are passed in regs, rather than in a memory-block.
350   //  - the file offset is specified in pagesize units rather than bytes,
351   //    so that it can be used for files bigger than 2^32 bytes.
352   // pagesize or 4K-size units in offset?  For ppc32/64-linux, this is
353   // 4K-sized.  Assert that the page size is 4K here for safety.
354   vg_assert(VKI_PAGE_SIZE == 4096);
355   PRINT("sys_mmap2 ( %#lx, %llu, %ld, %ld, %ld, %ld )",
356         ARG1, (ULong)ARG2, ARG3, ARG4, ARG5, ARG6 );
357   PRE_REG_READ6(long, "mmap2",
358                 unsigned long, start, unsigned long, length,
359                 unsigned long, prot,  unsigned long, flags,
360                 unsigned long, fd,    unsigned long, offset);
361
362   r = ML_(generic_PRE_sys_mmap)( tid, ARG1, ARG2, ARG3, ARG4, ARG5,
363                                       4096 * (Off64T)ARG6 );
364   SET_STATUS_from_SysRes(r);
365}
366
367// XXX: lstat64/fstat64/stat64 are generic, but not necessarily
368// applicable to every architecture -- I think only to 32-bit archs.
369// We're going to need something like linux/core_os32.h for such
370// things, eventually, I think.  --njn
371PRE(sys_lstat64)
372{
373   PRINT("sys_lstat64 ( %#lx(%s), %#lx )",ARG1,(char*)ARG1,ARG2);
374   PRE_REG_READ2(long, "lstat64", char *, file_name, struct stat64 *, buf);
375   PRE_MEM_RASCIIZ( "lstat64(file_name)", ARG1 );
376   PRE_MEM_WRITE( "lstat64(buf)", ARG2, sizeof(struct vki_stat64) );
377}
378
379POST(sys_lstat64)
380{
381   vg_assert(SUCCESS);
382   if (RES == 0) {
383      POST_MEM_WRITE( ARG2, sizeof(struct vki_stat64) );
384   }
385}
386
387PRE(sys_stat64)
388{
389   PRINT("sys_stat64 ( %#lx(%s), %#lx )",ARG1,(char*)ARG1,ARG2);
390   PRE_REG_READ2(long, "stat64", char *, file_name, struct stat64 *, buf);
391   PRE_MEM_RASCIIZ( "stat64(file_name)", ARG1 );
392   PRE_MEM_WRITE( "stat64(buf)", ARG2, sizeof(struct vki_stat64) );
393}
394
395POST(sys_stat64)
396{
397   POST_MEM_WRITE( ARG2, sizeof(struct vki_stat64) );
398}
399
400PRE(sys_fstatat64)
401{
402   PRINT("sys_fstatat64 ( %ld, %#lx(%s), %#lx )",ARG1,ARG2,(char*)ARG2,ARG3);
403   PRE_REG_READ3(long, "fstatat64",
404                 int, dfd, char *, file_name, struct stat64 *, buf);
405   PRE_MEM_RASCIIZ( "fstatat64(file_name)", ARG2 );
406   PRE_MEM_WRITE( "fstatat64(buf)", ARG3, sizeof(struct vki_stat64) );
407}
408
409POST(sys_fstatat64)
410{
411   POST_MEM_WRITE( ARG3, sizeof(struct vki_stat64) );
412}
413
414PRE(sys_fstat64)
415{
416   PRINT("sys_fstat64 ( %ld, %#lx )",ARG1,ARG2);
417   PRE_REG_READ2(long, "fstat64", unsigned long, fd, struct stat64 *, buf);
418   PRE_MEM_WRITE( "fstat64(buf)", ARG2, sizeof(struct vki_stat64) );
419}
420
421POST(sys_fstat64)
422{
423   POST_MEM_WRITE( ARG2, sizeof(struct vki_stat64) );
424}
425
426PRE(sys_clone)
427{
428    UInt cloneflags;
429
430   PRINT("sys_clone ( %lx, %#lx, %#lx, %#lx, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5);
431   PRE_REG_READ5(int, "clone",
432                 unsigned long, flags,
433                 void *, child_stack,
434                 int *, parent_tidptr,
435                 void *, child_tls,
436                 int *, child_tidptr);
437
438   if (ARG1 & VKI_CLONE_PARENT_SETTID) {
439      PRE_MEM_WRITE("clone(parent_tidptr)", ARG3, sizeof(Int));
440      if (!VG_(am_is_valid_for_client)(ARG3, sizeof(Int),
441                                             VKI_PROT_WRITE)) {
442         SET_STATUS_Failure( VKI_EFAULT );
443         return;
444      }
445   }
446   if (ARG1 & (VKI_CLONE_CHILD_SETTID | VKI_CLONE_CHILD_CLEARTID)) {
447      PRE_MEM_WRITE("clone(child_tidptr)", ARG5, sizeof(Int));
448      if (!VG_(am_is_valid_for_client)(ARG5, sizeof(Int),
449                                             VKI_PROT_WRITE)) {
450         SET_STATUS_Failure( VKI_EFAULT );
451         return;
452      }
453   }
454   if (ARG1 & VKI_CLONE_SETTLS) {
455      PRE_MEM_READ("clone(tls_user_desc)", ARG4, sizeof(vki_modify_ldt_t));
456      if (!VG_(am_is_valid_for_client)(ARG4, sizeof(vki_modify_ldt_t),
457                                             VKI_PROT_READ)) {
458         SET_STATUS_Failure( VKI_EFAULT );
459         return;
460      }
461   }
462
463   cloneflags = ARG1;
464
465   if (!ML_(client_signal_OK)(ARG1 & VKI_CSIGNAL)) {
466      SET_STATUS_Failure( VKI_EINVAL );
467      return;
468   }
469
470   /* Only look at the flags we really care about */
471   switch (cloneflags & (VKI_CLONE_VM | VKI_CLONE_FS
472                         | VKI_CLONE_FILES | VKI_CLONE_VFORK)) {
473   case VKI_CLONE_VM | VKI_CLONE_FS | VKI_CLONE_FILES:
474      /* thread creation */
475      SET_STATUS_from_SysRes(
476         do_clone(tid,
477                  ARG1,         /* flags */
478                  (Addr)ARG2,   /* child ESP */
479                  (Int *)ARG3,  /* parent_tidptr */
480                  (Int *)ARG5,  /* child_tidptr */
481                  (Addr)ARG4)); /* set_tls */
482      break;
483
484   case VKI_CLONE_VFORK | VKI_CLONE_VM: /* vfork */
485      /* FALLTHROUGH - assume vfork == fork */
486      cloneflags &= ~(VKI_CLONE_VFORK | VKI_CLONE_VM);
487
488   case 0: /* plain fork */
489      SET_STATUS_from_SysRes(
490         ML_(do_fork_clone)(tid,
491                       cloneflags,      /* flags */
492                       (Int *)ARG3,     /* parent_tidptr */
493                       (Int *)ARG5));   /* child_tidptr */
494      break;
495
496   default:
497      /* should we just ENOSYS? */
498      VG_(message)(Vg_UserMsg, "Unsupported clone() flags: 0x%lx\n", ARG1);
499      VG_(message)(Vg_UserMsg, "\n");
500      VG_(message)(Vg_UserMsg, "The only supported clone() uses are:\n");
501      VG_(message)(Vg_UserMsg, " - via a threads library (LinuxThreads or NPTL)\n");
502      VG_(message)(Vg_UserMsg, " - via the implementation of fork or vfork\n");
503      VG_(message)(Vg_UserMsg, " - for the Quadrics Elan3 user-space driver\n");
504      VG_(unimplemented)
505         ("Valgrind does not support general clone().");
506   }
507
508   if (SUCCESS) {
509      if (ARG1 & VKI_CLONE_PARENT_SETTID)
510         POST_MEM_WRITE(ARG3, sizeof(Int));
511      if (ARG1 & (VKI_CLONE_CHILD_SETTID | VKI_CLONE_CHILD_CLEARTID))
512         POST_MEM_WRITE(ARG5, sizeof(Int));
513
514      /* Thread creation was successful; let the child have the chance
515         to run */
516      *flags |= SfYieldAfter;
517   }
518}
519
520PRE(sys_sigreturn)
521{
522   /* See comments on PRE(sys_rt_sigreturn) in syswrap-amd64-linux.c for
523     an explanation of what follows. */
524
525   PRINT("sys_sigreturn ( )");
526
527   vg_assert(VG_(is_valid_tid)(tid));
528   vg_assert(tid >= 1 && tid < VG_N_THREADS);
529   vg_assert(VG_(is_running_thread)(tid));
530
531   /* Restore register state from frame and remove it */
532   VG_(sigframe_destroy)(tid, False);
533
534   /* Tell the driver not to update the guest state with the "result",
535      and set a bogus result to keep it happy. */
536   *flags |= SfNoWriteResult;
537   SET_STATUS_Success(0);
538
539   /* Check to see if any signals arose as a result of this. */
540   *flags |= SfPollAfter;
541}
542
543PRE(sys_rt_sigreturn)
544{
545  /* See comments on PRE(sys_rt_sigreturn) in syswrap-amd64-linux.c for
546      an explanation of what follows. */
547
548   PRINT("rt_sigreturn ( )");
549
550   vg_assert(VG_(is_valid_tid)(tid));
551   vg_assert(tid >= 1 && tid < VG_N_THREADS);
552   vg_assert(VG_(is_running_thread)(tid));
553
554   /* Restore register state from frame and remove it */
555   VG_(sigframe_destroy)(tid, True);
556
557   /* Tell the driver not to update the guest state with the "result",
558      and set a bogus result to keep it happy. */
559   *flags |= SfNoWriteResult;
560   SET_STATUS_Success(0);
561
562   /* Check to see if any signals arose as a result of this. */
563   *flags |= SfPollAfter;
564}
565
566/* NB: clone of x86-linux version, and ppc32-linux has an almost
567   identical one. */
568PRE(sys_sigsuspend)
569{
570   /* The C library interface to sigsuspend just takes a pointer to
571      a signal mask but this system call has three arguments - the first
572      two don't appear to be used by the kernel and are always passed as
573      zero by glibc and the third is the first word of the signal mask
574      so only 32 signals are supported.
575
576      In fact glibc normally uses rt_sigsuspend if it is available as
577      that takes a pointer to the signal mask so supports more signals.
578    */
579   *flags |= SfMayBlock;
580   PRINT("sys_sigsuspend ( %ld, %ld, %ld )", ARG1,ARG2,ARG3 );
581   PRE_REG_READ3(int, "sigsuspend",
582                 int, history0, int, history1,
583                 vki_old_sigset_t, mask);
584}
585
586/* Very much ARM specific */
587
588PRE(sys_set_tls)
589{
590   PRINT("set_tls (%lx)",ARG1);
591   PRE_REG_READ1(long, "set_tls", unsigned long, addr);
592
593   SET_STATUS_from_SysRes( sys_set_tls( tid, ARG1 ) );
594}
595
596PRE(sys_cacheflush)
597{
598   PRINT("cacheflush (%lx, %#lx, %#lx)",ARG1,ARG2,ARG3);
599   PRE_REG_READ3(long, "cacheflush", void*, addrlow,void*, addrhigh,int, flags);
600   VG_(discard_translations)( (Addr)ARG1,
601                              ((ULong)ARG2) - ((ULong)ARG1) + 1ULL/*paranoia*/,
602                              "PRE(sys_cacheflush)" );
603   SET_STATUS_Success(0);
604}
605
606// ARG3 is only used for pointers into the traced process's address
607// space and for offsets into the traced process's struct
608// user_regs_struct. It is never a pointer into this process's memory
609// space, and we should therefore not check anything it points to.
610PRE(sys_ptrace)
611{
612   PRINT("sys_ptrace ( %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4);
613   PRE_REG_READ4(int, "ptrace",
614                 long, request, long, pid, long, addr, long, data);
615   switch (ARG1) {
616   case VKI_PTRACE_PEEKTEXT:
617   case VKI_PTRACE_PEEKDATA:
618   case VKI_PTRACE_PEEKUSR:
619      PRE_MEM_WRITE( "ptrace(peek)", ARG4,
620		     sizeof (long));
621      break;
622   case VKI_PTRACE_GETREGS:
623      PRE_MEM_WRITE( "ptrace(getregs)", ARG4,
624		     sizeof (struct vki_user_regs_struct));
625      break;
626   case VKI_PTRACE_GETFPREGS:
627      PRE_MEM_WRITE( "ptrace(getfpregs)", ARG4,
628		     sizeof (struct vki_user_fp));
629      break;
630   case VKI_PTRACE_GETWMMXREGS:
631      PRE_MEM_WRITE( "ptrace(getwmmxregs)", ARG4,
632		     VKI_IWMMXT_SIZE);
633      break;
634   case VKI_PTRACE_GETCRUNCHREGS:
635      PRE_MEM_WRITE( "ptrace(getcrunchregs)", ARG4,
636		     VKI_CRUNCH_SIZE);
637      break;
638   case VKI_PTRACE_GETVFPREGS:
639      PRE_MEM_WRITE( "ptrace(getvfpregs)", ARG4,
640                     sizeof (struct vki_user_vfp) );
641      break;
642   case VKI_PTRACE_GETHBPREGS:
643      PRE_MEM_WRITE( "ptrace(gethbpregs)", ARG4,
644                     sizeof (unsigned long) );
645      break;
646   case VKI_PTRACE_SETREGS:
647      PRE_MEM_READ( "ptrace(setregs)", ARG4,
648		     sizeof (struct vki_user_regs_struct));
649      break;
650   case VKI_PTRACE_SETFPREGS:
651      PRE_MEM_READ( "ptrace(setfpregs)", ARG4,
652		     sizeof (struct vki_user_fp));
653      break;
654   case VKI_PTRACE_SETWMMXREGS:
655      PRE_MEM_READ( "ptrace(setwmmxregs)", ARG4,
656		     VKI_IWMMXT_SIZE);
657      break;
658   case VKI_PTRACE_SETCRUNCHREGS:
659      PRE_MEM_READ( "ptrace(setcrunchregs)", ARG4,
660		     VKI_CRUNCH_SIZE);
661      break;
662   case VKI_PTRACE_SETVFPREGS:
663      PRE_MEM_READ( "ptrace(setvfpregs)", ARG4,
664                     sizeof (struct vki_user_vfp));
665      break;
666   case VKI_PTRACE_SETHBPREGS:
667      PRE_MEM_READ( "ptrace(sethbpregs)", ARG4, sizeof(unsigned long));
668      break;
669   case VKI_PTRACE_GET_THREAD_AREA:
670      PRE_MEM_WRITE( "ptrace(get_thread_area)", ARG4, sizeof(unsigned long));
671      break;
672   case VKI_PTRACE_GETEVENTMSG:
673      PRE_MEM_WRITE( "ptrace(geteventmsg)", ARG4, sizeof(unsigned long));
674      break;
675   case VKI_PTRACE_GETSIGINFO:
676      PRE_MEM_WRITE( "ptrace(getsiginfo)", ARG4, sizeof(vki_siginfo_t));
677      break;
678   case VKI_PTRACE_SETSIGINFO:
679      PRE_MEM_READ( "ptrace(setsiginfo)", ARG4, sizeof(vki_siginfo_t));
680      break;
681   case VKI_PTRACE_GETREGSET:
682      ML_(linux_PRE_getregset)(tid, ARG3, ARG4);
683      break;
684   case VKI_PTRACE_SETREGSET:
685      ML_(linux_PRE_setregset)(tid, ARG3, ARG4);
686      break;
687   default:
688      break;
689   }
690}
691
692POST(sys_ptrace)
693{
694   switch (ARG1) {
695   case VKI_PTRACE_PEEKTEXT:
696   case VKI_PTRACE_PEEKDATA:
697   case VKI_PTRACE_PEEKUSR:
698      POST_MEM_WRITE( ARG4, sizeof (long));
699      break;
700   case VKI_PTRACE_GETREGS:
701      POST_MEM_WRITE( ARG4, sizeof (struct vki_user_regs_struct));
702      break;
703   case VKI_PTRACE_GETFPREGS:
704      POST_MEM_WRITE( ARG4, sizeof (struct vki_user_fp));
705      break;
706   case VKI_PTRACE_GETWMMXREGS:
707      POST_MEM_WRITE( ARG4, VKI_IWMMXT_SIZE);
708      break;
709   case VKI_PTRACE_GETCRUNCHREGS:
710      POST_MEM_WRITE( ARG4, VKI_CRUNCH_SIZE);
711      break;
712   case VKI_PTRACE_GETVFPREGS:
713      POST_MEM_WRITE( ARG4, sizeof(struct vki_user_vfp));
714      break;
715   case VKI_PTRACE_GET_THREAD_AREA:
716   case VKI_PTRACE_GETHBPREGS:
717   case VKI_PTRACE_GETEVENTMSG:
718      POST_MEM_WRITE( ARG4, sizeof(unsigned long));
719      break;
720   case VKI_PTRACE_GETSIGINFO:
721      /* XXX: This is a simplification. Different parts of the
722       * siginfo_t are valid depending on the type of signal.
723       */
724      POST_MEM_WRITE( ARG4, sizeof(vki_siginfo_t));
725      break;
726   case VKI_PTRACE_GETREGSET:
727      ML_(linux_POST_getregset)(tid, ARG3, ARG4);
728      break;
729   default:
730      break;
731   }
732}
733
734#undef PRE
735#undef POST
736
737/* ---------------------------------------------------------------------
738   The arm/Linux syscall table
739   ------------------------------------------------------------------ */
740
741#if 0
742#define __NR_OABI_SYSCALL_BASE 0x900000
743#else
744#define __NR_OABI_SYSCALL_BASE 0x0
745#endif
746
747#define PLAX_(sysno, name)    WRAPPER_ENTRY_X_(arm_linux, sysno, name)
748#define PLAXY(sysno, name)    WRAPPER_ENTRY_XY(arm_linux, sysno, name)
749
750// This table maps from __NR_xxx syscall numbers (from
751// linux/include/asm-arm/unistd.h) to the appropriate PRE/POST sys_foo()
752// wrappers on arm (as per sys_call_table in linux/arch/arm/kernel/entry.S).
753//
754// For those syscalls not handled by Valgrind, the annotation indicate its
755// arch/OS combination, eg. */* (generic), */Linux (Linux only), ?/?
756// (unknown).
757
758static SyscallTableEntry syscall_main_table[] = {
759//zz    //   (restart_syscall)                             // 0
760   GENX_(__NR_exit,              sys_exit),           // 1
761   GENX_(__NR_fork,              sys_fork),           // 2
762   GENXY(__NR_read,              sys_read),           // 3
763   GENX_(__NR_write,             sys_write),          // 4
764
765   GENXY(__NR_open,              sys_open),           // 5
766   GENXY(__NR_close,             sys_close),          // 6
767//   GENXY(__NR_waitpid,           sys_waitpid),        // 7
768   GENXY(__NR_creat,             sys_creat),          // 8
769   GENX_(__NR_link,              sys_link),           // 9
770
771   GENX_(__NR_unlink,            sys_unlink),         // 10
772   GENX_(__NR_execve,            sys_execve),         // 11
773   GENX_(__NR_chdir,             sys_chdir),          // 12
774   GENXY(__NR_time,              sys_time),           // 13
775   GENX_(__NR_mknod,             sys_mknod),          // 14
776
777   GENX_(__NR_chmod,             sys_chmod),          // 15
778//zz    LINX_(__NR_lchown,            sys_lchown16),       // 16
779//   GENX_(__NR_break,             sys_ni_syscall),     // 17
780//zz    //   (__NR_oldstat,           sys_stat),           // 18 (obsolete)
781   LINX_(__NR_lseek,             sys_lseek),          // 19
782
783   GENX_(__NR_getpid,            sys_getpid),         // 20
784   LINX_(__NR_mount,             sys_mount),          // 21
785   LINX_(__NR_umount,            sys_oldumount),      // 22
786   LINX_(__NR_setuid,            sys_setuid16),       // 23 ## P
787   LINX_(__NR_getuid,            sys_getuid16),       // 24 ## P
788//zz
789//zz    //   (__NR_stime,             sys_stime),          // 25 * (SVr4,SVID,X/OPEN)
790   PLAXY(__NR_ptrace,            sys_ptrace),         // 26
791   GENX_(__NR_alarm,             sys_alarm),          // 27
792//zz    //   (__NR_oldfstat,          sys_fstat),          // 28 * L -- obsolete
793   GENX_(__NR_pause,             sys_pause),          // 29
794
795   LINX_(__NR_utime,             sys_utime),          // 30
796//   GENX_(__NR_stty,              sys_ni_syscall),     // 31
797//   GENX_(__NR_gtty,              sys_ni_syscall),     // 32
798   GENX_(__NR_access,            sys_access),         // 33
799   GENX_(__NR_nice,              sys_nice),           // 34
800
801//   GENX_(__NR_ftime,             sys_ni_syscall),     // 35
802   GENX_(__NR_sync,              sys_sync),           // 36
803   GENX_(__NR_kill,              sys_kill),           // 37
804   GENX_(__NR_rename,            sys_rename),         // 38
805   GENX_(__NR_mkdir,             sys_mkdir),          // 39
806
807   GENX_(__NR_rmdir,             sys_rmdir),          // 40
808   GENXY(__NR_dup,               sys_dup),            // 41
809   LINXY(__NR_pipe,              sys_pipe),           // 42
810   GENXY(__NR_times,             sys_times),          // 43
811//   GENX_(__NR_prof,              sys_ni_syscall),     // 44
812//zz
813   GENX_(__NR_brk,               sys_brk),            // 45
814   LINX_(__NR_setgid,            sys_setgid16),       // 46
815   LINX_(__NR_getgid,            sys_getgid16),       // 47
816//zz    //   (__NR_signal,            sys_signal),         // 48 */* (ANSI C)
817   LINX_(__NR_geteuid,           sys_geteuid16),      // 49
818
819   LINX_(__NR_getegid,           sys_getegid16),      // 50
820   GENX_(__NR_acct,              sys_acct),           // 51
821   LINX_(__NR_umount2,           sys_umount),         // 52
822//   GENX_(__NR_lock,              sys_ni_syscall),     // 53
823   LINXY(__NR_ioctl,             sys_ioctl),          // 54
824
825   LINXY(__NR_fcntl,             sys_fcntl),          // 55
826//   GENX_(__NR_mpx,               sys_ni_syscall),     // 56
827   GENX_(__NR_setpgid,           sys_setpgid),        // 57
828//   GENX_(__NR_ulimit,            sys_ni_syscall),     // 58
829//zz    //   (__NR_oldolduname,       sys_olduname),       // 59 Linux -- obsolete
830//zz
831   GENX_(__NR_umask,             sys_umask),          // 60
832   GENX_(__NR_chroot,            sys_chroot),         // 61
833//zz    //   (__NR_ustat,             sys_ustat)           // 62 SVr4 -- deprecated
834   GENXY(__NR_dup2,              sys_dup2),           // 63
835   GENX_(__NR_getppid,           sys_getppid),        // 64
836
837   GENX_(__NR_getpgrp,           sys_getpgrp),        // 65
838   GENX_(__NR_setsid,            sys_setsid),         // 66
839   LINXY(__NR_sigaction,         sys_sigaction),      // 67
840//zz    //   (__NR_sgetmask,          sys_sgetmask),       // 68 */* (ANSI C)
841//zz    //   (__NR_ssetmask,          sys_ssetmask),       // 69 */* (ANSI C)
842//zz
843   LINX_(__NR_setreuid,          sys_setreuid16),     // 70
844   LINX_(__NR_setregid,          sys_setregid16),     // 71
845   PLAX_(__NR_sigsuspend,        sys_sigsuspend),     // 72
846   LINXY(__NR_sigpending,        sys_sigpending),     // 73
847//zz    //   (__NR_sethostname,       sys_sethostname),    // 74 */*
848//zz
849   GENX_(__NR_setrlimit,         sys_setrlimit),      // 75
850   GENXY(__NR_getrlimit,         sys_old_getrlimit),  // 76
851   GENXY(__NR_getrusage,         sys_getrusage),      // 77
852   GENXY(__NR_gettimeofday,      sys_gettimeofday),   // 78
853   GENX_(__NR_settimeofday,      sys_settimeofday),   // 79
854
855   LINXY(__NR_getgroups,         sys_getgroups16),    // 80
856   LINX_(__NR_setgroups,         sys_setgroups16),    // 81
857//   PLAX_(__NR_select,            old_select),         // 82
858   GENX_(__NR_symlink,           sys_symlink),        // 83
859//zz    //   (__NR_oldlstat,          sys_lstat),          // 84 -- obsolete
860//zz
861   GENX_(__NR_readlink,          sys_readlink),       // 85
862//zz    //   (__NR_uselib,            sys_uselib),         // 86 */Linux
863//zz    //   (__NR_swapon,            sys_swapon),         // 87 */Linux
864//zz    //   (__NR_reboot,            sys_reboot),         // 88 */Linux
865//zz    //   (__NR_readdir,           old_readdir),        // 89 -- superseded
866//zz
867//   _____(__NR_mmap,              old_mmap),           // 90
868   GENXY(__NR_munmap,            sys_munmap),         // 91
869   GENX_(__NR_truncate,          sys_truncate),       // 92
870   GENX_(__NR_ftruncate,         sys_ftruncate),      // 93
871   GENX_(__NR_fchmod,            sys_fchmod),         // 94
872
873   LINX_(__NR_fchown,            sys_fchown16),       // 95
874   GENX_(__NR_getpriority,       sys_getpriority),    // 96
875   GENX_(__NR_setpriority,       sys_setpriority),    // 97
876//   GENX_(__NR_profil,            sys_ni_syscall),     // 98
877   GENXY(__NR_statfs,            sys_statfs),         // 99
878
879   GENXY(__NR_fstatfs,           sys_fstatfs),        // 100
880//   LINX_(__NR_ioperm,            sys_ioperm),         // 101
881   LINXY(__NR_socketcall,        sys_socketcall),     // 102
882   LINXY(__NR_syslog,            sys_syslog),         // 103
883   GENXY(__NR_setitimer,         sys_setitimer),      // 104
884
885   GENXY(__NR_getitimer,         sys_getitimer),      // 105
886   GENXY(__NR_stat,              sys_newstat),        // 106
887   GENXY(__NR_lstat,             sys_newlstat),       // 107
888   GENXY(__NR_fstat,             sys_newfstat),       // 108
889//zz    //   (__NR_olduname,          sys_uname),          // 109 -- obsolete
890//zz
891//   GENX_(__NR_iopl,              sys_iopl),           // 110
892   LINX_(__NR_vhangup,           sys_vhangup),        // 111
893//   GENX_(__NR_idle,              sys_ni_syscall),     // 112
894// PLAXY(__NR_vm86old,           sys_vm86old),        // 113 __NR_syscall... weird
895   GENXY(__NR_wait4,             sys_wait4),          // 114
896//zz
897//zz    //   (__NR_swapoff,           sys_swapoff),        // 115 */Linux
898   LINXY(__NR_sysinfo,           sys_sysinfo),        // 116
899//   _____(__NR_ipc,               sys_ipc),            // 117
900   GENX_(__NR_fsync,             sys_fsync),          // 118
901   PLAX_(__NR_sigreturn,         sys_sigreturn),      // 119 ?/Linux
902
903   PLAX_(__NR_clone,             sys_clone),          // 120
904//zz    //   (__NR_setdomainname,     sys_setdomainname),  // 121 */*(?)
905   GENXY(__NR_uname,             sys_newuname),       // 122
906//   PLAX_(__NR_modify_ldt,        sys_modify_ldt),     // 123
907//zz    LINXY(__NR_adjtimex,          sys_adjtimex),       // 124
908//zz
909   GENXY(__NR_mprotect,          sys_mprotect),       // 125
910   LINXY(__NR_sigprocmask,       sys_sigprocmask),    // 126
911//zz    // Nb: create_module() was removed 2.4-->2.6
912//   GENX_(__NR_create_module,     sys_ni_syscall),     // 127
913   LINX_(__NR_init_module,       sys_init_module),    // 128
914   LINX_(__NR_delete_module,     sys_delete_module),  // 129
915//zz
916//zz    // Nb: get_kernel_syms() was removed 2.4-->2.6
917//   GENX_(__NR_get_kernel_syms,   sys_ni_syscall),     // 130
918   LINX_(__NR_quotactl,          sys_quotactl),       // 131
919   GENX_(__NR_getpgid,           sys_getpgid),        // 132
920   GENX_(__NR_fchdir,            sys_fchdir),         // 133
921//zz    //   (__NR_bdflush,           sys_bdflush),        // 134 */Linux
922//zz
923//zz    //   (__NR_sysfs,             sys_sysfs),          // 135 SVr4
924   LINX_(__NR_personality,       sys_personality),    // 136
925//   GENX_(__NR_afs_syscall,       sys_ni_syscall),     // 137
926   LINX_(__NR_setfsuid,          sys_setfsuid16),     // 138
927   LINX_(__NR_setfsgid,          sys_setfsgid16),     // 139
928
929   LINXY(__NR__llseek,           sys_llseek),         // 140
930   GENXY(__NR_getdents,          sys_getdents),       // 141
931   GENX_(__NR__newselect,        sys_select),         // 142
932   GENX_(__NR_flock,             sys_flock),          // 143
933   GENX_(__NR_msync,             sys_msync),          // 144
934
935   GENXY(__NR_readv,             sys_readv),          // 145
936   GENX_(__NR_writev,            sys_writev),         // 146
937   GENX_(__NR_getsid,            sys_getsid),         // 147
938   GENX_(__NR_fdatasync,         sys_fdatasync),      // 148
939   LINXY(__NR__sysctl,           sys_sysctl),         // 149
940
941   GENX_(__NR_mlock,             sys_mlock),          // 150
942   GENX_(__NR_munlock,           sys_munlock),        // 151
943   GENX_(__NR_mlockall,          sys_mlockall),       // 152
944   LINX_(__NR_munlockall,        sys_munlockall),     // 153
945   LINXY(__NR_sched_setparam,    sys_sched_setparam), // 154
946
947   LINXY(__NR_sched_getparam,         sys_sched_getparam),        // 155
948   LINX_(__NR_sched_setscheduler,     sys_sched_setscheduler),    // 156
949   LINX_(__NR_sched_getscheduler,     sys_sched_getscheduler),    // 157
950   LINX_(__NR_sched_yield,            sys_sched_yield),           // 158
951   LINX_(__NR_sched_get_priority_max, sys_sched_get_priority_max),// 159
952
953   LINX_(__NR_sched_get_priority_min, sys_sched_get_priority_min),// 160
954//zz    //LINX?(__NR_sched_rr_get_interval,  sys_sched_rr_get_interval), // 161 */*
955   GENXY(__NR_nanosleep,         sys_nanosleep),      // 162
956   GENX_(__NR_mremap,            sys_mremap),         // 163
957   LINX_(__NR_setresuid,         sys_setresuid16),    // 164
958
959   LINXY(__NR_getresuid,         sys_getresuid16),    // 165
960//   PLAXY(__NR_vm86,              sys_vm86),           // 166 x86/Linux-only
961//   GENX_(__NR_query_module,      sys_ni_syscall),     // 167
962   GENXY(__NR_poll,              sys_poll),           // 168
963//zz    //   (__NR_nfsservctl,        sys_nfsservctl),     // 169 */Linux
964//zz
965   LINX_(__NR_setresgid,         sys_setresgid16),    // 170
966   LINXY(__NR_getresgid,         sys_getresgid16),    // 171
967   LINXY(__NR_prctl,             sys_prctl),          // 172
968   PLAX_(__NR_rt_sigreturn,      sys_rt_sigreturn),   // 173
969   LINXY(__NR_rt_sigaction,      sys_rt_sigaction),   // 174
970
971   LINXY(__NR_rt_sigprocmask,    sys_rt_sigprocmask), // 175
972   LINXY(__NR_rt_sigpending,     sys_rt_sigpending),  // 176
973   LINXY(__NR_rt_sigtimedwait,   sys_rt_sigtimedwait),// 177
974   LINXY(__NR_rt_sigqueueinfo,   sys_rt_sigqueueinfo),// 178
975   LINX_(__NR_rt_sigsuspend,     sys_rt_sigsuspend),  // 179
976
977   GENXY(__NR_pread64,           sys_pread64),        // 180
978   GENX_(__NR_pwrite64,          sys_pwrite64),       // 181
979   LINX_(__NR_chown,             sys_chown16),        // 182
980   GENXY(__NR_getcwd,            sys_getcwd),         // 183
981   LINXY(__NR_capget,            sys_capget),         // 184
982
983   LINX_(__NR_capset,            sys_capset),         // 185
984   GENXY(__NR_sigaltstack,       sys_sigaltstack),    // 186
985   LINXY(__NR_sendfile,          sys_sendfile),       // 187
986//   GENXY(__NR_getpmsg,           sys_getpmsg),        // 188
987//   GENX_(__NR_putpmsg,           sys_putpmsg),        // 189
988
989   // Nb: we treat vfork as fork
990   GENX_(__NR_vfork,             sys_fork),           // 190
991   GENXY(__NR_ugetrlimit,        sys_getrlimit),      // 191
992   PLAX_(__NR_mmap2,             sys_mmap2),          // 192
993   GENX_(__NR_truncate64,        sys_truncate64),     // 193
994   GENX_(__NR_ftruncate64,       sys_ftruncate64),    // 194
995
996   PLAXY(__NR_stat64,            sys_stat64),         // 195
997   PLAXY(__NR_lstat64,           sys_lstat64),        // 196
998   PLAXY(__NR_fstat64,           sys_fstat64),        // 197
999   GENX_(__NR_lchown32,          sys_lchown),         // 198
1000   GENX_(__NR_getuid32,          sys_getuid),         // 199
1001
1002   GENX_(__NR_getgid32,          sys_getgid),         // 200
1003   GENX_(__NR_geteuid32,         sys_geteuid),        // 201
1004   GENX_(__NR_getegid32,         sys_getegid),        // 202
1005   GENX_(__NR_setreuid32,        sys_setreuid),       // 203
1006   GENX_(__NR_setregid32,        sys_setregid),       // 204
1007
1008   GENXY(__NR_getgroups32,       sys_getgroups),      // 205
1009   GENX_(__NR_setgroups32,       sys_setgroups),      // 206
1010   GENX_(__NR_fchown32,          sys_fchown),         // 207
1011   LINX_(__NR_setresuid32,       sys_setresuid),      // 208
1012   LINXY(__NR_getresuid32,       sys_getresuid),      // 209
1013
1014   LINX_(__NR_setresgid32,       sys_setresgid),      // 210
1015   LINXY(__NR_getresgid32,       sys_getresgid),      // 211
1016   GENX_(__NR_chown32,           sys_chown),          // 212
1017   GENX_(__NR_setuid32,          sys_setuid),         // 213
1018   GENX_(__NR_setgid32,          sys_setgid),         // 214
1019
1020   LINX_(__NR_setfsuid32,        sys_setfsuid),       // 215
1021   LINX_(__NR_setfsgid32,        sys_setfsgid),       // 216
1022   LINX_(__NR_pivot_root,        sys_pivot_root),     // 217
1023   GENXY(__NR_mincore,           sys_mincore),        // 218
1024   GENX_(__NR_madvise,           sys_madvise),        // 219
1025
1026   GENXY(__NR_getdents64,        sys_getdents64),     // 220
1027   LINXY(__NR_fcntl64,           sys_fcntl64),        // 221
1028//   GENX_(222,                    sys_ni_syscall),     // 222
1029//   PLAXY(223,                    sys_syscall223),     // 223 // sys_bproc?
1030   LINX_(__NR_gettid,            sys_gettid),         // 224
1031
1032   LINX_(__NR_readahead,         sys_readahead),      // 225 */Linux
1033   LINX_(__NR_setxattr,          sys_setxattr),       // 226
1034   LINX_(__NR_lsetxattr,         sys_lsetxattr),      // 227
1035   LINX_(__NR_fsetxattr,         sys_fsetxattr),      // 228
1036   LINXY(__NR_getxattr,          sys_getxattr),       // 229
1037
1038   LINXY(__NR_lgetxattr,         sys_lgetxattr),      // 230
1039   LINXY(__NR_fgetxattr,         sys_fgetxattr),      // 231
1040   LINXY(__NR_listxattr,         sys_listxattr),      // 232
1041   LINXY(__NR_llistxattr,        sys_llistxattr),     // 233
1042   LINXY(__NR_flistxattr,        sys_flistxattr),     // 234
1043
1044   LINX_(__NR_removexattr,       sys_removexattr),    // 235
1045   LINX_(__NR_lremovexattr,      sys_lremovexattr),   // 236
1046   LINX_(__NR_fremovexattr,      sys_fremovexattr),   // 237
1047   LINXY(__NR_tkill,             sys_tkill),          // 238 */Linux
1048   LINXY(__NR_sendfile64,        sys_sendfile64),     // 239
1049
1050   LINXY(__NR_futex,             sys_futex),             // 240
1051   LINX_(__NR_sched_setaffinity, sys_sched_setaffinity), // 241
1052   LINXY(__NR_sched_getaffinity, sys_sched_getaffinity), // 242
1053//   PLAX_(__NR_set_thread_area,   sys_set_thread_area),   // 243
1054//   PLAX_(__NR_get_thread_area,   sys_get_thread_area),   // 244
1055
1056   LINXY(__NR_io_setup,          sys_io_setup),       // 245
1057   LINX_(__NR_io_destroy,        sys_io_destroy),     // 246
1058   LINXY(__NR_io_getevents,      sys_io_getevents),   // 247
1059   LINX_(__NR_io_submit,         sys_io_submit),      // 248
1060   LINXY(__NR_io_cancel,         sys_io_cancel),      // 249
1061
1062//   LINX_(__NR_fadvise64,         sys_fadvise64),      // 250 */(Linux?)
1063   GENX_(251,                    sys_ni_syscall),     // 251
1064   LINX_(__NR_exit_group,        sys_exit_group),     // 252
1065//   GENXY(__NR_lookup_dcookie,    sys_lookup_dcookie), // 253
1066   LINXY(__NR_epoll_create,      sys_epoll_create),   // 254
1067
1068   LINX_(__NR_epoll_ctl,         sys_epoll_ctl),         // 255
1069   LINXY(__NR_epoll_wait,        sys_epoll_wait),        // 256
1070//zz    //   (__NR_remap_file_pages,  sys_remap_file_pages),  // 257 */Linux
1071   LINX_(__NR_set_tid_address,   sys_set_tid_address),   // 258
1072   LINXY(__NR_timer_create,      sys_timer_create),      // 259
1073
1074   LINXY(__NR_timer_settime,     sys_timer_settime),  // (timer_create+1)
1075   LINXY(__NR_timer_gettime,     sys_timer_gettime),  // (timer_create+2)
1076   LINX_(__NR_timer_getoverrun,  sys_timer_getoverrun),//(timer_create+3)
1077   LINX_(__NR_timer_delete,      sys_timer_delete),   // (timer_create+4)
1078   LINX_(__NR_clock_settime,     sys_clock_settime),  // (timer_create+5)
1079
1080   LINXY(__NR_clock_gettime,     sys_clock_gettime),  // (timer_create+6)
1081   LINXY(__NR_clock_getres,      sys_clock_getres),   // (timer_create+7)
1082   LINXY(__NR_clock_nanosleep,   sys_clock_nanosleep),// (timer_create+8) */*
1083   GENXY(__NR_statfs64,          sys_statfs64),       // 268
1084   GENXY(__NR_fstatfs64,         sys_fstatfs64),      // 269
1085
1086   LINX_(__NR_tgkill,            sys_tgkill),         // 270 */Linux
1087   GENX_(__NR_utimes,            sys_utimes),         // 271
1088   GENX_(__NR_vserver,           sys_ni_syscall),     // 273
1089   LINX_(__NR_mbind,             sys_mbind),          // 274 ?/?
1090
1091   LINXY(__NR_get_mempolicy,     sys_get_mempolicy),  // 275 ?/?
1092   LINX_(__NR_set_mempolicy,     sys_set_mempolicy),  // 276 ?/?
1093   LINXY(__NR_mq_open,           sys_mq_open),        // 277
1094   LINX_(__NR_mq_unlink,         sys_mq_unlink),      // (mq_open+1)
1095   LINX_(__NR_mq_timedsend,      sys_mq_timedsend),   // (mq_open+2)
1096
1097   LINXY(__NR_mq_timedreceive,   sys_mq_timedreceive),// (mq_open+3)
1098   LINX_(__NR_mq_notify,         sys_mq_notify),      // (mq_open+4)
1099   LINXY(__NR_mq_getsetattr,     sys_mq_getsetattr),  // (mq_open+5)
1100   LINXY(__NR_waitid,            sys_waitid),         // 280
1101
1102   LINXY(__NR_socket,            sys_socket),         // 281
1103   LINX_(__NR_bind,              sys_bind),           // 282
1104   LINX_(__NR_connect,           sys_connect),        // 283
1105   LINX_(__NR_listen,            sys_listen),         // 284
1106   LINXY(__NR_accept,            sys_accept),         // 285
1107   LINXY(__NR_getsockname,       sys_getsockname),    // 286
1108   LINXY(__NR_getpeername,       sys_getpeername),    // 287
1109   LINXY(__NR_socketpair,        sys_socketpair),     // 288
1110   LINX_(__NR_send,              sys_send),
1111   LINX_(__NR_sendto,            sys_sendto),         // 290
1112   LINXY(__NR_recv,              sys_recv),
1113   LINXY(__NR_recvfrom,          sys_recvfrom),       // 292
1114   LINX_(__NR_shutdown,          sys_shutdown),       // 293
1115   LINX_(__NR_setsockopt,        sys_setsockopt),     // 294
1116   LINXY(__NR_getsockopt,        sys_getsockopt),     // 295
1117   LINX_(__NR_sendmsg,           sys_sendmsg),        // 296
1118   LINXY(__NR_recvmsg,           sys_recvmsg),        // 297
1119   LINX_(__NR_semop,             sys_semop),          // 298
1120   LINX_(__NR_semget,            sys_semget),         // 299
1121   LINXY(__NR_semctl,            sys_semctl),         // 300
1122   LINX_(__NR_msgget,            sys_msgget),
1123   LINX_(__NR_msgsnd,            sys_msgsnd),
1124   LINXY(__NR_msgrcv,            sys_msgrcv),
1125   LINXY(__NR_msgctl,            sys_msgctl),         // 304
1126   LINX_(__NR_semtimedop,        sys_semtimedop),     // 312
1127
1128   LINX_(__NR_add_key,           sys_add_key),        // 286
1129   LINX_(__NR_request_key,       sys_request_key),    // 287
1130   LINXY(__NR_keyctl,            sys_keyctl),         // not 288...
1131//   LINX_(__NR_ioprio_set,        sys_ioprio_set),     // 289
1132
1133//   LINX_(__NR_ioprio_get,        sys_ioprio_get),     // 290
1134   LINX_(__NR_inotify_init,    sys_inotify_init),   // 291
1135   LINX_(__NR_inotify_add_watch, sys_inotify_add_watch), // 292
1136   LINX_(__NR_inotify_rm_watch,    sys_inotify_rm_watch), // 293
1137//   LINX_(__NR_migrate_pages,    sys_migrate_pages),    // 294
1138
1139   LINXY(__NR_openat,       sys_openat),           // 295
1140   LINX_(__NR_mkdirat,       sys_mkdirat),          // 296
1141   LINX_(__NR_mknodat,       sys_mknodat),          // 297
1142   LINX_(__NR_fchownat,       sys_fchownat),         // 298
1143   LINX_(__NR_futimesat,    sys_futimesat),        // 326 on arm
1144
1145   PLAXY(__NR_fstatat64,    sys_fstatat64),        // 300
1146   LINX_(__NR_unlinkat,       sys_unlinkat),         // 301
1147   LINX_(__NR_renameat,       sys_renameat),         // 302
1148   LINX_(__NR_linkat,       sys_linkat),           // 303
1149   LINX_(__NR_symlinkat,    sys_symlinkat),        // 304
1150
1151   LINX_(__NR_readlinkat,    sys_readlinkat),       //
1152   LINX_(__NR_fchmodat,       sys_fchmodat),         //
1153   LINX_(__NR_faccessat,    sys_faccessat),        //
1154   LINXY(__NR_shmat,         wrap_sys_shmat),       //305
1155   LINXY(__NR_shmdt,             sys_shmdt),          //306
1156   LINX_(__NR_shmget,            sys_shmget),         //307
1157   LINXY(__NR_shmctl,            sys_shmctl),         // 308
1158//   LINX_(__NR_pselect6,       sys_pselect6),         //
1159
1160   LINX_(__NR_unshare,       sys_unshare),          // 310
1161   LINX_(__NR_set_robust_list,    sys_set_robust_list),  // 311
1162   LINXY(__NR_get_robust_list,    sys_get_robust_list),  // 312
1163//   LINX_(__NR_splice,            sys_ni_syscall),       // 313
1164//   LINX_(__NR_sync_file_range,   sys_sync_file_range),  // 314
1165
1166//   LINX_(__NR_tee,               sys_ni_syscall),       // 315
1167//   LINX_(__NR_vmsplice,          sys_ni_syscall),       // 316
1168   LINXY(__NR_move_pages,        sys_move_pages),       // 317
1169//   LINX_(__NR_getcpu,            sys_ni_syscall),       // 318
1170
1171   LINX_(__NR_utimensat,         sys_utimensat),        // 320
1172   LINXY(__NR_signalfd,          sys_signalfd),         // 321
1173   LINXY(__NR_timerfd_create,    sys_timerfd_create),   // 322
1174   LINXY(__NR_eventfd,           sys_eventfd),          // 323
1175
1176   LINXY(__NR_timerfd_settime,   sys_timerfd_settime),  // 325
1177   LINXY(__NR_timerfd_gettime,   sys_timerfd_gettime),   // 326
1178
1179   ///////////////
1180
1181   // JRS 2010-Jan-03: I believe that all the numbers listed
1182   // in comments in the table prior to this point (eg "// 326",
1183   // etc) are bogus since it looks to me like they are copied
1184   // verbatim from syswrap-x86-linux.c and they certainly do not
1185   // correspond to what's in include/vki/vki-scnums-arm-linux.h.
1186   // From here onwards, please ensure the numbers are correct.
1187
1188   LINX_(__NR_arm_fadvise64_64,  sys_fadvise64_64),     // 270 */(Linux?)
1189
1190   LINX_(__NR_pselect6,          sys_pselect6),         // 335
1191   LINXY(__NR_ppoll,             sys_ppoll),            // 336
1192
1193   LINXY(__NR_epoll_pwait,       sys_epoll_pwait),      // 346
1194
1195   LINX_(__NR_fallocate,         sys_fallocate),        // 352
1196
1197   LINXY(__NR_signalfd4,         sys_signalfd4),        // 355
1198   LINXY(__NR_eventfd2,          sys_eventfd2),         // 356
1199   LINXY(__NR_epoll_create1,     sys_epoll_create1),    // 357
1200   LINXY(__NR_dup3,              sys_dup3),             // 358
1201   LINXY(__NR_pipe2,             sys_pipe2),            // 359
1202   LINXY(__NR_inotify_init1,     sys_inotify_init1),    // 360
1203   LINXY(__NR_preadv,            sys_preadv),           // 361
1204   LINX_(__NR_pwritev,           sys_pwritev),          // 362
1205   LINXY(__NR_rt_tgsigqueueinfo, sys_rt_tgsigqueueinfo),// 363
1206   LINXY(__NR_perf_event_open,   sys_perf_event_open),  // 364
1207   LINXY(__NR_recvmmsg,          sys_recvmmsg),         // 365
1208   LINXY(__NR_accept4,           sys_accept4),          // 366
1209   LINXY(__NR_fanotify_init,     sys_fanotify_init),    // 367
1210   LINX_(__NR_fanotify_mark,     sys_fanotify_mark),    // 368
1211   LINXY(__NR_prlimit64,         sys_prlimit64),        // 369
1212   LINXY(__NR_name_to_handle_at, sys_name_to_handle_at),// 370
1213   LINXY(__NR_open_by_handle_at, sys_open_by_handle_at),// 371
1214   LINXY(__NR_clock_adjtime,     sys_clock_adjtime),    // 372
1215   LINX_(__NR_syncfs,            sys_syncfs),           // 373
1216   LINXY(__NR_sendmmsg,          sys_sendmmsg),         // 374
1217   LINXY(__NR_getrandom,         sys_getrandom),        // 384
1218   LINXY(__NR_memfd_create,      sys_memfd_create)      // 385
1219};
1220
1221
1222/* These are not in the main table because there indexes are not small
1223   integers, but rather values close to one million.  So their
1224   inclusion would force the main table to be huge (about 8 MB). */
1225
1226static SyscallTableEntry ste___ARM_set_tls
1227   = { WRAPPER_PRE_NAME(arm_linux,sys_set_tls), NULL };
1228
1229static SyscallTableEntry ste___ARM_cacheflush
1230   = { WRAPPER_PRE_NAME(arm_linux,sys_cacheflush), NULL };
1231
1232SyscallTableEntry* ML_(get_linux_syscall_entry) ( UInt sysno )
1233{
1234   const UInt syscall_main_table_size
1235      = sizeof(syscall_main_table) / sizeof(syscall_main_table[0]);
1236
1237   /* Is it in the contiguous initial section of the table? */
1238   if (sysno < syscall_main_table_size) {
1239      SyscallTableEntry* sys = &syscall_main_table[sysno];
1240      if (sys->before == NULL)
1241         return NULL; /* no entry */
1242      else
1243         return sys;
1244   }
1245
1246   /* Check if it's one of the out-of-line entries. */
1247   switch (sysno) {
1248      case __NR_ARM_set_tls:    return &ste___ARM_set_tls;
1249      case __NR_ARM_cacheflush: return &ste___ARM_cacheflush;
1250      default: break;
1251   }
1252
1253   /* Can't find a wrapper */
1254   return NULL;
1255}
1256
1257#endif // defined(VGP_arm_linux)
1258
1259/*--------------------------------------------------------------------*/
1260/*--- end                                      syswrap-arm-linux.c ---*/
1261/*--------------------------------------------------------------------*/
1262