Home | History | Annotate | Download | only in m_syswrap
      1 
      2 /*--------------------------------------------------------------------*/
      3 /*--- Platform-specific syscalls stuff.    syswrap-tilegx-linux.c ----*/
      4 /*--------------------------------------------------------------------*/
      5 
      6 /*
      7   This file is part of Valgrind, a dynamic binary instrumentation
      8   framework.
      9 
     10   Copyright (C) 2010-2013 Tilera Corp.
     11 
     12   This program is free software; you can redistribute it and/or
     13   modify it under the terms of the GNU General Public License as
     14   published by the Free Software Foundation; either version 2 of the
     15   License, or (at your option) any later version.
     16 
     17   This program is distributed in the hope that it will be useful, but
     18   WITHOUT ANY WARRANTY; without even the implied warranty of
     19   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     20   General Public License for more details.
     21 
     22   You should have received a copy of the GNU General Public License
     23   along with this program; if not, write to the Free Software
     24   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
     25   02111-1307, USA.
     26 
     27   The GNU General Public License is contained in the file COPYING.
     28 */
     29 
     30 /* Contributed by Zhi-Gang Liu */
     31 
     32 #if defined(VGP_tilegx_linux)
     33 #include "pub_core_basics.h"
     34 #include "pub_core_vki.h"
     35 #include "pub_core_vkiscnums.h"
     36 #include "pub_core_threadstate.h"
     37 #include "pub_core_aspacemgr.h"
     38 #include "pub_core_debuglog.h"
     39 #include "pub_core_libcbase.h"
     40 #include "pub_core_libcassert.h"
     41 #include "pub_core_libcprint.h"
     42 #include "pub_core_libcproc.h"
     43 #include "pub_core_libcsignal.h"
     44 #include "pub_core_options.h"
     45 #include "pub_core_scheduler.h"
     46 #include "pub_core_sigframe.h"     // For VG_(sigframe_destroy)()
     47 #include "pub_core_signals.h"
     48 #include "pub_core_syscall.h"
     49 #include "pub_core_syswrap.h"
     50 #include "pub_core_tooliface.h"
     51 #include "pub_core_stacks.h"        // VG_(register_stack)
     52 #include "pub_core_transtab.h"      // VG_(discard_translations)
     53 #include "priv_types_n_macros.h"
     54 #include "priv_syswrap-generic.h"   /* for decls of generic wrappers */
     55 #include "priv_syswrap-linux.h"     /* for decls of linux wrappers */
     56 #include "priv_syswrap-main.h"
     57 
     58 #include "pub_core_debuginfo.h"     // VG_(di_notify_*)
     59 #include "pub_core_xarray.h"
     60 #include "pub_core_clientstate.h"   // VG_(brk_base), VG_(brk_limit)
     61 #include "pub_core_errormgr.h"
     62 #include "pub_core_libcfile.h"
     63 #include "pub_core_machine.h"       // VG_(get_SP)
     64 #include "pub_core_mallocfree.h"
     65 #include "pub_core_stacktrace.h"    // For VG_(get_and_pp_StackTrace)()
     66 #include "pub_core_ume.h"
     67 
     68 #include "config.h"
     69 
     70 /* ---------------------------------------------------------------------
     71    clone() handling
     72    ------------------------------------------------------------------ */
     73 /* Call f(arg1), but first switch stacks, using 'stack' as the new
     74    stack, and use 'retaddr' as f's return-to address.  Also, clear all
     75    the integer registers before entering f.*/
     76 
     77 __attribute__ ((noreturn))
     78 void ML_(call_on_new_stack_0_1) (Addr stack, Addr retaddr,
     79                                  void (*f) (Word), Word arg1);
     80                                 //    r0 = stack
     81                                 //    r1 = retaddr
     82                                 //    r2 = f
     83                                 //    r3 = arg1
     84      asm (
     85        ".text\n"
     86        ".globl vgModuleLocal_call_on_new_stack_0_1\n"
     87        "vgModuleLocal_call_on_new_stack_0_1:\n"
     88        "  {\n"
     89        "   move sp, r0\n\t"
     90        "   move r51, r2\n\t"
     91        "  }\n"
     92        "  {\n"
     93        "   move r0, r3\n\t"
     94        "   move r1, zero\n\t"
     95        "  }\n"
     96        "  {\n"
     97        "   move r2, zero\n\t"
     98        "   move r3, zero\n\t"
     99        "  }\n"
    100        "  {\n"
    101        "   move r4, zero\n\t"
    102        "   move r5, zero\n\t"
    103        "  }\n"
    104        "  {\n"
    105        "   move r6, zero\n\t"
    106        "   move r7, zero\n\t"
    107        "  }\n"
    108        "  {\n"
    109        "   move r8, zero\n\t"
    110        "   move r9, zero\n\t"
    111        "  }\n"
    112        "  {\n"
    113        "   move r10, zero\n\t"
    114        "   move r11, zero\n\t"
    115        "  }\n"
    116        "  {\n"
    117        "   move r12, zero\n\t"
    118        "   move r13, zero\n\t"
    119        "  }\n"
    120        "  {\n"
    121        "   move r14, zero\n\t"
    122        "   move r15, zero\n\t"
    123        "  }\n"
    124        "  {\n"
    125        "   move r16, zero\n\t"
    126        "   move r17, zero\n\t"
    127        "  }\n"
    128        "  {\n"
    129        "   move r18, zero\n\t"
    130        "   move r19, zero\n\t"
    131        "  }\n"
    132        "  {\n"
    133        "   move r20, zero\n\t"
    134        "   move r21, zero\n\t"
    135        "  }\n"
    136        "  {\n"
    137        "   move r22, zero\n\t"
    138        "   move r23, zero\n\t"
    139        "  }\n"
    140        "  {\n"
    141        "   move r24, zero\n\t"
    142        "   move r25, zero\n\t"
    143        "  }\n"
    144        "  {\n"
    145        "   move r26, zero\n\t"
    146        "   move r27, zero\n\t"
    147        "  }\n"
    148        "  {\n"
    149        "   move r28, zero\n\t"
    150        "   move r29, zero\n\t"
    151        "  }\n"
    152        "  {\n"
    153        "   move r30, zero\n\t"
    154        "   move r31, zero\n\t"
    155        "  }\n"
    156        "  {\n"
    157        "   move r32, zero\n\t"
    158        "   move r33, zero\n\t"
    159        "  }\n"
    160        "  {\n"
    161        "   move r34, zero\n\t"
    162        "   move r35, zero\n\t"
    163        "  }\n"
    164        "  {\n"
    165        "   move r36, zero\n\t"
    166        "   move r37, zero\n\t"
    167        "  }\n"
    168        "  {\n"
    169        "   move r38, zero\n\t"
    170        "   move r39, zero\n\t"
    171        "  }\n"
    172        "  {\n"
    173        "   move r40, zero\n\t"
    174        "   move r41, zero\n\t"
    175        "  }\n"
    176        "  {\n"
    177        "   move r42, zero\n\t"
    178        "   move r43, zero\n\t"
    179        "  }\n"
    180        "  {\n"
    181        "   move r44, zero\n\t"
    182        "   move r45, zero\n\t"
    183        "  }\n"
    184        "  {\n"
    185        "   move r46, zero\n\t"
    186        "   move r47, zero\n\t"
    187        "  }\n"
    188        "  {\n"
    189        "   move r48, zero\n\t"
    190        "   move r49, zero\n\t"
    191        "  }\n"
    192        "  {\n"
    193        "   move r50, zero\n\t"
    194        "   jr      r51\n\t"
    195        "  }\n"
    196        "   ill \n"    // should never get here
    197           );
    198 /*
    199   Perform a clone system call.  clone is strange because it has
    200   fork()-like return-twice semantics, so it needs special
    201   handling here.
    202   Upon entry, we have:
    203   int (fn)(void*)     in  r0
    204   void* child_stack   in  r1
    205   int flags           in  r2
    206   void* arg           in  r3
    207   pid_t* child_tid    in  r4
    208   pid_t* parent_tid   in  r5
    209   void* tls_ptr       in  r6
    210 
    211   System call requires:
    212   int    $__NR_clone  in r10
    213   int    flags        in r0
    214   void*  child_stack  in r1
    215   pid_t* parent_tid   in r2
    216   void*  tls_ptr      in $r3
    217   pid_t* child_tid    in sr4
    218 
    219   int clone(int (*fn)(void *arg), void *child_stack, int flags, void *arg,
    220   void *parent_tidptr, void *tls, void *child_tidptr)
    221 
    222   Returns an Int encoded in the linux-tilegx way, not a SysRes.
    223 */
    224 #define __NR_CLONE        VG_STRINGIFY(__NR_clone)
    225 #define __NR_EXIT         VG_STRINGIFY(__NR_exit)
    226 
    227 Long do_syscall_clone_tilegx_linux ( Word (*fn) (void *),  //r0
    228                                      void *stack,          //r1
    229                                      Long flags,           //r2
    230                                      void *arg,            //r3
    231                                      Long * child_tid,     //r4
    232                                      Long * parent_tid,    //r5
    233                                      Long   tls );         //r6
    234     /*
    235       stack
    236       high -> 4  r29
    237       3
    238       2
    239       1  r10
    240       low  -> 0  lr    <- sp
    241     */
    242      asm (
    243        ".text\n"
    244        "   .globl   do_syscall_clone_tilegx_linux\n"
    245        "   do_syscall_clone_tilegx_linux:\n"
    246        "   beqz  r0, .Linvalid\n"
    247        "   beqz  r1, .Linvalid\n"
    248        "   {\n"
    249        "    st    sp, r29; "       // save r29 at top
    250        "    addli sp, sp, -32\n"   // open new stack space
    251        "   }\n"
    252 
    253        "    move  r29, sp; "       // r29 <- sp
    254        "    st    r29, lr\n"       // save lr at 0(sp)
    255 
    256        "    addi  r29, r29, 8\n"
    257        "   {\n"
    258        "    st    r29, r10\n"      // save r10 at 8(sp)
    259        /*  setup child stack */
    260        "    addi  r1, r1, -32\n"   // new stack frame for child
    261        "   }\n"
    262        /*  save fn */
    263        "   { st  r1, r0; addi r1, r1, 8 }\n"
    264        /*  save args */
    265        "   { st  r1, r3; addi r1, r1, 8 }\n"
    266        /*  save flags */
    267        "   { st  r1, r2; addi r1, r1, -16 }\n"
    268 
    269        /*  Child stack layout
    270 
    271            flags
    272            args
    273            r1->  fn
    274        */
    275        "   {\n"
    276        /*   prepare args for clone. */
    277        "    move r0,  r2\n"   // arg0 = flags
    278        /*   arg1=r1 child stack */
    279        "    move r2,  r5\n"   // arg2 = parent tid
    280        "   }\n"
    281        "   {\n"
    282        "    move r3,  r4\n"   // arg3 = child tid
    283        "    move r4,  r6\n"   // arg4 = tls
    284        "   }\n"
    285        "   moveli r10, " __NR_CLONE "\n"
    286        "   swint1\n"
    287 
    288        "   beqz  r0, .Lchild\n"
    289        "   move r29, sp\n"
    290        "   ld   lr, r29\n"        // Restore lr
    291        "   addi r29, r29, 8\n"
    292        "   {\n"
    293        "    ld   r10,  r29\n"      // resotre r10
    294        "    addi sp, sp, 32\n"
    295        "   }\n"
    296        "   ld   r29, sp\n"
    297        "   jrp  lr\n"
    298 
    299        ".Lchild:"
    300        "   move r2, sp\n"
    301        "   {\n"
    302        "    ld   r3, r2\n"
    303        "    addi r2, r2, 8\n"
    304        "   }\n"
    305        "   ld   r0, r2\n"
    306        "   jalr r3\n"
    307        "   moveli r10, " __NR_EXIT "\n"
    308        "   swint1\n"
    309 
    310        ".Linvalid:"
    311        "  { movei r1, 22; jrp lr }\n"
    312           );
    313 
    314 #undef __NR_CLONE
    315 #undef __NR_EXIT
    316 
    317 // forward declarations
    318 static void setup_child ( ThreadArchState *, ThreadArchState * );
    319 static SysRes sys_set_tls ( ThreadId tid, Addr tlsptr );
    320  /*
    321    When a client clones, we need to keep track of the new thread.  This means:
    322    1. allocate a ThreadId+ThreadState+stack for the the thread
    323    2. initialize the thread's new VCPU state
    324    3. create the thread using the same args as the client requested,
    325    but using the scheduler entrypoint for IP, and a separate stack
    326    for SP.
    327  */
    328 static SysRes do_clone ( ThreadId ptid,
    329                          Long flags, Addr sp,
    330                          Long * parent_tidptr,
    331                          Long * child_tidptr,
    332                          Addr child_tls )
    333 {
    334   const Bool debug = False;
    335   ThreadId ctid = VG_ (alloc_ThreadState) ();
    336   ThreadState * ptst = VG_ (get_ThreadState) (ptid);
    337   ThreadState * ctst = VG_ (get_ThreadState) (ctid);
    338   Long ret = 0;
    339   Long * stack;
    340   SysRes res;
    341   vki_sigset_t blockall, savedmask;
    342 
    343   VG_ (sigfillset) (&blockall);
    344   vg_assert (VG_ (is_running_thread) (ptid));
    345   vg_assert (VG_ (is_valid_tid) (ctid));
    346   stack = (Long *) ML_ (allocstack) (ctid);
    347   if (stack == NULL) {
    348     res = VG_ (mk_SysRes_Error) (VKI_ENOMEM);
    349     goto out;
    350   }
    351   setup_child (&ctst->arch, &ptst->arch);
    352 
    353   /* On TILEGX we need to set r0 and r3 to zero */
    354   ctst->arch.vex.guest_r0 = 0;
    355   ctst->arch.vex.guest_r3 = 0;
    356   if (sp != 0)
    357     ctst->arch.vex.guest_r54 = sp;
    358 
    359   ctst->os_state.parent = ptid;
    360   ctst->sig_mask = ptst->sig_mask;
    361   ctst->tmp_sig_mask = ptst->sig_mask;
    362 
    363   /* Start the child with its threadgroup being the same as the
    364      parent's.  This is so that any exit_group calls that happen
    365      after the child is created but before it sets its
    366      os_state.threadgroup field for real (in thread_wrapper in
    367      syswrap-linux.c), really kill the new thread.  a.k.a this avoids
    368      a race condition in which the thread is unkillable (via
    369      exit_group) because its threadgroup is not set.  The race window
    370      is probably only a few hundred or a few thousand cycles long.
    371      See #226116. */
    372 
    373   ctst->os_state.threadgroup = ptst->os_state.threadgroup;
    374   ML_(guess_and_register_stack) (sp, ctst);
    375 
    376   VG_TRACK (pre_thread_ll_create, ptid, ctid);
    377   if (flags & VKI_CLONE_SETTLS) {
    378     if (debug)
    379       VG_(printf)("clone child has SETTLS: tls at %#lx\n", child_tls);
    380     ctst->arch.vex.guest_r53 = child_tls;
    381     res = sys_set_tls(ctid, child_tls);
    382     if (sr_isError(res))
    383       goto out;
    384   }
    385 
    386   flags &= ~VKI_CLONE_SETTLS;
    387   VG_ (sigprocmask) (VKI_SIG_SETMASK, &blockall, &savedmask);
    388   /* Create the new thread */
    389   ret = do_syscall_clone_tilegx_linux (ML_ (start_thread_NORETURN),
    390                                        stack, flags, &VG_ (threads)[ctid],
    391                                        child_tidptr, parent_tidptr,
    392                                        (Long)NULL /*child_tls*/);
    393 
    394   /* High half word64 is syscall return value. */
    395   if (debug)
    396     VG_(printf)("ret: 0x%lx\n", ret);
    397 
    398   res = VG_(mk_SysRes_tilegx_linux) (/*val */ ret);
    399 
    400   VG_ (sigprocmask) (VKI_SIG_SETMASK, &savedmask, NULL);
    401 
    402  out:
    403   if (sr_isError (res)) {
    404     VG_(cleanup_thread) (&ctst->arch);
    405     ctst->status = VgTs_Empty;
    406     VG_TRACK (pre_thread_ll_exit, ctid);
    407   }
    408   ptst->arch.vex.guest_r0 = 0;
    409 
    410   return res;
    411 }
    412 
    413 extern Addr do_brk ( Addr newbrk );
    414 
    415 extern
    416 SysRes do_mremap( Addr old_addr, SizeT old_len,
    417                   Addr new_addr, SizeT new_len,
    418                   UWord flags, ThreadId tid );
    419 
    420 extern Bool linux_kernel_2_6_22(void);
    421 
    422 /* ---------------------------------------------------------------------
    423    More thread stuff
    424    ------------------------------------------------------------------ */
    425 
    426 // TILEGX doesn't have any architecture specific thread stuff that
    427 // needs to be cleaned up.
    428 void
    429 VG_ (cleanup_thread) ( ThreadArchState * arch ) { }
    430 
    431 void
    432 setup_child ( /*OUT*/ ThreadArchState * child,
    433               /*IN*/ ThreadArchState * parent )
    434 {
    435   /* We inherit our parent's guest state. */
    436   child->vex = parent->vex;
    437   child->vex_shadow1 = parent->vex_shadow1;
    438   child->vex_shadow2 = parent->vex_shadow2;
    439 }
    440 
    441 SysRes sys_set_tls ( ThreadId tid, Addr tlsptr )
    442 {
    443   VG_(threads)[tid].arch.vex.guest_r53 = tlsptr;
    444   return VG_(mk_SysRes_Success)( 0 );
    445 }
    446 
    447 
    448 /* ---------------------------------------------------------------------
    449    PRE/POST wrappers for tilegx/Linux-specific syscalls
    450    ------------------------------------------------------------------ */
    451 #define PRE(name)       DEFN_PRE_TEMPLATE(tilegx_linux, name)
    452 #define POST(name)      DEFN_POST_TEMPLATE(tilegx_linux, name)
    453 
    454 /* Add prototypes for the wrappers declared here, so that gcc doesn't
    455    harass us for not having prototypes.  Really this is a kludge --
    456    the right thing to do is to make these wrappers 'static' since they
    457    aren't visible outside this file, but that requires even more macro
    458    magic. */
    459 
    460 DECL_TEMPLATE (tilegx_linux, sys_clone);
    461 DECL_TEMPLATE (tilegx_linux, sys_rt_sigreturn);
    462 DECL_TEMPLATE (tilegx_linux, sys_socket);
    463 DECL_TEMPLATE (tilegx_linux, sys_setsockopt);
    464 DECL_TEMPLATE (tilegx_linux, sys_getsockopt);
    465 DECL_TEMPLATE (tilegx_linux, sys_connect);
    466 DECL_TEMPLATE (tilegx_linux, sys_accept);
    467 DECL_TEMPLATE (tilegx_linux, sys_accept4);
    468 DECL_TEMPLATE (tilegx_linux, sys_sendto);
    469 DECL_TEMPLATE (tilegx_linux, sys_recvfrom);
    470 DECL_TEMPLATE (tilegx_linux, sys_sendmsg);
    471 DECL_TEMPLATE (tilegx_linux, sys_recvmsg);
    472 DECL_TEMPLATE (tilegx_linux, sys_shutdown);
    473 DECL_TEMPLATE (tilegx_linux, sys_bind);
    474 DECL_TEMPLATE (tilegx_linux, sys_listen);
    475 DECL_TEMPLATE (tilegx_linux, sys_getsockname);
    476 DECL_TEMPLATE (tilegx_linux, sys_getpeername);
    477 DECL_TEMPLATE (tilegx_linux, sys_socketpair);
    478 DECL_TEMPLATE (tilegx_linux, sys_semget);
    479 DECL_TEMPLATE (tilegx_linux, sys_semop);
    480 DECL_TEMPLATE (tilegx_linux, sys_semtimedop);
    481 DECL_TEMPLATE (tilegx_linux, sys_semctl);
    482 DECL_TEMPLATE (tilegx_linux, sys_msgget);
    483 DECL_TEMPLATE (tilegx_linux, sys_msgrcv);
    484 DECL_TEMPLATE (tilegx_linux, sys_msgsnd);
    485 DECL_TEMPLATE (tilegx_linux, sys_msgctl);
    486 DECL_TEMPLATE (tilegx_linux, sys_shmget);
    487 DECL_TEMPLATE (tilegx_linux, wrap_sys_shmat);
    488 DECL_TEMPLATE (tilegx_linux, sys_shmdt);
    489 DECL_TEMPLATE (tilegx_linux, sys_shmdt);
    490 DECL_TEMPLATE (tilegx_linux, sys_shmctl);
    491 DECL_TEMPLATE (tilegx_linux, sys_arch_prctl);
    492 DECL_TEMPLATE (tilegx_linux, sys_ptrace);
    493 DECL_TEMPLATE (tilegx_linux, sys_fadvise64);
    494 DECL_TEMPLATE (tilegx_linux, sys_mmap);
    495 DECL_TEMPLATE (tilegx_linux, sys_syscall184);
    496 DECL_TEMPLATE (tilegx_linux, sys_cacheflush);
    497 DECL_TEMPLATE (tilegx_linux, sys_set_dataplane);
    498 
    499 PRE(sys_clone)
    500 {
    501   ULong cloneflags;
    502 
    503   PRINT("sys_clone ( %lx, %#lx, %#lx, %#lx, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5);
    504   PRE_REG_READ5(int, "clone",
    505                 unsigned long, flags,
    506                 void *, child_stack,
    507                 int *, parent_tidptr,
    508                 int *, child_tidptr,
    509                 void *, tlsaddr);
    510 
    511   if (ARG1 & VKI_CLONE_PARENT_SETTID) {
    512     PRE_MEM_WRITE("clone(parent_tidptr)", ARG3, sizeof(Int));
    513     if (!VG_(am_is_valid_for_client)(ARG3, sizeof(Int), VKI_PROT_WRITE)) {
    514       SET_STATUS_Failure( VKI_EFAULT );
    515       return;
    516     }
    517   }
    518   if (ARG1 & (VKI_CLONE_CHILD_SETTID | VKI_CLONE_CHILD_CLEARTID)) {
    519     PRE_MEM_WRITE("clone(child_tidptr)", ARG4, sizeof(Int));
    520     if (!VG_(am_is_valid_for_client)(ARG4, sizeof(Int), VKI_PROT_WRITE)) {
    521       SET_STATUS_Failure( VKI_EFAULT );
    522       return;
    523     }
    524   }
    525 
    526   cloneflags = ARG1;
    527 
    528   if (!ML_(client_signal_OK)(ARG1 & VKI_CSIGNAL)) {
    529     SET_STATUS_Failure( VKI_EINVAL );
    530     return;
    531   }
    532 
    533   /* Only look at the flags we really care about */
    534   switch (cloneflags & (VKI_CLONE_VM | VKI_CLONE_FS
    535                         | VKI_CLONE_FILES | VKI_CLONE_VFORK)) {
    536   case VKI_CLONE_VM | VKI_CLONE_FS | VKI_CLONE_FILES:
    537     /* thread creation */
    538     SET_STATUS_from_SysRes(
    539       do_clone(tid,
    540                ARG1,          /* flags */
    541                (Addr)ARG2,    /* child ESP */
    542                (Long *)ARG3,  /* parent_tidptr */
    543                (Long *)ARG4,  /* child_tidptr */
    544                (Addr)ARG5));  /* set_tls */
    545     break;
    546 
    547   case VKI_CLONE_VFORK | VKI_CLONE_VM: /* vfork */
    548     /* FALLTHROUGH - assume vfork == fork */
    549     cloneflags &= ~(VKI_CLONE_VFORK | VKI_CLONE_VM);
    550 
    551   case 0: /* plain fork */
    552     SET_STATUS_from_SysRes(
    553       ML_(do_fork_clone)(tid,
    554                          cloneflags,      /* flags */
    555                          (Int *)ARG3,     /* parent_tidptr */
    556                          (Int *)ARG4));   /* child_tidptr */
    557     break;
    558 
    559   default:
    560     /* should we just ENOSYS? */
    561     VG_(message)(Vg_UserMsg,
    562                  "Unsupported clone() flags: 0x%lx\n", ARG1);
    563     VG_(message)(Vg_UserMsg,
    564                  "\n");
    565     VG_(message)(Vg_UserMsg,
    566                  "The only supported clone() uses are:\n");
    567     VG_(message)(Vg_UserMsg,
    568                  " - via a threads library (LinuxThreads or NPTL)\n");
    569     VG_(message)(Vg_UserMsg,
    570                  " - via the implementation of fork or vfork\n");
    571     VG_(unimplemented)
    572       ("Valgrind does not support general clone().");
    573   }
    574 
    575   if (SUCCESS) {
    576     if (ARG1 & VKI_CLONE_PARENT_SETTID)
    577       POST_MEM_WRITE(ARG3, sizeof(Int));
    578     if (ARG1 & (VKI_CLONE_CHILD_SETTID | VKI_CLONE_CHILD_CLEARTID))
    579       POST_MEM_WRITE(ARG4, sizeof(Int));
    580 
    581     /* Thread creation was successful; let the child have the chance
    582        to run */
    583     *flags |= SfYieldAfter;
    584   }
    585 }
    586 
    587 PRE(sys_rt_sigreturn)
    588 {
    589   /* This isn't really a syscall at all - it's a misuse of the
    590      syscall mechanism by m_sigframe.  VG_(sigframe_create) sets the
    591      return address of the signal frames it creates to be a short
    592      piece of code which does this "syscall".  The only purpose of
    593      the syscall is to call VG_(sigframe_destroy), which restores the
    594      thread's registers from the frame and then removes it.
    595      Consequently we must ask the syswrap driver logic not to write
    596      back the syscall "result" as that would overwrite the
    597      just-restored register state. */
    598 
    599   ThreadState* tst;
    600   PRINT("sys_rt_sigreturn ( )");
    601 
    602   vg_assert(VG_(is_valid_tid)(tid));
    603   vg_assert(tid >= 1 && tid < VG_N_THREADS);
    604   vg_assert(VG_(is_running_thread)(tid));
    605 
    606   /* Adjust RSP to point to start of frame; skip back up over handler
    607      ret addr */
    608   tst = VG_(get_ThreadState)(tid);
    609   tst->arch.vex.guest_r54 -= sizeof(Addr);
    610 
    611   /* This is only so that the RIP is (might be) useful to report if
    612      something goes wrong in the sigreturn.  JRS 20070318: no idea
    613      what this is for */
    614   ML_(fixup_guest_state_to_restart_syscall)(&tst->arch);
    615 
    616   /* Restore register state from frame and remove it, as
    617      described above */
    618   VG_(sigframe_destroy)(tid, True);
    619 
    620   /* Tell the driver not to update the guest state with the "result",
    621      and set a bogus result to keep it happy. */
    622   *flags |= SfNoWriteResult;
    623   SET_STATUS_Success(0);
    624 
    625   /* Check to see if any signals arose as a result of this. */
    626   *flags |= SfPollAfter;
    627 }
    628 
    629 PRE(sys_arch_prctl)
    630 {
    631   PRINT( "arch_prctl ( %ld, %lx )", ARG1, ARG2 );
    632 
    633   vg_assert(VG_(is_valid_tid)(tid));
    634   vg_assert(tid >= 1 && tid < VG_N_THREADS);
    635   vg_assert(VG_(is_running_thread)(tid));
    636 
    637   I_die_here;
    638 }
    639 
    640 // Parts of this are tilegx-specific, but the *PEEK* cases are generic.
    641 //
    642 // ARG3 is only used for pointers into the traced process's address
    643 // space and for offsets into the traced process's struct
    644 // user_regs_struct. It is never a pointer into this process's memory
    645 // space, and we should therefore not check anything it points to.
    646 PRE(sys_ptrace)
    647 {
    648   PRINT("sys_ptrace ( %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4);
    649   PRE_REG_READ4(int, "ptrace",
    650                 long, request, long, pid, long, addr, long, data);
    651   switch (ARG1) {
    652   case VKI_PTRACE_PEEKTEXT:
    653   case VKI_PTRACE_PEEKDATA:
    654   case VKI_PTRACE_PEEKUSR:
    655     PRE_MEM_WRITE( "ptrace(peek)", ARG4,
    656                    sizeof (long));
    657     break;
    658   case VKI_PTRACE_GETREGS:
    659     PRE_MEM_WRITE( "ptrace(getregs)", ARG4,
    660                    sizeof (struct vki_user_regs_struct));
    661     break;
    662 #if 0 // FIXME
    663   case VKI_PTRACE_GETFPREGS:
    664     PRE_MEM_WRITE( "ptrace(getfpregs)", ARG4,
    665                    sizeof (struct vki_user_i387_struct));
    666     break;
    667 #endif
    668   case VKI_PTRACE_SETREGS:
    669     PRE_MEM_READ( "ptrace(setregs)", ARG4,
    670                   sizeof (struct vki_user_regs_struct));
    671     break;
    672 #if 0 // FIXME
    673   case VKI_PTRACE_SETFPREGS:
    674     PRE_MEM_READ( "ptrace(setfpregs)", ARG4,
    675                   sizeof (struct vki_user_i387_struct));
    676     break;
    677 #endif
    678   case VKI_PTRACE_GETEVENTMSG:
    679     PRE_MEM_WRITE( "ptrace(geteventmsg)", ARG4, sizeof(unsigned long));
    680     break;
    681   case VKI_PTRACE_GETSIGINFO:
    682     PRE_MEM_WRITE( "ptrace(getsiginfo)", ARG4, sizeof(vki_siginfo_t));
    683     break;
    684   case VKI_PTRACE_SETSIGINFO:
    685     PRE_MEM_READ( "ptrace(setsiginfo)", ARG4, sizeof(vki_siginfo_t));
    686     break;
    687   default:
    688     break;
    689   }
    690 }
    691 
    692 POST(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 #if 0 // FIXME
    704   case VKI_PTRACE_GETFPREGS:
    705     POST_MEM_WRITE( ARG4, sizeof (struct vki_user_i387_struct));
    706     break;
    707 #endif
    708   case VKI_PTRACE_GETEVENTMSG:
    709     POST_MEM_WRITE( ARG4, sizeof(unsigned long));
    710     break;
    711   case VKI_PTRACE_GETSIGINFO:
    712     /* XXX: This is a simplification. Different parts of the
    713      * siginfo_t are valid depending on the type of signal.
    714      */
    715     POST_MEM_WRITE( ARG4, sizeof(vki_siginfo_t));
    716     break;
    717   default:
    718     break;
    719   }
    720 }
    721 
    722 PRE(sys_socket)
    723 {
    724   PRINT("sys_socket ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
    725   PRE_REG_READ3(long, "socket", int, domain, int, type, int, protocol);
    726 }
    727 POST(sys_socket)
    728 {
    729   SysRes r;
    730   vg_assert(SUCCESS);
    731   r = ML_(generic_POST_sys_socket)(tid, VG_(mk_SysRes_Success)(RES));
    732   SET_STATUS_from_SysRes(r);
    733 }
    734 
    735 PRE(sys_setsockopt)
    736 {
    737   PRINT("sys_setsockopt ( %ld, %ld, %ld, %#lx, %ld )",ARG1,ARG2,ARG3,ARG4,ARG5);
    738   PRE_REG_READ5(long, "setsockopt",
    739                 int, s, int, level, int, optname,
    740                 const void *, optval, int, optlen);
    741   ML_(generic_PRE_sys_setsockopt)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
    742 }
    743 
    744 PRE(sys_getsockopt)
    745 {
    746   PRINT("sys_getsockopt ( %ld, %ld, %ld, %#lx, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5);
    747   PRE_REG_READ5(long, "getsockopt",
    748                 int, s, int, level, int, optname,
    749                 void *, optval, int, *optlen);
    750   ML_(linux_PRE_sys_getsockopt)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
    751 }
    752 POST(sys_getsockopt)
    753 {
    754   vg_assert(SUCCESS);
    755   ML_(linux_POST_sys_getsockopt)(tid, VG_(mk_SysRes_Success)(RES),
    756                                  ARG1,ARG2,ARG3,ARG4,ARG5);
    757 }
    758 
    759 PRE(sys_connect)
    760 {
    761   *flags |= SfMayBlock;
    762   PRINT("sys_connect ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
    763   PRE_REG_READ3(long, "connect",
    764                 int, sockfd, struct sockaddr *, serv_addr, int, addrlen);
    765   ML_(generic_PRE_sys_connect)(tid, ARG1,ARG2,ARG3);
    766 }
    767 
    768 PRE(sys_accept)
    769 {
    770   *flags |= SfMayBlock;
    771   PRINT("sys_accept ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
    772   PRE_REG_READ3(long, "accept",
    773                 int, s, struct sockaddr *, addr, int, *addrlen);
    774   ML_(generic_PRE_sys_accept)(tid, ARG1,ARG2,ARG3);
    775 }
    776 POST(sys_accept)
    777 {
    778   SysRes r;
    779   vg_assert(SUCCESS);
    780   r = ML_(generic_POST_sys_accept)(tid, VG_(mk_SysRes_Success)(RES),
    781                                    ARG1,ARG2,ARG3);
    782   SET_STATUS_from_SysRes(r);
    783 }
    784 
    785 PRE(sys_accept4)
    786 {
    787   *flags |= SfMayBlock;
    788   PRINT("sys_accept4 ( %ld, %#lx, %ld, %ld )",ARG1,ARG2,ARG3,ARG4);
    789   PRE_REG_READ4(long, "accept4",
    790                 int, s, struct sockaddr *, addr, int, *addrlen, int, flags);
    791   ML_(generic_PRE_sys_accept)(tid, ARG1,ARG2,ARG3);
    792 }
    793 POST(sys_accept4)
    794 {
    795   SysRes r;
    796   vg_assert(SUCCESS);
    797   r = ML_(generic_POST_sys_accept)(tid, VG_(mk_SysRes_Success)(RES),
    798                                    ARG1,ARG2,ARG3);
    799   SET_STATUS_from_SysRes(r);
    800 }
    801 
    802 PRE(sys_sendto)
    803 {
    804   *flags |= SfMayBlock;
    805   PRINT("sys_sendto ( %ld, %#lx, %ld, %lu, %#lx, %ld )",ARG1,ARG2,ARG3,
    806         ARG4,ARG5,ARG6);
    807   PRE_REG_READ6(long, "sendto",
    808                 int, s, const void *, msg, int, len,
    809                 unsigned int, flags,
    810                 const struct sockaddr *, to, int, tolen);
    811   ML_(generic_PRE_sys_sendto)(tid, ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
    812 }
    813 
    814 PRE(sys_recvfrom)
    815 {
    816   *flags |= SfMayBlock;
    817   PRINT("sys_recvfrom ( %ld, %#lx, %ld, %lu, %#lx, %#lx )",ARG1,ARG2,ARG3,
    818         ARG4,ARG5,ARG6);
    819   PRE_REG_READ6(long, "recvfrom",
    820                 int, s, void *, buf, int, len, unsigned int, flags,
    821                 struct sockaddr *, from, int *, fromlen);
    822   ML_(generic_PRE_sys_recvfrom)(tid, ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
    823 }
    824 POST(sys_recvfrom)
    825 {
    826   vg_assert(SUCCESS);
    827   ML_(generic_POST_sys_recvfrom)(tid, VG_(mk_SysRes_Success)(RES),
    828                                  ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
    829 }
    830 
    831 PRE(sys_sendmsg)
    832 {
    833   *flags |= SfMayBlock;
    834   PRINT("sys_sendmsg ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
    835   PRE_REG_READ3(long, "sendmsg",
    836                 int, s, const struct msghdr *, msg, int, flags);
    837   ML_(generic_PRE_sys_sendmsg)(tid, "msg", ARG2);
    838 }
    839 
    840 PRE(sys_recvmsg)
    841 {
    842   *flags |= SfMayBlock;
    843   PRINT("sys_recvmsg ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
    844   PRE_REG_READ3(long, "recvmsg", int, s, struct msghdr *, msg, int, flags);
    845   ML_(generic_PRE_sys_recvmsg)(tid, "msg", (struct vki_msghdr *) ARG2);
    846 }
    847 
    848 POST(sys_recvmsg)
    849 {
    850   ML_(generic_POST_sys_recvmsg)(tid, "msg", (struct vki_msghdr *)ARG2, RES);
    851 }
    852 
    853 PRE(sys_shutdown)
    854 {
    855   *flags |= SfMayBlock;
    856   PRINT("sys_shutdown ( %ld, %ld )",ARG1,ARG2);
    857   PRE_REG_READ2(int, "shutdown", int, s, int, how);
    858 }
    859 
    860 PRE(sys_bind)
    861 {
    862   PRINT("sys_bind ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
    863   PRE_REG_READ3(long, "bind",
    864                 int, sockfd, struct sockaddr *, my_addr, int, addrlen);
    865   ML_(generic_PRE_sys_bind)(tid, ARG1,ARG2,ARG3);
    866 }
    867 
    868 PRE(sys_listen)
    869 {
    870   PRINT("sys_listen ( %ld, %ld )",ARG1,ARG2);
    871   PRE_REG_READ2(long, "listen", int, s, int, backlog);
    872 }
    873 
    874 PRE(sys_getsockname)
    875 {
    876   PRINT("sys_getsockname ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
    877   PRE_REG_READ3(long, "getsockname",
    878                 int, s, struct sockaddr *, name, int *, namelen);
    879   ML_(generic_PRE_sys_getsockname)(tid, ARG1,ARG2,ARG3);
    880 }
    881 POST(sys_getsockname)
    882 {
    883   vg_assert(SUCCESS);
    884   ML_(generic_POST_sys_getsockname)(tid, VG_(mk_SysRes_Success)(RES),
    885                                     ARG1,ARG2,ARG3);
    886 }
    887 
    888 PRE(sys_getpeername)
    889 {
    890   PRINT("sys_getpeername ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
    891   PRE_REG_READ3(long, "getpeername",
    892                 int, s, struct sockaddr *, name, int *, namelen);
    893   ML_(generic_PRE_sys_getpeername)(tid, ARG1,ARG2,ARG3);
    894 }
    895 POST(sys_getpeername)
    896 {
    897   vg_assert(SUCCESS);
    898   ML_(generic_POST_sys_getpeername)(tid, VG_(mk_SysRes_Success)(RES),
    899                                     ARG1,ARG2,ARG3);
    900 }
    901 
    902 PRE(sys_socketpair)
    903 {
    904   PRINT("sys_socketpair ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
    905   PRE_REG_READ4(long, "socketpair",
    906                 int, d, int, type, int, protocol, int*, sv);
    907   ML_(generic_PRE_sys_socketpair)(tid, ARG1,ARG2,ARG3,ARG4);
    908 }
    909 POST(sys_socketpair)
    910 {
    911   vg_assert(SUCCESS);
    912   ML_(generic_POST_sys_socketpair)(tid, VG_(mk_SysRes_Success)(RES),
    913                                    ARG1,ARG2,ARG3,ARG4);
    914 }
    915 
    916 PRE(sys_semget)
    917 {
    918   PRINT("sys_semget ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
    919   PRE_REG_READ3(long, "semget", vki_key_t, key, int, nsems, int, semflg);
    920 }
    921 
    922 PRE(sys_semop)
    923 {
    924   *flags |= SfMayBlock;
    925   PRINT("sys_semop ( %ld, %#lx, %lu )",ARG1,ARG2,ARG3);
    926   PRE_REG_READ3(long, "semop",
    927                 int, semid, struct sembuf *, sops, unsigned, nsoops);
    928   ML_(generic_PRE_sys_semop)(tid, ARG1,ARG2,ARG3);
    929 }
    930 
    931 PRE(sys_semtimedop)
    932 {
    933   *flags |= SfMayBlock;
    934   PRINT("sys_semtimedop ( %ld, %#lx, %lu, %#lx )",ARG1,ARG2,ARG3,ARG4);
    935   PRE_REG_READ4(long, "semtimedop",
    936                 int, semid, struct sembuf *, sops, unsigned, nsoops,
    937                 struct timespec *, timeout);
    938   ML_(generic_PRE_sys_semtimedop)(tid, ARG1,ARG2,ARG3,ARG4);
    939 }
    940 
    941 PRE(sys_semctl)
    942 {
    943   switch (ARG3 & ~VKI_IPC_64) {
    944   case VKI_IPC_INFO:
    945   case VKI_SEM_INFO:
    946     PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
    947     PRE_REG_READ4(long, "semctl",
    948                   int, semid, int, semnum, int, cmd, struct seminfo *, arg);
    949     break;
    950   case VKI_IPC_STAT:
    951   case VKI_SEM_STAT:
    952   case VKI_IPC_SET:
    953     PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
    954     PRE_REG_READ4(long, "semctl",
    955                   int, semid, int, semnum, int, cmd, struct semid_ds *, arg);
    956     break;
    957   case VKI_GETALL:
    958   case VKI_SETALL:
    959     PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
    960     PRE_REG_READ4(long, "semctl",
    961                   int, semid, int, semnum, int, cmd, unsigned short *, arg);
    962     break;
    963   default:
    964     PRINT("sys_semctl ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
    965     PRE_REG_READ3(long, "semctl",
    966                   int, semid, int, semnum, int, cmd);
    967     break;
    968   }
    969   ML_(generic_PRE_sys_semctl)(tid, ARG1,ARG2,ARG3|VKI_IPC_64,ARG4);
    970 }
    971 POST(sys_semctl)
    972 {
    973   ML_(generic_POST_sys_semctl)(tid, RES,ARG1,ARG2,ARG3|VKI_IPC_64,ARG4);
    974 }
    975 
    976 PRE(sys_msgget)
    977 {
    978   PRINT("sys_msgget ( %ld, %ld )",ARG1,ARG2);
    979   PRE_REG_READ2(long, "msgget", vki_key_t, key, int, msgflg);
    980 }
    981 
    982 PRE(sys_msgsnd)
    983 {
    984   PRINT("sys_msgsnd ( %ld, %#lx, %ld, %ld )",ARG1,ARG2,ARG3,ARG4);
    985   PRE_REG_READ4(long, "msgsnd",
    986                 int, msqid, struct msgbuf *, msgp, vki_size_t, msgsz,
    987                 int, msgflg);
    988   ML_(linux_PRE_sys_msgsnd)(tid, ARG1,ARG2,ARG3,ARG4);
    989   if ((ARG4 & VKI_IPC_NOWAIT) == 0)
    990     *flags |= SfMayBlock;
    991 }
    992 
    993 PRE(sys_msgrcv)
    994 {
    995   PRINT("sys_msgrcv ( %ld, %#lx, %ld, %ld, %ld )",ARG1,ARG2,ARG3,ARG4,ARG5);
    996   PRE_REG_READ5(long, "msgrcv",
    997                 int, msqid, struct msgbuf *, msgp, vki_size_t, msgsz,
    998                 long, msgytp, int, msgflg);
    999   ML_(linux_PRE_sys_msgrcv)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
   1000   if ((ARG4 & VKI_IPC_NOWAIT) == 0)
   1001     *flags |= SfMayBlock;
   1002 }
   1003 POST(sys_msgrcv)
   1004 {
   1005   ML_(linux_POST_sys_msgrcv)(tid, RES,ARG1,ARG2,ARG3,ARG4,ARG5);
   1006 }
   1007 
   1008 PRE(sys_msgctl)
   1009 {
   1010   PRINT("sys_msgctl ( %ld, %ld, %#lx )",ARG1,ARG2,ARG3);
   1011   PRE_REG_READ3(long, "msgctl",
   1012                 int, msqid, int, cmd, struct msqid_ds *, buf);
   1013   ML_(linux_PRE_sys_msgctl)(tid, ARG1,ARG2,ARG3);
   1014 }
   1015 POST(sys_msgctl)
   1016 {
   1017   ML_(linux_POST_sys_msgctl)(tid, RES,ARG1,ARG2,ARG3);
   1018 }
   1019 
   1020 PRE(sys_shmget)
   1021 {
   1022   PRINT("sys_shmget ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
   1023   PRE_REG_READ3(long, "shmget", vki_key_t, key, vki_size_t, size, int, shmflg);
   1024 }
   1025 
   1026 PRE(wrap_sys_shmat)
   1027 {
   1028   UWord arg2tmp;
   1029   PRINT("wrap_sys_shmat ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
   1030   PRE_REG_READ3(long, "shmat",
   1031                 int, shmid, const void *, shmaddr, int, shmflg);
   1032   arg2tmp = ML_(generic_PRE_sys_shmat)(tid, ARG1,ARG2,ARG3);
   1033   if (arg2tmp == 0)
   1034     SET_STATUS_Failure( VKI_EINVAL );
   1035   else
   1036     ARG2 = arg2tmp;  // used in POST
   1037 }
   1038 POST(wrap_sys_shmat)
   1039 {
   1040   ML_(generic_POST_sys_shmat)(tid, RES,ARG1,ARG2,ARG3);
   1041 }
   1042 
   1043 PRE(sys_shmdt)
   1044 {
   1045   PRINT("sys_shmdt ( %#lx )",ARG1);
   1046   PRE_REG_READ1(long, "shmdt", const void *, shmaddr);
   1047   if (!ML_(generic_PRE_sys_shmdt)(tid, ARG1))
   1048     SET_STATUS_Failure( VKI_EINVAL );
   1049 }
   1050 POST(sys_shmdt)
   1051 {
   1052   ML_(generic_POST_sys_shmdt)(tid, RES,ARG1);
   1053 }
   1054 
   1055 PRE(sys_shmctl)
   1056 {
   1057   PRINT("sys_shmctl ( %ld, %ld, %#lx )",ARG1,ARG2,ARG3);
   1058   PRE_REG_READ3(long, "shmctl",
   1059                 int, shmid, int, cmd, struct shmid_ds *, buf);
   1060   ML_(generic_PRE_sys_shmctl)(tid, ARG1,ARG2|VKI_IPC_64,ARG3);
   1061 }
   1062 POST(sys_shmctl)
   1063 {
   1064   ML_(generic_POST_sys_shmctl)(tid, RES,ARG1,ARG2|VKI_IPC_64,ARG3);
   1065 }
   1066 
   1067 PRE(sys_fadvise64)
   1068 {
   1069   PRINT("sys_fadvise64 ( %ld, %ld, %lu, %ld )", ARG1,ARG2,ARG3,ARG4);
   1070   PRE_REG_READ4(long, "fadvise64",
   1071                 int, fd, vki_loff_t, offset, vki_size_t, len, int, advice);
   1072 }
   1073 
   1074 PRE(sys_mmap)
   1075 {
   1076   SysRes r;
   1077 
   1078   PRINT("sys_mmap ( %#lx, %llu, %ld, %ld, %d, %ld )",
   1079         ARG1, (ULong)ARG2, ARG3, ARG4, (Int)ARG5, ARG6 );
   1080   PRE_REG_READ6(long, "mmap",
   1081                 unsigned long, start, unsigned long, length,
   1082                 unsigned long, prot,  unsigned long, flags,
   1083                 unsigned long, fd,    unsigned long, offset);
   1084 
   1085   r = ML_(generic_PRE_sys_mmap)( tid, ARG1, ARG2, ARG3, ARG4, ARG5, ARG6 );
   1086   SET_STATUS_from_SysRes(r);
   1087 }
   1088 
   1089 
   1090 /* ---------------------------------------------------------------
   1091    PRE/POST wrappers for TILEGX/Linux-variant specific syscalls
   1092    ------------------------------------------------------------ */
   1093 PRE(sys_cacheflush)
   1094 {
   1095    PRINT("cacheflush (%lx, %lx, %lx)", ARG1, ARG2, ARG3);
   1096    PRE_REG_READ3(long, "cacheflush", unsigned long, addr,
   1097                  int, nbytes, int, cache);
   1098    VG_ (discard_translations) ((Addr)ARG1, (ULong) ARG2,
   1099                                "PRE(sys_cacheflush)");
   1100    SET_STATUS_Success(0);
   1101 }
   1102 
   1103 PRE(sys_set_dataplane)
   1104 {
   1105   *flags |= SfMayBlock;
   1106   PRINT("sys_set_dataplane ( %ld )", ARG1);
   1107   PRE_REG_READ1(long, "set_dataplane", unsigned long, flag);
   1108 }
   1109 
   1110 #undef PRE
   1111 #undef POST
   1112 
   1113 
   1114 /* ---------------------------------------------------------------------
   1115    The TILEGX/Linux syscall table
   1116    ------------------------------------------------------------------ */
   1117 
   1118 /* Add an tilegx-linux specific wrapper to a syscall table. */
   1119 #define PLAX_(const, name)    WRAPPER_ENTRY_X_(tilegx_linux, const, name)
   1120 #define PLAXY(const, name)    WRAPPER_ENTRY_XY(tilegx_linux, const, name)
   1121 
   1122 // This table maps from __NR_xxx syscall numbers (from
   1123 // linux/include/asm/unistd.h) to the appropriate PRE/POST sys_foo()
   1124 //
   1125 // When implementing these wrappers, you need to work out if the wrapper is
   1126 // generic, Linux-only (but arch-independent), or TILEGX/Linux only.
   1127 
   1128 static SyscallTableEntry syscall_table[] = {
   1129 
   1130   LINXY(__NR_io_setup,          sys_io_setup),             // 0
   1131   LINX_(__NR_io_destroy,        sys_io_destroy),           // 1
   1132   LINX_(__NR_io_submit,         sys_io_submit),            // 2
   1133   LINXY(__NR_io_cancel,         sys_io_cancel),            // 3
   1134   LINXY(__NR_io_getevents,      sys_io_getevents),         // 4
   1135   LINX_(__NR_setxattr,          sys_setxattr),             // 5
   1136   LINX_(__NR_lsetxattr,         sys_lsetxattr),            // 6
   1137   LINX_(__NR_fsetxattr,         sys_fsetxattr),            // 7
   1138   LINXY(__NR_getxattr,          sys_getxattr),             // 8
   1139   LINXY(__NR_lgetxattr,         sys_lgetxattr),            // 9
   1140   LINXY(__NR_fgetxattr,         sys_fgetxattr),            // 10
   1141   LINXY(__NR_listxattr,         sys_listxattr),            // 11
   1142   LINXY(__NR_llistxattr,        sys_llistxattr),           // 12
   1143   LINXY(__NR_flistxattr,        sys_flistxattr),           // 13
   1144   LINX_(__NR_removexattr,       sys_removexattr),          // 14
   1145   LINX_(__NR_lremovexattr,      sys_lremovexattr),         // 15
   1146   LINX_(__NR_fremovexattr,      sys_fremovexattr),         // 16
   1147   GENXY(__NR_getcwd,            sys_getcwd),               // 17
   1148   LINXY(__NR_lookup_dcookie,    sys_lookup_dcookie),       // 18
   1149   LINX_(__NR_eventfd2,          sys_eventfd2),             // 19
   1150   LINXY(__NR_epoll_create1,     sys_epoll_create1),        // 20
   1151   LINX_(__NR_epoll_ctl,         sys_epoll_ctl),            // 21
   1152   LINXY(__NR_epoll_pwait,       sys_epoll_pwait),          // 22
   1153   GENXY(__NR_dup,               sys_dup),                  // 23
   1154   GENXY(__NR_dup2,              sys_dup2),                 // 23
   1155   LINXY(__NR_dup3,              sys_dup3),                 // 24
   1156   LINXY(__NR_fcntl,             sys_fcntl),                // 25
   1157   LINXY(__NR_inotify_init1,     sys_inotify_init1),        // 26
   1158   LINX_(__NR_inotify_add_watch, sys_inotify_add_watch),    // 27
   1159   LINX_(__NR_inotify_rm_watch,  sys_inotify_rm_watch),     // 28
   1160   LINXY(__NR_ioctl,             sys_ioctl),                // 29
   1161   LINX_(__NR_ioprio_set,        sys_ioprio_set),           // 30
   1162   LINX_(__NR_ioprio_get,        sys_ioprio_get),           // 31
   1163   GENX_(__NR_flock,             sys_flock),                // 32
   1164   LINX_(__NR_mknodat,           sys_mknodat),              // 33
   1165   LINX_(__NR_mkdirat,           sys_mkdirat),              // 34
   1166   LINX_(__NR_unlinkat,          sys_unlinkat),             // 35
   1167   LINX_(__NR_symlinkat,         sys_symlinkat),            // 36
   1168   LINX_(__NR_linkat,            sys_linkat),               // 37
   1169   LINX_(__NR_renameat,          sys_renameat),             // 38
   1170   LINX_(__NR_umount2,           sys_umount),               // 39
   1171   LINX_(__NR_mount,             sys_mount),                // 40
   1172 
   1173   GENXY(__NR_statfs,            sys_statfs),               // 43
   1174   GENXY(__NR_fstatfs,           sys_fstatfs),              // 44
   1175   GENX_(__NR_truncate,          sys_truncate),             // 45
   1176   GENX_(__NR_ftruncate,         sys_ftruncate),            // 46
   1177   LINX_(__NR_fallocate,         sys_fallocate),            // 47
   1178   LINX_(__NR_faccessat,         sys_faccessat),            // 48
   1179   GENX_(__NR_chdir,             sys_chdir),                // 49
   1180   GENX_(__NR_fchdir,            sys_fchdir),               // 50
   1181   GENX_(__NR_chroot,            sys_chroot),               // 51
   1182   GENX_(__NR_fchmod,            sys_fchmod),               // 52
   1183   LINX_(__NR_fchmodat,          sys_fchmodat),             // 53
   1184   LINX_(__NR_fchownat,          sys_fchownat),             // 54
   1185   GENX_(__NR_fchown,            sys_fchown),               // 55
   1186   LINXY(__NR_openat,            sys_openat),               // 56
   1187   GENXY(__NR_close,             sys_close),                // 57
   1188   LINX_(__NR_vhangup,           sys_vhangup),              // 58
   1189   LINXY(__NR_pipe2,             sys_pipe2),                // 59
   1190   LINX_(__NR_quotactl,          sys_quotactl),             // 60
   1191   GENXY(__NR_getdents64,        sys_getdents64),           // 61
   1192   LINX_(__NR_lseek,             sys_lseek),                // 62
   1193   GENXY(__NR_read,              sys_read),                 // 63
   1194   GENX_(__NR_write,             sys_write),                // 64
   1195   GENXY(__NR_readv,             sys_readv),                // 65
   1196   GENX_(__NR_writev,            sys_writev),               // 66
   1197   GENXY(__NR_pread64,           sys_pread64),              // 67
   1198   GENX_(__NR_pwrite64,          sys_pwrite64),             // 68
   1199   LINXY(__NR_preadv,            sys_preadv),               // 69
   1200   LINX_(__NR_pwritev,           sys_pwritev),              // 70
   1201   LINXY(__NR_sendfile,          sys_sendfile),             // 71
   1202   LINX_(__NR_pselect6,          sys_pselect6),             // 72
   1203   LINXY(__NR_ppoll,             sys_ppoll),                // 73
   1204   LINXY(__NR_signalfd4,         sys_signalfd4),            // 74
   1205   LINX_(__NR_splice,            sys_splice),               // 75
   1206   LINX_(__NR_readlinkat,        sys_readlinkat),           // 78
   1207   LINXY(__NR3264_fstatat,       sys_newfstatat),           // 79
   1208   GENXY(__NR_fstat,             sys_newfstat),             // 80
   1209   GENX_(__NR_sync,              sys_sync),                 // 81
   1210   GENX_(__NR_fsync,             sys_fsync),                // 82
   1211   GENX_(__NR_fdatasync,         sys_fdatasync),            // 83
   1212   LINX_(__NR_sync_file_range,   sys_sync_file_range),      // 84
   1213   LINXY(__NR_timerfd_create,    sys_timerfd_create),       // 85
   1214   LINXY(__NR_timerfd_settime,   sys_timerfd_settime),      // 86
   1215   LINXY(__NR_timerfd_gettime,   sys_timerfd_gettime),      // 87
   1216   LINX_(__NR_utimensat,         sys_utimensat),            // 88
   1217 
   1218   LINXY(__NR_capget,            sys_capget),               // 90
   1219   LINX_(__NR_capset,            sys_capset),               // 91
   1220   LINX_(__NR_personality,       sys_personality),          // 92
   1221   GENX_(__NR_exit,              sys_exit),                 // 93
   1222   LINX_(__NR_exit_group,        sys_exit_group),           // 94
   1223   LINXY(__NR_waitid,            sys_waitid),               // 95
   1224   LINX_(__NR_set_tid_address,   sys_set_tid_address),      // 96
   1225   LINXY(__NR_futex,             sys_futex),                // 98
   1226   LINX_(__NR_set_robust_list,   sys_set_robust_list),      // 99
   1227   LINXY(__NR_get_robust_list,   sys_get_robust_list),      // 100
   1228   GENXY(__NR_nanosleep,         sys_nanosleep),            // 101
   1229   GENXY(__NR_getitimer,         sys_getitimer),            // 102
   1230   GENXY(__NR_setitimer,         sys_setitimer),            // 103
   1231   LINX_(__NR_init_module,       sys_init_module),          // 105
   1232   LINX_(__NR_delete_module,     sys_delete_module),        // 106
   1233   LINXY(__NR_timer_create,      sys_timer_create),         // 107
   1234   LINXY(__NR_timer_gettime,     sys_timer_gettime),        // 108
   1235   LINX_(__NR_timer_getoverrun,  sys_timer_getoverrun),     // 109
   1236   LINXY(__NR_timer_settime,     sys_timer_settime),        // 110
   1237   LINX_(__NR_timer_delete,      sys_timer_delete),         // 111
   1238   LINX_(__NR_clock_settime,     sys_clock_settime),        // 112
   1239   LINXY(__NR_clock_gettime,     sys_clock_gettime),        // 113
   1240   LINXY(__NR_clock_getres,      sys_clock_getres),         // 114
   1241   LINXY(__NR_clock_nanosleep,   sys_clock_nanosleep),      // 115
   1242   LINXY(__NR_syslog,            sys_syslog),               // 116
   1243   PLAXY(__NR_ptrace,            sys_ptrace),               // 117
   1244   LINXY(__NR_sched_setparam,          sys_sched_setparam), // 118
   1245   LINX_(__NR_sched_setscheduler,      sys_sched_setscheduler),     // 119
   1246   LINX_(__NR_sched_getscheduler,      sys_sched_getscheduler),     // 120
   1247   LINXY(__NR_sched_getparam,          sys_sched_getparam), // 121
   1248   LINX_(__NR_sched_setaffinity, sys_sched_setaffinity),    // 122
   1249   LINXY(__NR_sched_getaffinity, sys_sched_getaffinity),    // 123
   1250   LINX_(__NR_sched_yield,       sys_sched_yield),          // 124
   1251   LINX_(__NR_sched_get_priority_max,  sys_sched_get_priority_max), // 125
   1252   LINX_(__NR_sched_get_priority_min,  sys_sched_get_priority_min), // 126
   1253   LINXY(__NR_sched_rr_get_interval,   sys_sched_rr_get_interval),  // 127
   1254 
   1255   GENX_(__NR_kill,              sys_kill),                 // 129
   1256   LINXY(__NR_tkill,             sys_tkill),                // 130
   1257   LINXY(__NR_tgkill,            sys_tgkill),               // 131
   1258   GENXY(__NR_sigaltstack,       sys_sigaltstack),          // 132
   1259   LINX_(__NR_rt_sigsuspend,     sys_rt_sigsuspend),        // 133
   1260   LINXY(__NR_rt_sigaction,      sys_rt_sigaction),         // 134
   1261   LINXY(__NR_rt_sigprocmask,    sys_rt_sigprocmask),       // 135
   1262   LINXY(__NR_rt_sigpending,     sys_rt_sigpending),        // 136
   1263   LINXY(__NR_rt_sigtimedwait,   sys_rt_sigtimedwait),      // 137
   1264   LINXY(__NR_rt_sigqueueinfo,   sys_rt_sigqueueinfo),      // 138
   1265   PLAX_(__NR_rt_sigreturn,      sys_rt_sigreturn),         // 139
   1266   GENX_(__NR_setpriority,             sys_setpriority),    // 140
   1267   GENX_(__NR_getpriority,             sys_getpriority),    // 141
   1268 
   1269   GENX_(__NR_setregid,          sys_setregid),             // 143
   1270   GENX_(__NR_setgid,            sys_setgid),               // 144
   1271   GENX_(__NR_setreuid,          sys_setreuid),             // 145
   1272   GENX_(__NR_setuid,            sys_setuid),               // 146
   1273   LINX_(__NR_setresuid,         sys_setresuid),            // 147
   1274   LINXY(__NR_getresuid,         sys_getresuid),            // 148
   1275   LINX_(__NR_setresgid,         sys_setresgid),            // 149
   1276   LINXY(__NR_getresgid,         sys_getresgid),            // 150
   1277   LINX_(__NR_setfsuid,          sys_setfsuid),             // 151
   1278   LINX_(__NR_setfsgid,          sys_setfsgid),             // 152
   1279   GENXY(__NR_times,             sys_times),                // 153
   1280   GENX_(__NR_setpgid,           sys_setpgid),              // 154
   1281   GENX_(__NR_getpgid,           sys_getpgid),              // 155
   1282   GENX_(__NR_getsid,            sys_getsid),               // 156
   1283   GENX_(__NR_setsid,            sys_setsid),               // 157
   1284   GENXY(__NR_getgroups,         sys_getgroups),            // 158
   1285   GENX_(__NR_setgroups,         sys_setgroups),            // 159
   1286   GENXY(__NR_uname,             sys_newuname),             // 160
   1287   GENXY(__NR_getrlimit,         sys_getrlimit),            // 163
   1288   GENX_(__NR_setrlimit,         sys_setrlimit),            // 164
   1289   GENXY(__NR_getrusage,         sys_getrusage),            // 165
   1290   GENX_(__NR_umask,             sys_umask),                // 166
   1291   LINXY(__NR_prctl,             sys_prctl),                // 167
   1292 
   1293   GENXY(__NR_gettimeofday,      sys_gettimeofday),         // 169
   1294   GENX_(__NR_settimeofday,      sys_settimeofday),         // 170
   1295   LINXY(__NR_adjtimex,          sys_adjtimex),             // 171
   1296   GENX_(__NR_getpid,            sys_getpid),               // 172
   1297   GENX_(__NR_getppid,           sys_getppid),              // 173
   1298   GENX_(__NR_getuid,            sys_getuid),               // 174
   1299   GENX_(__NR_geteuid,           sys_geteuid),              // 175
   1300   GENX_(__NR_getgid,            sys_getgid),               // 176
   1301   GENX_(__NR_getegid,           sys_getegid),              // 177
   1302   LINX_(__NR_gettid,            sys_gettid),               // 178
   1303   LINXY(__NR_sysinfo,           sys_sysinfo),              // 179
   1304   LINXY(__NR_mq_open,           sys_mq_open),              // 180
   1305   LINX_(__NR_mq_unlink,         sys_mq_unlink),            // 181
   1306   LINX_(__NR_mq_timedsend,      sys_mq_timedsend),         // 182
   1307   LINXY(__NR_mq_timedreceive,   sys_mq_timedreceive),      // 183
   1308   LINX_(__NR_mq_notify,         sys_mq_notify),            // 184
   1309   LINXY(__NR_mq_getsetattr,     sys_mq_getsetattr),        // 185
   1310   PLAX_(__NR_msgget,            sys_msgget),               // 186
   1311   PLAXY(__NR_msgctl,            sys_msgctl),               // 187
   1312   PLAXY(__NR_msgrcv,            sys_msgrcv),               // 188
   1313   PLAX_(__NR_msgsnd,            sys_msgsnd),               // 189
   1314   PLAX_(__NR_semget,            sys_semget),               // 190
   1315   PLAXY(__NR_semctl,            sys_semctl),               // 191
   1316   PLAX_(__NR_semtimedop,        sys_semtimedop),           // 192
   1317   PLAX_(__NR_semop,             sys_semop),                // 193
   1318   PLAX_(__NR_shmget,            sys_shmget),               // 194
   1319   PLAXY(__NR_shmat,             wrap_sys_shmat),           // 196
   1320   PLAXY(__NR_shmctl,            sys_shmctl),               // 195
   1321   PLAXY(__NR_shmdt,             sys_shmdt),                // 197
   1322   PLAXY(__NR_socket,            sys_socket),               // 198
   1323   PLAXY(__NR_socketpair,        sys_socketpair),           // 199
   1324   PLAX_(__NR_bind,              sys_bind),                 // 200
   1325   PLAX_(__NR_listen,            sys_listen),               // 201
   1326   PLAXY(__NR_accept,            sys_accept),               // 202
   1327   PLAX_(__NR_connect,           sys_connect),              // 203
   1328   PLAXY(__NR_getsockname,       sys_getsockname),          // 204
   1329   PLAXY(__NR_getpeername,       sys_getpeername),          // 205
   1330   PLAX_(__NR_sendto,            sys_sendto),               // 206
   1331   PLAXY(__NR_recvfrom,          sys_recvfrom),             // 207
   1332   PLAX_(__NR_setsockopt,        sys_setsockopt),           // 208
   1333   PLAXY(__NR_getsockopt,        sys_getsockopt),           // 209
   1334   PLAX_(__NR_shutdown,          sys_shutdown),             // 210
   1335   PLAX_(__NR_sendmsg,           sys_sendmsg),              // 211
   1336   PLAXY(__NR_recvmsg,           sys_recvmsg),              // 212
   1337   LINX_(__NR_readahead,         sys_readahead),            // 213
   1338   GENX_(__NR_brk,               sys_brk),                  // 214
   1339   GENXY(__NR_munmap,            sys_munmap),               // 215
   1340   GENX_(__NR_mremap,            sys_mremap),               // 216
   1341   LINX_(__NR_add_key,           sys_add_key),              // 217
   1342   LINX_(__NR_request_key,       sys_request_key),          // 218
   1343   LINXY(__NR_keyctl,            sys_keyctl),               // 219
   1344   PLAX_(__NR_clone,             sys_clone),                // 220
   1345   GENX_(__NR_execve,            sys_execve),               // 221
   1346   PLAX_(__NR_mmap,              sys_mmap),                 // 222
   1347   GENXY(__NR_mprotect,          sys_mprotect),             // 226
   1348   GENX_(__NR_msync,             sys_msync),                // 227
   1349   GENX_(__NR_mlock,                   sys_mlock),          // 228
   1350   GENX_(__NR_munlock,           sys_munlock),              // 229
   1351   GENX_(__NR_mlockall,          sys_mlockall),             // 230
   1352   LINX_(__NR_munlockall,        sys_munlockall),           // 231
   1353   GENX_(__NR_mincore,           sys_mincore),              // 232
   1354   GENX_(__NR_madvise,           sys_madvise),              // 233
   1355 
   1356   LINX_(__NR_mbind,             sys_mbind),                // 235
   1357   LINXY(__NR_get_mempolicy,     sys_get_mempolicy),        // 236
   1358   LINX_(__NR_set_mempolicy,     sys_set_mempolicy),        // 237
   1359 
   1360   LINXY(__NR_rt_tgsigqueueinfo, sys_rt_tgsigqueueinfo),    // 240
   1361 
   1362   PLAXY(__NR_accept4,           sys_accept4),              // 242
   1363 
   1364   PLAX_(__NR_cacheflush,        sys_cacheflush),           // 245
   1365   PLAX_(__NR_set_dataplane,     sys_set_dataplane),        // 246
   1366 
   1367   GENXY(__NR_wait4,             sys_wait4),                // 260
   1368 };
   1369 
   1370 SyscallTableEntry* ML_(get_linux_syscall_entry) ( UInt sysno )
   1371 {
   1372   const UInt syscall_table_size
   1373     = sizeof(syscall_table) / sizeof(syscall_table[0]);
   1374 
   1375   /* Is it in the contiguous initial section of the table? */
   1376   if (sysno < syscall_table_size) {
   1377     SyscallTableEntry* sys = &syscall_table[sysno];
   1378     if (sys->before == NULL)
   1379       return NULL; /* no entry */
   1380     else
   1381       return sys;
   1382   }
   1383   //vex_printf("sysno: %d\n", sysno);
   1384 
   1385   /* Can't find a wrapper */
   1386   return NULL;
   1387 }
   1388 
   1389 #endif // defined(VGP_tilegx_linux)
   1390 
   1391 /*--------------------------------------------------------------------*/
   1392 /*--- end                                   syswrap-tilegx-linux.c ---*/
   1393 /*--------------------------------------------------------------------*/
   1394