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