Home | History | Annotate | Download | only in m_syswrap
      1 
      2 /*--------------------------------------------------------------------*/
      3 /*--- Linux-specific syscalls, etc.                syswrap-linux.c ---*/
      4 /*--------------------------------------------------------------------*/
      5 
      6 /*
      7    This file is part of Valgrind, a dynamic binary instrumentation
      8    framework.
      9 
     10    Copyright (C) 2000-2010 Nicholas Nethercote
     11       njn (at) valgrind.org
     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(VGO_linux)
     32 
     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_debuginfo.h"    // VG_(di_notify_*)
     39 #include "pub_core_transtab.h"     // VG_(discard_translations)
     40 #include "pub_core_xarray.h"
     41 #include "pub_core_clientstate.h"
     42 #include "pub_core_debuglog.h"
     43 #include "pub_core_libcbase.h"
     44 #include "pub_core_libcassert.h"
     45 #include "pub_core_libcfile.h"
     46 #include "pub_core_libcprint.h"
     47 #include "pub_core_libcproc.h"
     48 #include "pub_core_libcsignal.h"
     49 #include "pub_core_mallocfree.h"
     50 #include "pub_core_tooliface.h"
     51 #include "pub_core_options.h"
     52 #include "pub_core_scheduler.h"
     53 #include "pub_core_signals.h"
     54 #include "pub_core_syscall.h"
     55 #include "pub_core_syswrap.h"
     56 
     57 #include "priv_types_n_macros.h"
     58 #include "priv_syswrap-generic.h"
     59 #include "priv_syswrap-linux.h"
     60 
     61 
     62 // Run a thread from beginning to end and return the thread's
     63 // scheduler-return-code.
     64 static VgSchedReturnCode thread_wrapper(Word /*ThreadId*/ tidW)
     65 {
     66    VgSchedReturnCode ret;
     67    ThreadId     tid = (ThreadId)tidW;
     68    ThreadState* tst = VG_(get_ThreadState)(tid);
     69 
     70    VG_(debugLog)(1, "syswrap-linux",
     71                     "thread_wrapper(tid=%lld): entry\n",
     72                     (ULong)tidW);
     73 
     74    vg_assert(tst->status == VgTs_Init);
     75 
     76    /* make sure we get the CPU lock before doing anything significant */
     77    VG_(acquire_BigLock)(tid, "thread_wrapper(starting new thread)");
     78 
     79    if (0)
     80       VG_(printf)("thread tid %d started: stack = %p\n",
     81 		  tid, &tid);
     82 
     83    VG_TRACK(pre_thread_first_insn, tid);
     84 
     85    tst->os_state.lwpid = VG_(gettid)();
     86    /* Set the threadgroup for real.  This overwrites the provisional
     87       value set in do_clone() syswrap-*-linux.c.  See comments in
     88       do_clone for background, also #226116. */
     89    tst->os_state.threadgroup = VG_(getpid)();
     90 
     91    /* Thread created with all signals blocked; scheduler will set the
     92       appropriate mask */
     93 
     94    ret = VG_(scheduler)(tid);
     95 
     96    vg_assert(VG_(is_exiting)(tid));
     97 
     98    vg_assert(tst->status == VgTs_Runnable);
     99    vg_assert(VG_(is_running_thread)(tid));
    100 
    101    VG_(debugLog)(1, "syswrap-linux",
    102                     "thread_wrapper(tid=%lld): exit\n",
    103                     (ULong)tidW);
    104 
    105    /* Return to caller, still holding the lock. */
    106    return ret;
    107 }
    108 
    109 
    110 /* ---------------------------------------------------------------------
    111    clone-related stuff
    112    ------------------------------------------------------------------ */
    113 
    114 /* Run a thread all the way to the end, then do appropriate exit actions
    115    (this is the last-one-out-turn-off-the-lights bit).  */
    116 static void run_a_thread_NORETURN ( Word tidW )
    117 {
    118    ThreadId          tid = (ThreadId)tidW;
    119    VgSchedReturnCode src;
    120    Int               c;
    121 
    122    VG_(debugLog)(1, "syswrap-linux",
    123                     "run_a_thread_NORETURN(tid=%lld): pre-thread_wrapper\n",
    124                     (ULong)tidW);
    125 
    126    /* Run the thread all the way through. */
    127    src = thread_wrapper(tid);
    128 
    129    VG_(debugLog)(1, "syswrap-linux",
    130                     "run_a_thread_NORETURN(tid=%lld): post-thread_wrapper\n",
    131                     (ULong)tidW);
    132 
    133    c = VG_(count_living_threads)();
    134    vg_assert(c >= 1); /* stay sane */
    135 
    136    // Tell the tool this thread is exiting
    137    VG_TRACK( pre_thread_ll_exit, tid );
    138 
    139    if (c == 1) {
    140 
    141       VG_(debugLog)(1, "syswrap-linux",
    142                        "run_a_thread_NORETURN(tid=%lld): "
    143                           "last one standing\n",
    144                           (ULong)tidW);
    145 
    146       /* We are the last one standing.  Keep hold of the lock and
    147          carry on to show final tool results, then exit the entire system.
    148          Use the continuation pointer set at startup in m_main. */
    149       ( * VG_(address_of_m_main_shutdown_actions_NORETURN) ) (tid, src);
    150 
    151    } else {
    152 
    153       ThreadState *tst;
    154 
    155       VG_(debugLog)(1, "syswrap-linux",
    156                        "run_a_thread_NORETURN(tid=%lld): "
    157                           "not last one standing\n",
    158                           (ULong)tidW);
    159 
    160       /* OK, thread is dead, but others still exist.  Just exit. */
    161       tst = VG_(get_ThreadState)(tid);
    162 
    163       /* This releases the run lock */
    164       VG_(exit_thread)(tid);
    165       vg_assert(tst->status == VgTs_Zombie);
    166 
    167       /* We have to use this sequence to terminate the thread to
    168          prevent a subtle race.  If VG_(exit_thread)() had left the
    169          ThreadState as Empty, then it could have been reallocated,
    170          reusing the stack while we're doing these last cleanups.
    171          Instead, VG_(exit_thread) leaves it as Zombie to prevent
    172          reallocation.  We need to make sure we don't touch the stack
    173          between marking it Empty and exiting.  Hence the
    174          assembler. */
    175 #if defined(VGP_x86_linux)
    176       asm volatile (
    177          "movl	%1, %0\n"	/* set tst->status = VgTs_Empty */
    178          "movl	%2, %%eax\n"    /* set %eax = __NR_exit */
    179          "movl	%3, %%ebx\n"    /* set %ebx = tst->os_state.exitcode */
    180          "int	$0x80\n"	/* exit(tst->os_state.exitcode) */
    181          : "=m" (tst->status)
    182          : "n" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode));
    183 #elif defined(VGP_amd64_linux)
    184       asm volatile (
    185          "movl	%1, %0\n"	/* set tst->status = VgTs_Empty */
    186          "movq	%2, %%rax\n"    /* set %rax = __NR_exit */
    187          "movq	%3, %%rdi\n"    /* set %rdi = tst->os_state.exitcode */
    188          "syscall\n"		/* exit(tst->os_state.exitcode) */
    189          : "=m" (tst->status)
    190          : "n" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode));
    191 #elif defined(VGP_ppc32_linux) || defined(VGP_ppc64_linux)
    192       { UInt vgts_empty = (UInt)VgTs_Empty;
    193         asm volatile (
    194           "stw %1,%0\n\t"          /* set tst->status = VgTs_Empty */
    195           "li  0,%2\n\t"           /* set r0 = __NR_exit */
    196           "lwz 3,%3\n\t"           /* set r3 = tst->os_state.exitcode */
    197           "sc\n\t"                 /* exit(tst->os_state.exitcode) */
    198           : "=m" (tst->status)
    199           : "r" (vgts_empty), "n" (__NR_exit), "m" (tst->os_state.exitcode));
    200       }
    201 #elif defined(VGP_arm_linux)
    202       asm volatile (
    203          "str  %1, %0\n"      /* set tst->status = VgTs_Empty */
    204          "mov  r7, %2\n"      /* set %r7 = __NR_exit */
    205          "ldr  r0, %3\n"      /* set %r0 = tst->os_state.exitcode */
    206          "svc  0x00000000\n"  /* exit(tst->os_state.exitcode) */
    207          : "=m" (tst->status)
    208          : "r" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode));
    209 #else
    210 # error Unknown platform
    211 #endif
    212 
    213       VG_(core_panic)("Thread exit failed?\n");
    214    }
    215 
    216    /*NOTREACHED*/
    217    vg_assert(0);
    218 }
    219 
    220 Word ML_(start_thread_NORETURN) ( void* arg )
    221 {
    222    ThreadState* tst = (ThreadState*)arg;
    223    ThreadId     tid = tst->tid;
    224 
    225    run_a_thread_NORETURN ( (Word)tid );
    226    /*NOTREACHED*/
    227    vg_assert(0);
    228 }
    229 
    230 /* Allocate a stack for this thread, if it doesn't already have one.
    231    They're allocated lazily, and never freed.  Returns the initial stack
    232    pointer value to use, or 0 if allocation failed. */
    233 Addr ML_(allocstack)(ThreadId tid)
    234 {
    235    ThreadState* tst = VG_(get_ThreadState)(tid);
    236    VgStack*     stack;
    237    Addr         initial_SP;
    238 
    239    /* Either the stack_base and stack_init_SP are both zero (in which
    240       case a stack hasn't been allocated) or they are both non-zero,
    241       in which case it has. */
    242 
    243    if (tst->os_state.valgrind_stack_base == 0)
    244       vg_assert(tst->os_state.valgrind_stack_init_SP == 0);
    245 
    246    if (tst->os_state.valgrind_stack_base != 0)
    247       vg_assert(tst->os_state.valgrind_stack_init_SP != 0);
    248 
    249    /* If no stack is present, allocate one. */
    250 
    251    if (tst->os_state.valgrind_stack_base == 0) {
    252       stack = VG_(am_alloc_VgStack)( &initial_SP );
    253       if (stack) {
    254          tst->os_state.valgrind_stack_base    = (Addr)stack;
    255          tst->os_state.valgrind_stack_init_SP = initial_SP;
    256       }
    257    }
    258 
    259    if (0)
    260       VG_(printf)( "stack for tid %d at %p; init_SP=%p\n",
    261                    tid,
    262                    (void*)tst->os_state.valgrind_stack_base,
    263                    (void*)tst->os_state.valgrind_stack_init_SP );
    264 
    265    return tst->os_state.valgrind_stack_init_SP;
    266 }
    267 
    268 /* Allocate a stack for the main thread, and run it all the way to the
    269    end.  Although we already have a working VgStack
    270    (VG_(interim_stack)) it's better to allocate a new one, so that
    271    overflow detection works uniformly for all threads.
    272 */
    273 void VG_(main_thread_wrapper_NORETURN)(ThreadId tid)
    274 {
    275    Addr sp;
    276    VG_(debugLog)(1, "syswrap-linux",
    277                     "entering VG_(main_thread_wrapper_NORETURN)\n");
    278 
    279    sp = ML_(allocstack)(tid);
    280 
    281 #if defined(VGP_ppc32_linux)
    282    /* make a stack frame */
    283    sp -= 16;
    284    sp &= ~0xF;
    285    *(UWord *)sp = 0;
    286 #elif defined(VGP_ppc64_linux)
    287    /* make a stack frame */
    288    sp -= 112;
    289    sp &= ~((Addr)0xF);
    290    *(UWord *)sp = 0;
    291 #endif
    292 
    293    /* If we can't even allocate the first thread's stack, we're hosed.
    294       Give up. */
    295    vg_assert2(sp != 0, "Cannot allocate main thread's stack.");
    296 
    297    /* shouldn't be any other threads around yet */
    298    vg_assert( VG_(count_living_threads)() == 1 );
    299 
    300    ML_(call_on_new_stack_0_1)(
    301       (Addr)sp,               /* stack */
    302       0,                      /* bogus return address */
    303       run_a_thread_NORETURN,  /* fn to call */
    304       (Word)tid               /* arg to give it */
    305    );
    306 
    307    /*NOTREACHED*/
    308    vg_assert(0);
    309 }
    310 
    311 
    312 /* Do a clone which is really a fork() */
    313 SysRes ML_(do_fork_clone) ( ThreadId tid, UInt flags,
    314                             Int* parent_tidptr, Int* child_tidptr )
    315 {
    316    vki_sigset_t fork_saved_mask;
    317    vki_sigset_t mask;
    318    SysRes       res;
    319 
    320    if (flags & (VKI_CLONE_SETTLS | VKI_CLONE_FS | VKI_CLONE_VM
    321                 | VKI_CLONE_FILES | VKI_CLONE_VFORK))
    322       return VG_(mk_SysRes_Error)( VKI_EINVAL );
    323 
    324    /* Block all signals during fork, so that we can fix things up in
    325       the child without being interrupted. */
    326    VG_(sigfillset)(&mask);
    327    VG_(sigprocmask)(VKI_SIG_SETMASK, &mask, &fork_saved_mask);
    328 
    329    VG_(do_atfork_pre)(tid);
    330 
    331    /* Since this is the fork() form of clone, we don't need all that
    332       VG_(clone) stuff */
    333 #if defined(VGP_x86_linux) \
    334     || defined(VGP_ppc32_linux) || defined(VGP_ppc64_linux) \
    335     || defined(VGP_arm_linux)
    336    res = VG_(do_syscall5)( __NR_clone, flags,
    337                            (UWord)NULL, (UWord)parent_tidptr,
    338                            (UWord)NULL, (UWord)child_tidptr );
    339 #elif defined(VGP_amd64_linux)
    340    /* note that the last two arguments are the opposite way round to x86 and
    341       ppc32 as the amd64 kernel expects the arguments in a different order */
    342    res = VG_(do_syscall5)( __NR_clone, flags,
    343                            (UWord)NULL, (UWord)parent_tidptr,
    344                            (UWord)child_tidptr, (UWord)NULL );
    345 #else
    346 # error Unknown platform
    347 #endif
    348 
    349    if (!sr_isError(res) && sr_Res(res) == 0) {
    350       /* child */
    351       VG_(do_atfork_child)(tid);
    352 
    353       /* restore signal mask */
    354       VG_(sigprocmask)(VKI_SIG_SETMASK, &fork_saved_mask, NULL);
    355 
    356       /* If --child-silent-after-fork=yes was specified, set the
    357          output file descriptors to 'impossible' values.  This is
    358          noticed by send_bytes_to_logging_sink in m_libcprint.c, which
    359          duly stops writing any further output. */
    360       if (VG_(clo_child_silent_after_fork)) {
    361          if (!VG_(log_output_sink).is_socket)
    362             VG_(log_output_sink).fd = -1;
    363          if (!VG_(xml_output_sink).is_socket)
    364             VG_(xml_output_sink).fd = -1;
    365       }
    366    }
    367    else
    368    if (!sr_isError(res) && sr_Res(res) > 0) {
    369       /* parent */
    370       VG_(do_atfork_parent)(tid);
    371 
    372       if (VG_(clo_trace_syscalls))
    373 	  VG_(printf)("   clone(fork): process %d created child %ld\n",
    374                       VG_(getpid)(), sr_Res(res));
    375 
    376       /* restore signal mask */
    377       VG_(sigprocmask)(VKI_SIG_SETMASK, &fork_saved_mask, NULL);
    378    }
    379 
    380    return res;
    381 }
    382 
    383 
    384 /* ---------------------------------------------------------------------
    385    PRE/POST wrappers for arch-generic, Linux-specific syscalls
    386    ------------------------------------------------------------------ */
    387 
    388 // Nb: See the comment above the generic PRE/POST wrappers in
    389 // m_syswrap/syswrap-generic.c for notes about how they work.
    390 
    391 #define PRE(name)       DEFN_PRE_TEMPLATE(linux, name)
    392 #define POST(name)      DEFN_POST_TEMPLATE(linux, name)
    393 
    394 // Macros to support 64-bit syscall args split into two 32 bit values
    395 #define LOHI64(lo,hi)   ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
    396 #if defined(VG_LITTLEENDIAN)
    397 #define MERGE64(lo,hi)   ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
    398 #define MERGE64_FIRST(name) name##_low
    399 #define MERGE64_SECOND(name) name##_high
    400 #elif defined(VG_BIGENDIAN)
    401 #define MERGE64(hi,lo)   ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
    402 #define MERGE64_FIRST(name) name##_high
    403 #define MERGE64_SECOND(name) name##_low
    404 #else
    405 #error Unknown endianness
    406 #endif
    407 
    408 /* ---------------------------------------------------------------------
    409    *mount wrappers
    410    ------------------------------------------------------------------ */
    411 
    412 PRE(sys_mount)
    413 {
    414    // Nb: depending on 'flags', the 'type' and 'data' args may be ignored.
    415    // We are conservative and check everything, except the memory pointed to
    416    // by 'data'.
    417    *flags |= SfMayBlock;
    418    PRINT("sys_mount( %#lx(%s), %#lx(%s), %#lx(%s), %#lx, %#lx )",
    419          ARG1,(Char*)ARG1, ARG2,(Char*)ARG2, ARG3,(Char*)ARG3, ARG4, ARG5);
    420    PRE_REG_READ5(long, "mount",
    421                  char *, source, char *, target, char *, type,
    422                  unsigned long, flags, void *, data);
    423    if (ARG1)
    424       PRE_MEM_RASCIIZ( "mount(source)", ARG1);
    425    PRE_MEM_RASCIIZ( "mount(target)", ARG2);
    426    PRE_MEM_RASCIIZ( "mount(type)", ARG3);
    427 }
    428 
    429 PRE(sys_oldumount)
    430 {
    431    PRINT("sys_oldumount( %#lx )", ARG1);
    432    PRE_REG_READ1(long, "umount", char *, path);
    433    PRE_MEM_RASCIIZ( "umount(path)", ARG1);
    434 }
    435 
    436 PRE(sys_umount)
    437 {
    438    PRINT("sys_umount( %#lx, %ld )", ARG1, ARG2);
    439    PRE_REG_READ2(long, "umount2", char *, path, int, flags);
    440    PRE_MEM_RASCIIZ( "umount2(path)", ARG1);
    441 }
    442 
    443 /* ---------------------------------------------------------------------
    444    16- and 32-bit uid/gid wrappers
    445    ------------------------------------------------------------------ */
    446 
    447 PRE(sys_setfsuid16)
    448 {
    449    PRINT("sys_setfsuid16 ( %ld )", ARG1);
    450    PRE_REG_READ1(long, "setfsuid16", vki_old_uid_t, uid);
    451 }
    452 
    453 PRE(sys_setfsuid)
    454 {
    455    PRINT("sys_setfsuid ( %ld )", ARG1);
    456    PRE_REG_READ1(long, "setfsuid", vki_uid_t, uid);
    457 }
    458 
    459 PRE(sys_setfsgid16)
    460 {
    461    PRINT("sys_setfsgid16 ( %ld )", ARG1);
    462    PRE_REG_READ1(long, "setfsgid16", vki_old_gid_t, gid);
    463 }
    464 
    465 PRE(sys_setfsgid)
    466 {
    467    PRINT("sys_setfsgid ( %ld )", ARG1);
    468    PRE_REG_READ1(long, "setfsgid", vki_gid_t, gid);
    469 }
    470 
    471 PRE(sys_setresuid16)
    472 {
    473    PRINT("sys_setresuid16 ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
    474    PRE_REG_READ3(long, "setresuid16",
    475                  vki_old_uid_t, ruid, vki_old_uid_t, euid, vki_old_uid_t, suid);
    476 }
    477 
    478 PRE(sys_setresuid)
    479 {
    480    PRINT("sys_setresuid ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
    481    PRE_REG_READ3(long, "setresuid",
    482                  vki_uid_t, ruid, vki_uid_t, euid, vki_uid_t, suid);
    483 }
    484 
    485 PRE(sys_getresuid16)
    486 {
    487    PRINT("sys_getresuid16 ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
    488    PRE_REG_READ3(long, "getresuid16",
    489                  vki_old_uid_t *, ruid, vki_old_uid_t *, euid,
    490                  vki_old_uid_t *, suid);
    491    PRE_MEM_WRITE( "getresuid16(ruid)", ARG1, sizeof(vki_old_uid_t) );
    492    PRE_MEM_WRITE( "getresuid16(euid)", ARG2, sizeof(vki_old_uid_t) );
    493    PRE_MEM_WRITE( "getresuid16(suid)", ARG3, sizeof(vki_old_uid_t) );
    494 }
    495 POST(sys_getresuid16)
    496 {
    497    vg_assert(SUCCESS);
    498    if (RES == 0) {
    499       POST_MEM_WRITE( ARG1, sizeof(vki_old_uid_t) );
    500       POST_MEM_WRITE( ARG2, sizeof(vki_old_uid_t) );
    501       POST_MEM_WRITE( ARG3, sizeof(vki_old_uid_t) );
    502    }
    503 }
    504 
    505 PRE(sys_getresuid)
    506 {
    507    PRINT("sys_getresuid ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
    508    PRE_REG_READ3(long, "getresuid",
    509                  vki_uid_t *, ruid, vki_uid_t *, euid, vki_uid_t *, suid);
    510    PRE_MEM_WRITE( "getresuid(ruid)", ARG1, sizeof(vki_uid_t) );
    511    PRE_MEM_WRITE( "getresuid(euid)", ARG2, sizeof(vki_uid_t) );
    512    PRE_MEM_WRITE( "getresuid(suid)", ARG3, sizeof(vki_uid_t) );
    513 }
    514 POST(sys_getresuid)
    515 {
    516    vg_assert(SUCCESS);
    517    if (RES == 0) {
    518       POST_MEM_WRITE( ARG1, sizeof(vki_uid_t) );
    519       POST_MEM_WRITE( ARG2, sizeof(vki_uid_t) );
    520       POST_MEM_WRITE( ARG3, sizeof(vki_uid_t) );
    521    }
    522 }
    523 
    524 PRE(sys_setresgid16)
    525 {
    526    PRINT("sys_setresgid16 ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
    527    PRE_REG_READ3(long, "setresgid16",
    528                  vki_old_gid_t, rgid,
    529                  vki_old_gid_t, egid, vki_old_gid_t, sgid);
    530 }
    531 
    532 PRE(sys_setresgid)
    533 {
    534    PRINT("sys_setresgid ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
    535    PRE_REG_READ3(long, "setresgid",
    536                  vki_gid_t, rgid, vki_gid_t, egid, vki_gid_t, sgid);
    537 }
    538 
    539 PRE(sys_getresgid16)
    540 {
    541    PRINT("sys_getresgid16 ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
    542    PRE_REG_READ3(long, "getresgid16",
    543                  vki_old_gid_t *, rgid, vki_old_gid_t *, egid,
    544                  vki_old_gid_t *, sgid);
    545    PRE_MEM_WRITE( "getresgid16(rgid)", ARG1, sizeof(vki_old_gid_t) );
    546    PRE_MEM_WRITE( "getresgid16(egid)", ARG2, sizeof(vki_old_gid_t) );
    547    PRE_MEM_WRITE( "getresgid16(sgid)", ARG3, sizeof(vki_old_gid_t) );
    548 }
    549 POST(sys_getresgid16)
    550 {
    551    vg_assert(SUCCESS);
    552    if (RES == 0) {
    553       POST_MEM_WRITE( ARG1, sizeof(vki_old_gid_t) );
    554       POST_MEM_WRITE( ARG2, sizeof(vki_old_gid_t) );
    555       POST_MEM_WRITE( ARG3, sizeof(vki_old_gid_t) );
    556    }
    557 }
    558 
    559 PRE(sys_getresgid)
    560 {
    561    PRINT("sys_getresgid ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
    562    PRE_REG_READ3(long, "getresgid",
    563                  vki_gid_t *, rgid, vki_gid_t *, egid, vki_gid_t *, sgid);
    564    PRE_MEM_WRITE( "getresgid(rgid)", ARG1, sizeof(vki_gid_t) );
    565    PRE_MEM_WRITE( "getresgid(egid)", ARG2, sizeof(vki_gid_t) );
    566    PRE_MEM_WRITE( "getresgid(sgid)", ARG3, sizeof(vki_gid_t) );
    567 }
    568 POST(sys_getresgid)
    569 {
    570    vg_assert(SUCCESS);
    571    if (RES == 0) {
    572       POST_MEM_WRITE( ARG1, sizeof(vki_gid_t) );
    573       POST_MEM_WRITE( ARG2, sizeof(vki_gid_t) );
    574       POST_MEM_WRITE( ARG3, sizeof(vki_gid_t) );
    575    }
    576 }
    577 
    578 /* ---------------------------------------------------------------------
    579    miscellaneous wrappers
    580    ------------------------------------------------------------------ */
    581 
    582 PRE(sys_exit_group)
    583 {
    584    ThreadId     t;
    585    ThreadState* tst;
    586 
    587    PRINT("exit_group( %ld )", ARG1);
    588    PRE_REG_READ1(void, "exit_group", int, status);
    589 
    590    tst = VG_(get_ThreadState)(tid);
    591 
    592    /* A little complex; find all the threads with the same threadgroup
    593       as this one (including this one), and mark them to exit */
    594    for (t = 1; t < VG_N_THREADS; t++) {
    595       if ( /* not alive */
    596            VG_(threads)[t].status == VgTs_Empty
    597            ||
    598 	   /* not our group */
    599            VG_(threads)[t].os_state.threadgroup != tst->os_state.threadgroup
    600          )
    601          continue;
    602 
    603       VG_(threads)[t].exitreason = VgSrc_ExitThread;
    604       VG_(threads)[t].os_state.exitcode = ARG1;
    605 
    606       if (t != tid)
    607 	 VG_(get_thread_out_of_syscall)(t); /* unblock it, if blocked */
    608    }
    609 
    610    /* We have to claim the syscall already succeeded. */
    611    SET_STATUS_Success(0);
    612 }
    613 
    614 PRE(sys_llseek)
    615 {
    616    PRINT("sys_llseek ( %ld, 0x%lx, 0x%lx, %#lx, %ld )", ARG1,ARG2,ARG3,ARG4,ARG5);
    617    PRE_REG_READ5(long, "llseek",
    618                  unsigned int, fd, unsigned long, offset_high,
    619                  unsigned long, offset_low, vki_loff_t *, result,
    620                  unsigned int, whence);
    621    if (!ML_(fd_allowed)(ARG1, "llseek", tid, False))
    622       SET_STATUS_Failure( VKI_EBADF );
    623    else
    624       PRE_MEM_WRITE( "llseek(result)", ARG4, sizeof(vki_loff_t));
    625 }
    626 POST(sys_llseek)
    627 {
    628    vg_assert(SUCCESS);
    629    if (RES == 0)
    630       POST_MEM_WRITE( ARG4, sizeof(vki_loff_t) );
    631 }
    632 
    633 PRE(sys_adjtimex)
    634 {
    635    struct vki_timex *tx = (struct vki_timex *)ARG1;
    636    PRINT("sys_adjtimex ( %#lx )", ARG1);
    637    PRE_REG_READ1(long, "adjtimex", struct timex *, buf);
    638    PRE_MEM_READ( "adjtimex(timex->modes)", ARG1, sizeof(tx->modes));
    639 
    640 #define ADJX(bits,field) 				\
    641    if (tx->modes & (bits))                              \
    642       PRE_MEM_READ( "adjtimex(timex->"#field")",	\
    643 		    (Addr)&tx->field, sizeof(tx->field))
    644 
    645    if (tx->modes & VKI_ADJ_ADJTIME) {
    646       if (!(tx->modes & VKI_ADJ_OFFSET_READONLY))
    647          PRE_MEM_READ( "adjtimex(timex->offset)", (Addr)&tx->offset, sizeof(tx->offset));
    648    } else {
    649       ADJX(VKI_ADJ_OFFSET, offset);
    650       ADJX(VKI_ADJ_FREQUENCY, freq);
    651       ADJX(VKI_ADJ_MAXERROR, maxerror);
    652       ADJX(VKI_ADJ_ESTERROR, esterror);
    653       ADJX(VKI_ADJ_STATUS, status);
    654       ADJX(VKI_ADJ_TIMECONST|VKI_ADJ_TAI, constant);
    655       ADJX(VKI_ADJ_TICK, tick);
    656    }
    657 #undef ADJX
    658 
    659    PRE_MEM_WRITE( "adjtimex(timex)", ARG1, sizeof(struct vki_timex));
    660 }
    661 
    662 POST(sys_adjtimex)
    663 {
    664    POST_MEM_WRITE( ARG1, sizeof(struct vki_timex) );
    665 }
    666 
    667 PRE(sys_ioperm)
    668 {
    669    PRINT("sys_ioperm ( %ld, %ld, %ld )", ARG1, ARG2, ARG3 );
    670    PRE_REG_READ3(long, "ioperm",
    671                  unsigned long, from, unsigned long, num, int, turn_on);
    672 }
    673 
    674 PRE(sys_syslog)
    675 {
    676    *flags |= SfMayBlock;
    677    PRINT("sys_syslog (%ld, %#lx, %ld)", ARG1,ARG2,ARG3);
    678    PRE_REG_READ3(long, "syslog", int, type, char *, bufp, int, len);
    679    switch (ARG1) {
    680    // The kernel uses magic numbers here, rather than named constants,
    681    // therefore so do we.
    682    case 2: case 3: case 4:
    683       PRE_MEM_WRITE( "syslog(bufp)", ARG2, ARG3);
    684       break;
    685    default:
    686       break;
    687    }
    688 }
    689 POST(sys_syslog)
    690 {
    691    switch (ARG1) {
    692    case 2: case 3: case 4:
    693       POST_MEM_WRITE( ARG2, ARG3 );
    694       break;
    695    default:
    696       break;
    697    }
    698 }
    699 
    700 PRE(sys_vhangup)
    701 {
    702    PRINT("sys_vhangup ( )");
    703    PRE_REG_READ0(long, "vhangup");
    704 }
    705 
    706 PRE(sys_sysinfo)
    707 {
    708    PRINT("sys_sysinfo ( %#lx )",ARG1);
    709    PRE_REG_READ1(long, "sysinfo", struct sysinfo *, info);
    710    PRE_MEM_WRITE( "sysinfo(info)", ARG1, sizeof(struct vki_sysinfo) );
    711 }
    712 POST(sys_sysinfo)
    713 {
    714    POST_MEM_WRITE( ARG1, sizeof(struct vki_sysinfo) );
    715 }
    716 
    717 PRE(sys_personality)
    718 {
    719    PRINT("sys_personality ( %llu )", (ULong)ARG1);
    720    PRE_REG_READ1(long, "personality", vki_u_long, persona);
    721 }
    722 
    723 PRE(sys_sysctl)
    724 {
    725    struct __vki_sysctl_args *args;
    726    PRINT("sys_sysctl ( %#lx )", ARG1 );
    727    args = (struct __vki_sysctl_args *)ARG1;
    728    PRE_REG_READ1(long, "sysctl", struct __sysctl_args *, args);
    729    PRE_MEM_WRITE( "sysctl(args)", ARG1, sizeof(struct __vki_sysctl_args) );
    730    if (!VG_(am_is_valid_for_client)(ARG1, sizeof(struct __vki_sysctl_args),
    731                                           VKI_PROT_READ)) {
    732       SET_STATUS_Failure( VKI_EFAULT );
    733       return;
    734    }
    735 
    736    PRE_MEM_READ("sysctl(name)", (Addr)args->name, args->nlen * sizeof(*args->name));
    737    if (args->newval != NULL)
    738       PRE_MEM_READ("sysctl(newval)", (Addr)args->newval, args->newlen);
    739    if (args->oldlenp != NULL) {
    740       PRE_MEM_READ("sysctl(oldlenp)", (Addr)args->oldlenp, sizeof(*args->oldlenp));
    741       PRE_MEM_WRITE("sysctl(oldval)", (Addr)args->oldval, *args->oldlenp);
    742    }
    743 }
    744 POST(sys_sysctl)
    745 {
    746    struct __vki_sysctl_args *args;
    747    args = (struct __vki_sysctl_args *)ARG1;
    748    if (args->oldlenp != NULL) {
    749       POST_MEM_WRITE((Addr)args->oldlenp, sizeof(*args->oldlenp));
    750       POST_MEM_WRITE((Addr)args->oldval, 1 + *args->oldlenp);
    751    }
    752 }
    753 
    754 PRE(sys_prctl)
    755 {
    756    *flags |= SfMayBlock;
    757    PRINT( "sys_prctl ( %ld, %ld, %ld, %ld, %ld )", ARG1, ARG2, ARG3, ARG4, ARG5 );
    758    switch (ARG1) {
    759    case VKI_PR_SET_PDEATHSIG:
    760       PRE_REG_READ2(int, "prctl", int, option, int, signal);
    761       break;
    762    case VKI_PR_GET_PDEATHSIG:
    763       PRE_REG_READ2(int, "prctl", int, option, int *, signal);
    764       PRE_MEM_WRITE("prctl(get-death-signal)", ARG2, sizeof(Int));
    765       break;
    766    case VKI_PR_GET_DUMPABLE:
    767       PRE_REG_READ1(int, "prctl", int, option);
    768       break;
    769    case VKI_PR_SET_DUMPABLE:
    770       PRE_REG_READ2(int, "prctl", int, option, int, dump);
    771       break;
    772    case VKI_PR_GET_UNALIGN:
    773       PRE_REG_READ2(int, "prctl", int, option, int *, value);
    774       PRE_MEM_WRITE("prctl(get-unalign)", ARG2, sizeof(Int));
    775       break;
    776    case VKI_PR_SET_UNALIGN:
    777       PRE_REG_READ2(int, "prctl", int, option, int, value);
    778       break;
    779    case VKI_PR_GET_KEEPCAPS:
    780       PRE_REG_READ1(int, "prctl", int, option);
    781       break;
    782    case VKI_PR_SET_KEEPCAPS:
    783       PRE_REG_READ2(int, "prctl", int, option, int, keepcaps);
    784       break;
    785    case VKI_PR_GET_FPEMU:
    786       PRE_REG_READ2(int, "prctl", int, option, int *, value);
    787       PRE_MEM_WRITE("prctl(get-fpemu)", ARG2, sizeof(Int));
    788       break;
    789    case VKI_PR_SET_FPEMU:
    790       PRE_REG_READ2(int, "prctl", int, option, int, value);
    791       break;
    792    case VKI_PR_GET_FPEXC:
    793       PRE_REG_READ2(int, "prctl", int, option, int *, value);
    794       PRE_MEM_WRITE("prctl(get-fpexc)", ARG2, sizeof(Int));
    795       break;
    796    case VKI_PR_SET_FPEXC:
    797       PRE_REG_READ2(int, "prctl", int, option, int, value);
    798       break;
    799    case VKI_PR_GET_TIMING:
    800       PRE_REG_READ1(int, "prctl", int, option);
    801       break;
    802    case VKI_PR_SET_TIMING:
    803       PRE_REG_READ2(int, "prctl", int, option, int, timing);
    804       break;
    805    case VKI_PR_SET_NAME:
    806       PRE_REG_READ2(int, "prctl", int, option, char *, name);
    807       PRE_MEM_RASCIIZ("prctl(set-name)", ARG2);
    808       break;
    809    case VKI_PR_GET_NAME:
    810       PRE_REG_READ2(int, "prctl", int, option, char *, name);
    811       PRE_MEM_WRITE("prctl(get-name)", ARG2, VKI_TASK_COMM_LEN);
    812       break;
    813    case VKI_PR_GET_ENDIAN:
    814       PRE_REG_READ2(int, "prctl", int, option, int *, value);
    815       PRE_MEM_WRITE("prctl(get-endian)", ARG2, sizeof(Int));
    816       break;
    817    case VKI_PR_SET_ENDIAN:
    818       PRE_REG_READ2(int, "prctl", int, option, int, value);
    819       break;
    820    default:
    821       PRE_REG_READ5(long, "prctl",
    822                     int, option, unsigned long, arg2, unsigned long, arg3,
    823                     unsigned long, arg4, unsigned long, arg5);
    824       break;
    825    }
    826 }
    827 POST(sys_prctl)
    828 {
    829    switch (ARG1) {
    830    case VKI_PR_GET_PDEATHSIG:
    831       POST_MEM_WRITE(ARG2, sizeof(Int));
    832       break;
    833    case VKI_PR_GET_UNALIGN:
    834       POST_MEM_WRITE(ARG2, sizeof(Int));
    835       break;
    836    case VKI_PR_GET_FPEMU:
    837       POST_MEM_WRITE(ARG2, sizeof(Int));
    838       break;
    839    case VKI_PR_GET_FPEXC:
    840       POST_MEM_WRITE(ARG2, sizeof(Int));
    841       break;
    842    case VKI_PR_GET_NAME:
    843       POST_MEM_WRITE(ARG2, VKI_TASK_COMM_LEN);
    844       break;
    845    case VKI_PR_GET_ENDIAN:
    846       POST_MEM_WRITE(ARG2, sizeof(Int));
    847       break;
    848    }
    849 }
    850 
    851 PRE(sys_sendfile)
    852 {
    853    *flags |= SfMayBlock;
    854    PRINT("sys_sendfile ( %ld, %ld, %#lx, %lu )", ARG1,ARG2,ARG3,ARG4);
    855    PRE_REG_READ4(ssize_t, "sendfile",
    856                  int, out_fd, int, in_fd, vki_off_t *, offset,
    857                  vki_size_t, count);
    858    if (ARG3 != 0)
    859       PRE_MEM_WRITE( "sendfile(offset)", ARG3, sizeof(vki_off_t) );
    860 }
    861 POST(sys_sendfile)
    862 {
    863    if (ARG3 != 0 ) {
    864       POST_MEM_WRITE( ARG3, sizeof( vki_off_t ) );
    865    }
    866 }
    867 
    868 PRE(sys_sendfile64)
    869 {
    870    *flags |= SfMayBlock;
    871    PRINT("sendfile64 ( %ld, %ld, %#lx, %lu )",ARG1,ARG2,ARG3,ARG4);
    872    PRE_REG_READ4(ssize_t, "sendfile64",
    873                  int, out_fd, int, in_fd, vki_loff_t *, offset,
    874                  vki_size_t, count);
    875    if (ARG3 != 0)
    876       PRE_MEM_WRITE( "sendfile64(offset)", ARG3, sizeof(vki_loff_t) );
    877 }
    878 POST(sys_sendfile64)
    879 {
    880    if (ARG3 != 0 ) {
    881       POST_MEM_WRITE( ARG3, sizeof(vki_loff_t) );
    882    }
    883 }
    884 
    885 PRE(sys_futex)
    886 {
    887    /*
    888       arg    param                              used by ops
    889 
    890       ARG1 - u32 *futex				all
    891       ARG2 - int op
    892       ARG3 - int val				WAIT,WAKE,FD,REQUEUE,CMP_REQUEUE
    893       ARG4 - struct timespec *utime		WAIT:time*	REQUEUE,CMP_REQUEUE:val2
    894       ARG5 - u32 *uaddr2			REQUEUE,CMP_REQUEUE
    895       ARG6 - int val3				CMP_REQUEUE
    896     */
    897    PRINT("sys_futex ( %#lx, %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
    898    switch(ARG2 & ~(VKI_FUTEX_PRIVATE_FLAG|VKI_FUTEX_CLOCK_REALTIME)) {
    899    case VKI_FUTEX_CMP_REQUEUE:
    900    case VKI_FUTEX_WAKE_OP:
    901    case VKI_FUTEX_CMP_REQUEUE_PI:
    902       PRE_REG_READ6(long, "futex",
    903                     vki_u32 *, futex, int, op, int, val,
    904                     struct timespec *, utime, vki_u32 *, uaddr2, int, val3);
    905       break;
    906    case VKI_FUTEX_REQUEUE:
    907    case VKI_FUTEX_WAIT_REQUEUE_PI:
    908       PRE_REG_READ5(long, "futex",
    909                     vki_u32 *, futex, int, op, int, val,
    910                     struct timespec *, utime, vki_u32 *, uaddr2);
    911       break;
    912    case VKI_FUTEX_WAIT_BITSET:
    913       PRE_REG_READ6(long, "futex",
    914                     vki_u32 *, futex, int, op, int, val,
    915                     struct timespec *, utime, int, dummy, int, val3);
    916       break;
    917    case VKI_FUTEX_WAKE_BITSET:
    918       PRE_REG_READ6(long, "futex",
    919                     vki_u32 *, futex, int, op, int, val,
    920                     int, dummy, int, dummy2, int, val3);
    921       break;
    922    case VKI_FUTEX_WAIT:
    923    case VKI_FUTEX_LOCK_PI:
    924       PRE_REG_READ4(long, "futex",
    925                     vki_u32 *, futex, int, op, int, val,
    926                     struct timespec *, utime);
    927       break;
    928    case VKI_FUTEX_WAKE:
    929    case VKI_FUTEX_FD:
    930    case VKI_FUTEX_TRYLOCK_PI:
    931       PRE_REG_READ3(long, "futex",
    932                     vki_u32 *, futex, int, op, int, val);
    933       break;
    934    case VKI_FUTEX_UNLOCK_PI:
    935    default:
    936       PRE_REG_READ2(long, "futex", vki_u32 *, futex, int, op);
    937       break;
    938    }
    939 
    940    *flags |= SfMayBlock;
    941 
    942    switch(ARG2 & ~(VKI_FUTEX_PRIVATE_FLAG|VKI_FUTEX_CLOCK_REALTIME)) {
    943    case VKI_FUTEX_WAIT:
    944    case VKI_FUTEX_LOCK_PI:
    945    case VKI_FUTEX_WAIT_BITSET:
    946    case VKI_FUTEX_WAIT_REQUEUE_PI:
    947       PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
    948       if (ARG4 != 0)
    949 	 PRE_MEM_READ( "futex(timeout)", ARG4, sizeof(struct vki_timespec) );
    950       break;
    951 
    952    case VKI_FUTEX_REQUEUE:
    953    case VKI_FUTEX_CMP_REQUEUE:
    954    case VKI_FUTEX_CMP_REQUEUE_PI:
    955    case VKI_FUTEX_WAKE_OP:
    956       PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
    957       PRE_MEM_READ( "futex(futex2)", ARG5, sizeof(Int) );
    958       break;
    959 
    960    case VKI_FUTEX_FD:
    961    case VKI_FUTEX_TRYLOCK_PI:
    962    case VKI_FUTEX_UNLOCK_PI:
    963       PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
    964      break;
    965 
    966    case VKI_FUTEX_WAKE:
    967    case VKI_FUTEX_WAKE_BITSET:
    968       /* no additional pointers */
    969       break;
    970 
    971    default:
    972       SET_STATUS_Failure( VKI_ENOSYS );   // some futex function we don't understand
    973       break;
    974    }
    975 }
    976 POST(sys_futex)
    977 {
    978    vg_assert(SUCCESS);
    979    POST_MEM_WRITE( ARG1, sizeof(int) );
    980    if (ARG2 == VKI_FUTEX_FD) {
    981       if (!ML_(fd_allowed)(RES, "futex", tid, True)) {
    982          VG_(close)(RES);
    983          SET_STATUS_Failure( VKI_EMFILE );
    984       } else {
    985          if (VG_(clo_track_fds))
    986             ML_(record_fd_open_nameless)(tid, RES);
    987       }
    988    }
    989 }
    990 
    991 PRE(sys_set_robust_list)
    992 {
    993    PRINT("sys_set_robust_list ( %#lx, %ld )", ARG1,ARG2);
    994    PRE_REG_READ2(long, "set_robust_list",
    995                  struct vki_robust_list_head *, head, vki_size_t, len);
    996 
    997    /* Just check the robust_list_head structure is readable - don't
    998       try and chase the list as the kernel will only read it when
    999       the thread exits so the current contents is irrelevant. */
   1000    if (ARG1 != 0)
   1001       PRE_MEM_READ("set_robust_list(head)", ARG1, ARG2);
   1002 }
   1003 
   1004 PRE(sys_get_robust_list)
   1005 {
   1006    PRINT("sys_get_robust_list ( %ld, %#lx, %ld )", ARG1,ARG2,ARG3);
   1007    PRE_REG_READ3(long, "get_robust_list",
   1008                  int, pid,
   1009                  struct vki_robust_list_head **, head_ptr,
   1010                  vki_size_t *, len_ptr);
   1011    PRE_MEM_WRITE("get_robust_list(head_ptr)",
   1012                  ARG2, sizeof(struct vki_robust_list_head *));
   1013    PRE_MEM_WRITE("get_robust_list(len_ptr)",
   1014                  ARG3, sizeof(struct vki_size_t *));
   1015 }
   1016 POST(sys_get_robust_list)
   1017 {
   1018    POST_MEM_WRITE(ARG2, sizeof(struct vki_robust_list_head *));
   1019    POST_MEM_WRITE(ARG3, sizeof(struct vki_size_t *));
   1020 }
   1021 
   1022 PRE(sys_pselect6)
   1023 {
   1024    *flags |= SfMayBlock;
   1025    PRINT("sys_pselect6 ( %ld, %#lx, %#lx, %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
   1026    PRE_REG_READ6(long, "pselect6",
   1027                  int, n, vki_fd_set *, readfds, vki_fd_set *, writefds,
   1028                  vki_fd_set *, exceptfds, struct vki_timeval *, timeout,
   1029                  void *, sig);
   1030    // XXX: this possibly understates how much memory is read.
   1031    if (ARG2 != 0)
   1032       PRE_MEM_READ( "pselect6(readfds)",
   1033 		     ARG2, ARG1/8 /* __FD_SETSIZE/8 */ );
   1034    if (ARG3 != 0)
   1035       PRE_MEM_READ( "pselect6(writefds)",
   1036 		     ARG3, ARG1/8 /* __FD_SETSIZE/8 */ );
   1037    if (ARG4 != 0)
   1038       PRE_MEM_READ( "pselect6(exceptfds)",
   1039 		     ARG4, ARG1/8 /* __FD_SETSIZE/8 */ );
   1040    if (ARG5 != 0)
   1041       PRE_MEM_READ( "pselect6(timeout)", ARG5, sizeof(struct vki_timeval) );
   1042    if (ARG6 != 0)
   1043       PRE_MEM_READ( "pselect6(sig)", ARG6, sizeof(void *)+sizeof(vki_size_t) );
   1044 }
   1045 
   1046 PRE(sys_ppoll)
   1047 {
   1048    UInt i;
   1049    struct vki_pollfd* ufds = (struct vki_pollfd *)ARG1;
   1050    *flags |= SfMayBlock;
   1051    PRINT("sys_ppoll ( %#lx, %ld, %#lx, %#lx, %llu )\n", ARG1,ARG2,ARG3,ARG4,(ULong)ARG5);
   1052    PRE_REG_READ5(long, "ppoll",
   1053                  struct vki_pollfd *, ufds, unsigned int, nfds,
   1054                  struct vki_timespec *, tsp, vki_sigset_t *, sigmask,
   1055                  vki_size_t, sigsetsize);
   1056 
   1057    for (i = 0; i < ARG2; i++) {
   1058       PRE_MEM_READ( "ppoll(ufds.fd)",
   1059                     (Addr)(&ufds[i].fd), sizeof(ufds[i].fd) );
   1060       PRE_MEM_READ( "ppoll(ufds.events)",
   1061                     (Addr)(&ufds[i].events), sizeof(ufds[i].events) );
   1062       PRE_MEM_WRITE( "ppoll(ufd.reventss)",
   1063                      (Addr)(&ufds[i].revents), sizeof(ufds[i].revents) );
   1064    }
   1065 
   1066    if (ARG3)
   1067       PRE_MEM_READ( "ppoll(tsp)", ARG3, sizeof(struct vki_timespec) );
   1068    if (ARG4)
   1069       PRE_MEM_READ( "ppoll(sigmask)", ARG4, sizeof(vki_sigset_t) );
   1070 }
   1071 
   1072 POST(sys_ppoll)
   1073 {
   1074    if (RES > 0) {
   1075       UInt i;
   1076       struct vki_pollfd* ufds = (struct vki_pollfd *)ARG1;
   1077       for (i = 0; i < ARG2; i++)
   1078 	 POST_MEM_WRITE( (Addr)(&ufds[i].revents), sizeof(ufds[i].revents) );
   1079    }
   1080 }
   1081 
   1082 
   1083 /* ---------------------------------------------------------------------
   1084    epoll_* wrappers
   1085    ------------------------------------------------------------------ */
   1086 
   1087 PRE(sys_epoll_create)
   1088 {
   1089    PRINT("sys_epoll_create ( %ld )", ARG1);
   1090    PRE_REG_READ1(long, "epoll_create", int, size);
   1091 }
   1092 POST(sys_epoll_create)
   1093 {
   1094    vg_assert(SUCCESS);
   1095    if (!ML_(fd_allowed)(RES, "epoll_create", tid, True)) {
   1096       VG_(close)(RES);
   1097       SET_STATUS_Failure( VKI_EMFILE );
   1098    } else {
   1099       if (VG_(clo_track_fds))
   1100          ML_(record_fd_open_nameless) (tid, RES);
   1101    }
   1102 }
   1103 
   1104 PRE(sys_epoll_create1)
   1105 {
   1106    PRINT("sys_epoll_create1 ( %ld )", ARG1);
   1107    PRE_REG_READ1(long, "epoll_create1", int, flags);
   1108 }
   1109 POST(sys_epoll_create1)
   1110 {
   1111    vg_assert(SUCCESS);
   1112    if (!ML_(fd_allowed)(RES, "epoll_create1", tid, True)) {
   1113       VG_(close)(RES);
   1114       SET_STATUS_Failure( VKI_EMFILE );
   1115    } else {
   1116       if (VG_(clo_track_fds))
   1117          ML_(record_fd_open_nameless) (tid, RES);
   1118    }
   1119 }
   1120 
   1121 PRE(sys_epoll_ctl)
   1122 {
   1123    static const HChar* epoll_ctl_s[3] = {
   1124       "EPOLL_CTL_ADD",
   1125       "EPOLL_CTL_DEL",
   1126       "EPOLL_CTL_MOD"
   1127    };
   1128    PRINT("sys_epoll_ctl ( %ld, %s, %ld, %#lx )",
   1129          ARG1, ( ARG2<3 ? epoll_ctl_s[ARG2] : "?" ), ARG3, ARG4);
   1130    PRE_REG_READ4(long, "epoll_ctl",
   1131                  int, epfd, int, op, int, fd, struct vki_epoll_event *, event);
   1132    if (ARG2 != VKI_EPOLL_CTL_DEL)
   1133       PRE_MEM_READ( "epoll_ctl(event)", ARG4, sizeof(struct vki_epoll_event) );
   1134 }
   1135 
   1136 PRE(sys_epoll_wait)
   1137 {
   1138    *flags |= SfMayBlock;
   1139    PRINT("sys_epoll_wait ( %ld, %#lx, %ld, %ld )", ARG1, ARG2, ARG3, ARG4);
   1140    PRE_REG_READ4(long, "epoll_wait",
   1141                  int, epfd, struct vki_epoll_event *, events,
   1142                  int, maxevents, int, timeout);
   1143    PRE_MEM_WRITE( "epoll_wait(events)", ARG2, sizeof(struct vki_epoll_event)*ARG3);
   1144 }
   1145 POST(sys_epoll_wait)
   1146 {
   1147    vg_assert(SUCCESS);
   1148    if (RES > 0)
   1149       POST_MEM_WRITE( ARG2, sizeof(struct vki_epoll_event)*RES ) ;
   1150 }
   1151 
   1152 PRE(sys_epoll_pwait)
   1153 {
   1154    *flags |= SfMayBlock;
   1155    PRINT("sys_epoll_pwait ( %ld, %#lx, %ld, %ld, %#lx, %llu )", ARG1,ARG2,ARG3,ARG4,ARG5,(ULong)ARG6);
   1156    PRE_REG_READ6(long, "epoll_pwait",
   1157                  int, epfd, struct vki_epoll_event *, events,
   1158                  int, maxevents, int, timeout, vki_sigset_t *, sigmask,
   1159                  vki_size_t, sigsetsize);
   1160    PRE_MEM_WRITE( "epoll_pwait(events)", ARG2, sizeof(struct vki_epoll_event)*ARG3);
   1161    if (ARG4)
   1162       PRE_MEM_READ( "epoll_pwait(sigmask)", ARG5, sizeof(vki_sigset_t) );
   1163 }
   1164 POST(sys_epoll_pwait)
   1165 {
   1166    vg_assert(SUCCESS);
   1167    if (RES > 0)
   1168       POST_MEM_WRITE( ARG2, sizeof(struct vki_epoll_event)*RES ) ;
   1169 }
   1170 
   1171 PRE(sys_eventfd)
   1172 {
   1173    PRINT("sys_eventfd ( %lu )", ARG1);
   1174    PRE_REG_READ1(long, "sys_eventfd", unsigned int, count);
   1175 }
   1176 POST(sys_eventfd)
   1177 {
   1178    if (!ML_(fd_allowed)(RES, "eventfd", tid, True)) {
   1179       VG_(close)(RES);
   1180       SET_STATUS_Failure( VKI_EMFILE );
   1181    } else {
   1182       if (VG_(clo_track_fds))
   1183          ML_(record_fd_open_nameless) (tid, RES);
   1184    }
   1185 }
   1186 
   1187 PRE(sys_eventfd2)
   1188 {
   1189    PRINT("sys_eventfd2 ( %lu, %ld )", ARG1,ARG2);
   1190    PRE_REG_READ2(long, "sys_eventfd2", unsigned int, count, int, flags);
   1191 }
   1192 POST(sys_eventfd2)
   1193 {
   1194    if (!ML_(fd_allowed)(RES, "eventfd2", tid, True)) {
   1195       VG_(close)(RES);
   1196       SET_STATUS_Failure( VKI_EMFILE );
   1197    } else {
   1198       if (VG_(clo_track_fds))
   1199          ML_(record_fd_open_nameless) (tid, RES);
   1200    }
   1201 }
   1202 
   1203 PRE(sys_fallocate)
   1204 {
   1205    *flags |= SfMayBlock;
   1206 #if VG_WORDSIZE == 4
   1207    PRINT("sys_fallocate ( %ld, %ld, %lld, %lld )",
   1208          ARG1, ARG2, MERGE64(ARG3,ARG4), MERGE64(ARG5,ARG6));
   1209    PRE_REG_READ6(long, "fallocate",
   1210                  int, fd, int, mode,
   1211                  unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
   1212                  unsigned, MERGE64_FIRST(len), unsigned, MERGE64_SECOND(len));
   1213 #elif VG_WORDSIZE == 8
   1214    PRINT("sys_fallocate ( %ld, %ld, %lld, %lld )",
   1215          ARG1, ARG2, (Long)ARG3, (Long)ARG4);
   1216    PRE_REG_READ4(long, "fallocate",
   1217                  int, fd, int, mode, vki_loff_t, offset, vki_loff_t, len);
   1218 #else
   1219 #  error Unexpected word size
   1220 #endif
   1221    if (!ML_(fd_allowed)(ARG1, "fallocate", tid, False))
   1222       SET_STATUS_Failure( VKI_EBADF );
   1223 }
   1224 
   1225 /* ---------------------------------------------------------------------
   1226    tid-related wrappers
   1227    ------------------------------------------------------------------ */
   1228 
   1229 PRE(sys_gettid)
   1230 {
   1231    PRINT("sys_gettid ()");
   1232    PRE_REG_READ0(long, "gettid");
   1233 }
   1234 
   1235 PRE(sys_set_tid_address)
   1236 {
   1237    PRINT("sys_set_tid_address ( %#lx )", ARG1);
   1238    PRE_REG_READ1(long, "set_tid_address", int *, tidptr);
   1239 }
   1240 
   1241 PRE(sys_tkill)
   1242 {
   1243    PRINT("sys_tgkill ( %ld, %ld )", ARG1,ARG2);
   1244    PRE_REG_READ2(long, "tkill", int, tid, int, sig);
   1245    if (!ML_(client_signal_OK)(ARG2)) {
   1246       SET_STATUS_Failure( VKI_EINVAL );
   1247       return;
   1248    }
   1249 
   1250    /* Check to see if this kill gave us a pending signal */
   1251    *flags |= SfPollAfter;
   1252 
   1253    if (VG_(clo_trace_signals))
   1254       VG_(message)(Vg_DebugMsg, "tkill: sending signal %ld to pid %ld\n",
   1255 		   ARG2, ARG1);
   1256 
   1257    /* If we're sending SIGKILL, check to see if the target is one of
   1258       our threads and handle it specially. */
   1259    if (ARG2 == VKI_SIGKILL && ML_(do_sigkill)(ARG1, -1)) {
   1260       SET_STATUS_Success(0);
   1261       return;
   1262    }
   1263 
   1264    /* Ask to handle this syscall via the slow route, since that's the
   1265       only one that sets tst->status to VgTs_WaitSys.  If the result
   1266       of doing the syscall is an immediate run of
   1267       async_signalhandler() in m_signals, then we need the thread to
   1268       be properly tidied away.  I have the impression the previous
   1269       version of this wrapper worked on x86/amd64 only because the
   1270       kernel did not immediately deliver the async signal to this
   1271       thread (on ppc it did, which broke the assertion re tst->status
   1272       at the top of async_signalhandler()). */
   1273    *flags |= SfMayBlock;
   1274 }
   1275 POST(sys_tkill)
   1276 {
   1277    if (VG_(clo_trace_signals))
   1278       VG_(message)(Vg_DebugMsg, "tkill: sent signal %ld to pid %ld\n",
   1279                    ARG2, ARG1);
   1280 }
   1281 
   1282 PRE(sys_tgkill)
   1283 {
   1284    PRINT("sys_tgkill ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   1285    PRE_REG_READ3(long, "tgkill", int, tgid, int, tid, int, sig);
   1286    if (!ML_(client_signal_OK)(ARG3)) {
   1287       SET_STATUS_Failure( VKI_EINVAL );
   1288       return;
   1289    }
   1290 
   1291    /* Check to see if this kill gave us a pending signal */
   1292    *flags |= SfPollAfter;
   1293 
   1294    if (VG_(clo_trace_signals))
   1295       VG_(message)(Vg_DebugMsg,
   1296                    "tgkill: sending signal %ld to pid %ld/%ld\n",
   1297 		   ARG3, ARG1, ARG2);
   1298 
   1299    /* If we're sending SIGKILL, check to see if the target is one of
   1300       our threads and handle it specially. */
   1301    if (ARG3 == VKI_SIGKILL && ML_(do_sigkill)(ARG2, ARG1)) {
   1302       SET_STATUS_Success(0);
   1303       return;
   1304    }
   1305 
   1306    /* Ask to handle this syscall via the slow route, since that's the
   1307       only one that sets tst->status to VgTs_WaitSys.  If the result
   1308       of doing the syscall is an immediate run of
   1309       async_signalhandler() in m_signals, then we need the thread to
   1310       be properly tidied away.  I have the impression the previous
   1311       version of this wrapper worked on x86/amd64 only because the
   1312       kernel did not immediately deliver the async signal to this
   1313       thread (on ppc it did, which broke the assertion re tst->status
   1314       at the top of async_signalhandler()). */
   1315    *flags |= SfMayBlock;
   1316 }
   1317 POST(sys_tgkill)
   1318 {
   1319    if (VG_(clo_trace_signals))
   1320       VG_(message)(Vg_DebugMsg,
   1321                    "tgkill: sent signal %ld to pid %ld/%ld\n",
   1322                    ARG3, ARG1, ARG2);
   1323 }
   1324 
   1325 /* ---------------------------------------------------------------------
   1326    fadvise64* wrappers
   1327    ------------------------------------------------------------------ */
   1328 
   1329 PRE(sys_fadvise64)
   1330 {
   1331    PRINT("sys_fadvise64 ( %ld, %lld, %lu, %ld )",
   1332          ARG1, MERGE64(ARG2,ARG3), ARG4, ARG5);
   1333    PRE_REG_READ5(long, "fadvise64",
   1334                  int, fd, vki_u32, MERGE64_FIRST(offset), vki_u32, MERGE64_SECOND(offset),
   1335                  vki_size_t, len, int, advice);
   1336 }
   1337 
   1338 PRE(sys_fadvise64_64)
   1339 {
   1340    PRINT("sys_fadvise64_64 ( %ld, %lld, %lld, %ld )",
   1341          ARG1, MERGE64(ARG2,ARG3), MERGE64(ARG4,ARG5), ARG6);
   1342    PRE_REG_READ6(long, "fadvise64_64",
   1343                  int, fd, vki_u32, MERGE64_FIRST(offset), vki_u32, MERGE64_SECOND(offset),
   1344                  vki_u32, MERGE64_FIRST(len), vki_u32, MERGE64_SECOND(len), int, advice);
   1345 }
   1346 
   1347 /* ---------------------------------------------------------------------
   1348    io_* wrappers
   1349    ------------------------------------------------------------------ */
   1350 
   1351 // Nb: this wrapper has to pad/unpad memory around the syscall itself,
   1352 // and this allows us to control exactly the code that gets run while
   1353 // the padding is in place.
   1354 
   1355 PRE(sys_io_setup)
   1356 {
   1357    PRINT("sys_io_setup ( %lu, %#lx )", ARG1,ARG2);
   1358    PRE_REG_READ2(long, "io_setup",
   1359                  unsigned, nr_events, vki_aio_context_t *, ctxp);
   1360    PRE_MEM_WRITE( "io_setup(ctxp)", ARG2, sizeof(vki_aio_context_t) );
   1361 }
   1362 
   1363 POST(sys_io_setup)
   1364 {
   1365    SizeT size;
   1366    struct vki_aio_ring *r;
   1367 
   1368    size = VG_PGROUNDUP(sizeof(struct vki_aio_ring) +
   1369                        ARG1*sizeof(struct vki_io_event));
   1370    r = *(struct vki_aio_ring **)ARG2;
   1371    vg_assert(ML_(valid_client_addr)((Addr)r, size, tid, "io_setup"));
   1372 
   1373    ML_(notify_core_and_tool_of_mmap)( (Addr)r, size,
   1374                                       VKI_PROT_READ | VKI_PROT_WRITE,
   1375                                       VKI_MAP_ANONYMOUS, -1, 0 );
   1376 
   1377    POST_MEM_WRITE( ARG2, sizeof(vki_aio_context_t) );
   1378 }
   1379 
   1380 // Nb: This wrapper is "Special" because we need 'size' to do the unmap
   1381 // after the syscall.  We must get 'size' from the aio_ring structure,
   1382 // before the syscall, while the aio_ring structure still exists.  (And we
   1383 // know that we must look at the aio_ring structure because Tom inspected the
   1384 // kernel and glibc sources to see what they do, yuk.)
   1385 //
   1386 // XXX This segment can be implicitly unmapped when aio
   1387 // file-descriptors are closed...
   1388 PRE(sys_io_destroy)
   1389 {
   1390    SizeT size = 0;
   1391 
   1392    PRINT("sys_io_destroy ( %llu )", (ULong)ARG1);
   1393    PRE_REG_READ1(long, "io_destroy", vki_aio_context_t, ctx);
   1394 
   1395    // If we are going to seg fault (due to a bogus ARG1) do it as late as
   1396    // possible...
   1397    if (ML_(safe_to_deref)( (void*)ARG1, sizeof(struct vki_aio_ring))) {
   1398       struct vki_aio_ring *r = (struct vki_aio_ring *)ARG1;
   1399       size = VG_PGROUNDUP(sizeof(struct vki_aio_ring) +
   1400                           r->nr*sizeof(struct vki_io_event));
   1401    }
   1402 
   1403    SET_STATUS_from_SysRes( VG_(do_syscall1)(SYSNO, ARG1) );
   1404 
   1405    if (SUCCESS && RES == 0) {
   1406       Bool d = VG_(am_notify_munmap)( ARG1, size );
   1407       VG_TRACK( die_mem_munmap, ARG1, size );
   1408       if (d)
   1409          VG_(discard_translations)( (Addr64)ARG1, (ULong)size,
   1410                                     "PRE(sys_io_destroy)" );
   1411    }
   1412 }
   1413 
   1414 PRE(sys_io_getevents)
   1415 {
   1416    *flags |= SfMayBlock;
   1417    PRINT("sys_io_getevents ( %llu, %lld, %lld, %#lx, %#lx )",
   1418          (ULong)ARG1,(Long)ARG2,(Long)ARG3,ARG4,ARG5);
   1419    PRE_REG_READ5(long, "io_getevents",
   1420                  vki_aio_context_t, ctx_id, long, min_nr, long, nr,
   1421                  struct io_event *, events,
   1422                  struct timespec *, timeout);
   1423    if (ARG3 > 0)
   1424       PRE_MEM_WRITE( "io_getevents(events)",
   1425                      ARG4, sizeof(struct vki_io_event)*ARG3 );
   1426    if (ARG5 != 0)
   1427       PRE_MEM_READ( "io_getevents(timeout)",
   1428                     ARG5, sizeof(struct vki_timespec));
   1429 }
   1430 POST(sys_io_getevents)
   1431 {
   1432    Int i;
   1433    vg_assert(SUCCESS);
   1434    if (RES > 0) {
   1435       POST_MEM_WRITE( ARG4, sizeof(struct vki_io_event)*RES );
   1436       for (i = 0; i < RES; i++) {
   1437          const struct vki_io_event *vev = ((struct vki_io_event *)ARG4) + i;
   1438          const struct vki_iocb *cb = (struct vki_iocb *)(Addr)vev->obj;
   1439 
   1440          switch (cb->aio_lio_opcode) {
   1441          case VKI_IOCB_CMD_PREAD:
   1442             if (vev->result > 0)
   1443                POST_MEM_WRITE( cb->aio_buf, vev->result );
   1444             break;
   1445 
   1446          case VKI_IOCB_CMD_PWRITE:
   1447             break;
   1448 
   1449          case VKI_IOCB_CMD_FSYNC:
   1450             break;
   1451 
   1452          case VKI_IOCB_CMD_FDSYNC:
   1453             break;
   1454 
   1455          case VKI_IOCB_CMD_PREADV:
   1456 	     if (vev->result > 0) {
   1457                   struct vki_iovec * vec = (struct vki_iovec *)(Addr)cb->aio_buf;
   1458                   Int remains = vev->result;
   1459                   Int j;
   1460 
   1461                   for (j = 0; j < cb->aio_nbytes; j++) {
   1462                        Int nReadThisBuf = vec[j].iov_len;
   1463                        if (nReadThisBuf > remains) nReadThisBuf = remains;
   1464                        POST_MEM_WRITE( (Addr)vec[j].iov_base, nReadThisBuf );
   1465                        remains -= nReadThisBuf;
   1466                        if (remains < 0) VG_(core_panic)("io_getevents(PREADV): remains < 0");
   1467                   }
   1468 	     }
   1469              break;
   1470 
   1471          case VKI_IOCB_CMD_PWRITEV:
   1472              break;
   1473 
   1474          default:
   1475             VG_(message)(Vg_DebugMsg,
   1476                         "Warning: unhandled io_getevents opcode: %u\n",
   1477                         cb->aio_lio_opcode);
   1478             break;
   1479          }
   1480       }
   1481    }
   1482 }
   1483 
   1484 PRE(sys_io_submit)
   1485 {
   1486    Int i, j;
   1487 
   1488    PRINT("sys_io_submit ( %llu, %ld, %#lx )", (ULong)ARG1,ARG2,ARG3);
   1489    PRE_REG_READ3(long, "io_submit",
   1490                  vki_aio_context_t, ctx_id, long, nr,
   1491                  struct iocb **, iocbpp);
   1492    PRE_MEM_READ( "io_submit(iocbpp)", ARG3, ARG2*sizeof(struct vki_iocb *) );
   1493    if (ARG3 != 0) {
   1494       for (i = 0; i < ARG2; i++) {
   1495          struct vki_iocb *cb = ((struct vki_iocb **)ARG3)[i];
   1496          struct vki_iovec *iov;
   1497 
   1498          PRE_MEM_READ( "io_submit(iocb)", (Addr)cb, sizeof(struct vki_iocb) );
   1499          switch (cb->aio_lio_opcode) {
   1500          case VKI_IOCB_CMD_PREAD:
   1501             PRE_MEM_WRITE( "io_submit(PREAD)", cb->aio_buf, cb->aio_nbytes );
   1502             break;
   1503 
   1504          case VKI_IOCB_CMD_PWRITE:
   1505             PRE_MEM_READ( "io_submit(PWRITE)", cb->aio_buf, cb->aio_nbytes );
   1506             break;
   1507 
   1508          case VKI_IOCB_CMD_FSYNC:
   1509             break;
   1510 
   1511          case VKI_IOCB_CMD_FDSYNC:
   1512             break;
   1513 
   1514          case VKI_IOCB_CMD_PREADV:
   1515             iov = (struct vki_iovec *)(Addr)cb->aio_buf;
   1516             PRE_MEM_READ( "io_submit(PREADV)", cb->aio_buf, cb->aio_nbytes * sizeof(struct vki_iovec) );
   1517             for (j = 0; j < cb->aio_nbytes; j++)
   1518                 PRE_MEM_WRITE( "io_submit(PREADV(iov[i]))", (Addr)iov[j].iov_base, iov[j].iov_len );
   1519             break;
   1520 
   1521          case VKI_IOCB_CMD_PWRITEV:
   1522             iov = (struct vki_iovec *)(Addr)cb->aio_buf;
   1523             PRE_MEM_READ( "io_submit(PWRITEV)", cb->aio_buf, cb->aio_nbytes * sizeof(struct vki_iovec) );
   1524             for (j = 0; j < cb->aio_nbytes; j++)
   1525                 PRE_MEM_READ( "io_submit(PWRITEV(iov[i]))", (Addr)iov[j].iov_base, iov[j].iov_len );
   1526             break;
   1527 
   1528          default:
   1529             VG_(message)(Vg_DebugMsg,"Warning: unhandled io_submit opcode: %u\n",
   1530                          cb->aio_lio_opcode);
   1531             break;
   1532          }
   1533       }
   1534    }
   1535 }
   1536 
   1537 PRE(sys_io_cancel)
   1538 {
   1539    PRINT("sys_io_cancel ( %llu, %#lx, %#lx )", (ULong)ARG1,ARG2,ARG3);
   1540    PRE_REG_READ3(long, "io_cancel",
   1541                  vki_aio_context_t, ctx_id, struct iocb *, iocb,
   1542                  struct io_event *, result);
   1543    PRE_MEM_READ( "io_cancel(iocb)", ARG2, sizeof(struct vki_iocb) );
   1544    PRE_MEM_WRITE( "io_cancel(result)", ARG3, sizeof(struct vki_io_event) );
   1545 }
   1546 POST(sys_io_cancel)
   1547 {
   1548    POST_MEM_WRITE( ARG3, sizeof(struct vki_io_event) );
   1549 }
   1550 
   1551 /* ---------------------------------------------------------------------
   1552    *_mempolicy wrappers
   1553    ------------------------------------------------------------------ */
   1554 
   1555 PRE(sys_mbind)
   1556 {
   1557    PRINT("sys_mbind ( %#lx, %lu, %ld, %#lx, %lu, %lu )", ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
   1558    PRE_REG_READ6(long, "mbind",
   1559                  unsigned long, start, unsigned long, len,
   1560                  unsigned long, policy, unsigned long *, nodemask,
   1561                  unsigned long, maxnode, unsigned, flags);
   1562    if (ARG1 != 0)
   1563       PRE_MEM_READ( "mbind(nodemask)", ARG4,
   1564                     VG_ROUNDUP( ARG5, sizeof(UWord) ) / sizeof(UWord) );
   1565 }
   1566 
   1567 PRE(sys_set_mempolicy)
   1568 {
   1569    PRINT("sys_set_mempolicy ( %ld, %#lx, %ld )", ARG1,ARG2,ARG3);
   1570    PRE_REG_READ3(long, "set_mempolicy",
   1571                  int, policy, unsigned long *, nodemask,
   1572                  unsigned long, maxnode);
   1573    PRE_MEM_READ( "set_mempolicy(nodemask)", ARG2,
   1574                  VG_ROUNDUP( ARG3, sizeof(UWord) ) / sizeof(UWord) );
   1575 }
   1576 
   1577 PRE(sys_get_mempolicy)
   1578 {
   1579    PRINT("sys_get_mempolicy ( %#lx, %#lx, %ld, %#lx, %lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
   1580    PRE_REG_READ5(long, "get_mempolicy",
   1581                  int *, policy, unsigned long *, nodemask,
   1582                  unsigned long, maxnode, unsigned long, addr,
   1583                  unsigned long, flags);
   1584    if (ARG1 != 0)
   1585       PRE_MEM_WRITE( "get_mempolicy(policy)", ARG1, sizeof(Int) );
   1586    if (ARG2 != 0)
   1587       PRE_MEM_WRITE( "get_mempolicy(nodemask)", ARG2,
   1588                      VG_ROUNDUP( ARG3, sizeof(UWord) * 8 ) / sizeof(UWord) );
   1589 }
   1590 POST(sys_get_mempolicy)
   1591 {
   1592    if (ARG1 != 0)
   1593       POST_MEM_WRITE( ARG1, sizeof(Int) );
   1594    if (ARG2 != 0)
   1595       POST_MEM_WRITE( ARG2, VG_ROUNDUP( ARG3, sizeof(UWord) * 8 ) / sizeof(UWord) );
   1596 }
   1597 
   1598 /* ---------------------------------------------------------------------
   1599    inotify_* wrappers
   1600    ------------------------------------------------------------------ */
   1601 
   1602 PRE(sys_inotify_init)
   1603 {
   1604    PRINT("sys_inotify_init ( )");
   1605    PRE_REG_READ0(long, "inotify_init");
   1606 }
   1607 POST(sys_inotify_init)
   1608 {
   1609    vg_assert(SUCCESS);
   1610    if (!ML_(fd_allowed)(RES, "inotify_init", tid, True)) {
   1611       VG_(close)(RES);
   1612       SET_STATUS_Failure( VKI_EMFILE );
   1613    } else {
   1614       if (VG_(clo_track_fds))
   1615          ML_(record_fd_open_nameless) (tid, RES);
   1616    }
   1617 }
   1618 
   1619 PRE(sys_inotify_init1)
   1620 {
   1621    PRINT("sys_inotify_init ( %ld )", ARG1);
   1622    PRE_REG_READ1(long, "inotify_init", int, flag);
   1623 }
   1624 
   1625 POST(sys_inotify_init1)
   1626 {
   1627    vg_assert(SUCCESS);
   1628    if (!ML_(fd_allowed)(RES, "inotify_init", tid, True)) {
   1629       VG_(close)(RES);
   1630       SET_STATUS_Failure( VKI_EMFILE );
   1631    } else {
   1632       if (VG_(clo_track_fds))
   1633          ML_(record_fd_open_nameless) (tid, RES);
   1634    }
   1635 }
   1636 
   1637 PRE(sys_inotify_add_watch)
   1638 {
   1639    PRINT( "sys_inotify_add_watch ( %ld, %#lx, %lx )", ARG1,ARG2,ARG3);
   1640    PRE_REG_READ3(long, "inotify_add_watch", int, fd, char *, path, int, mask);
   1641    PRE_MEM_RASCIIZ( "inotify_add_watch(path)", ARG2 );
   1642 }
   1643 
   1644 PRE(sys_inotify_rm_watch)
   1645 {
   1646    PRINT( "sys_inotify_rm_watch ( %ld, %lx )", ARG1,ARG2);
   1647    PRE_REG_READ2(long, "inotify_rm_watch", int, fd, int, wd);
   1648 }
   1649 
   1650 /* ---------------------------------------------------------------------
   1651    mq_* wrappers
   1652    ------------------------------------------------------------------ */
   1653 
   1654 PRE(sys_mq_open)
   1655 {
   1656    PRINT("sys_mq_open( %#lx(%s), %ld, %lld, %#lx )",
   1657          ARG1,(char*)ARG1,ARG2,(ULong)ARG3,ARG4);
   1658    PRE_REG_READ4(long, "mq_open",
   1659                  const char *, name, int, oflag, vki_mode_t, mode,
   1660                  struct mq_attr *, attr);
   1661    PRE_MEM_RASCIIZ( "mq_open(name)", ARG1 );
   1662    if ((ARG2 & VKI_O_CREAT) != 0 && ARG4 != 0) {
   1663       const struct vki_mq_attr *attr = (struct vki_mq_attr *)ARG4;
   1664       PRE_MEM_READ( "mq_open(attr->mq_maxmsg)",
   1665                      (Addr)&attr->mq_maxmsg, sizeof(attr->mq_maxmsg) );
   1666       PRE_MEM_READ( "mq_open(attr->mq_msgsize)",
   1667                      (Addr)&attr->mq_msgsize, sizeof(attr->mq_msgsize) );
   1668    }
   1669 }
   1670 POST(sys_mq_open)
   1671 {
   1672    vg_assert(SUCCESS);
   1673    if (!ML_(fd_allowed)(RES, "mq_open", tid, True)) {
   1674       VG_(close)(RES);
   1675       SET_STATUS_Failure( VKI_EMFILE );
   1676    } else {
   1677       if (VG_(clo_track_fds))
   1678          ML_(record_fd_open_with_given_name)(tid, RES, (Char*)ARG1);
   1679    }
   1680 }
   1681 
   1682 PRE(sys_mq_unlink)
   1683 {
   1684    PRINT("sys_mq_unlink ( %#lx(%s) )", ARG1,(char*)ARG1);
   1685    PRE_REG_READ1(long, "mq_unlink", const char *, name);
   1686    PRE_MEM_RASCIIZ( "mq_unlink(name)", ARG1 );
   1687 }
   1688 
   1689 PRE(sys_mq_timedsend)
   1690 {
   1691    *flags |= SfMayBlock;
   1692    PRINT("sys_mq_timedsend ( %ld, %#lx, %llu, %ld, %#lx )",
   1693          ARG1,ARG2,(ULong)ARG3,ARG4,ARG5);
   1694    PRE_REG_READ5(long, "mq_timedsend",
   1695                  vki_mqd_t, mqdes, const char *, msg_ptr, vki_size_t, msg_len,
   1696                  unsigned int, msg_prio, const struct timespec *, abs_timeout);
   1697    if (!ML_(fd_allowed)(ARG1, "mq_timedsend", tid, False)) {
   1698       SET_STATUS_Failure( VKI_EBADF );
   1699    } else {
   1700       PRE_MEM_READ( "mq_timedsend(msg_ptr)", ARG2, ARG3 );
   1701       if (ARG5 != 0)
   1702          PRE_MEM_READ( "mq_timedsend(abs_timeout)", ARG5,
   1703                         sizeof(struct vki_timespec) );
   1704    }
   1705 }
   1706 
   1707 PRE(sys_mq_timedreceive)
   1708 {
   1709    *flags |= SfMayBlock;
   1710    PRINT("sys_mq_timedreceive( %ld, %#lx, %llu, %#lx, %#lx )",
   1711          ARG1,ARG2,(ULong)ARG3,ARG4,ARG5);
   1712    PRE_REG_READ5(ssize_t, "mq_timedreceive",
   1713                  vki_mqd_t, mqdes, char *, msg_ptr, vki_size_t, msg_len,
   1714                  unsigned int *, msg_prio,
   1715                  const struct timespec *, abs_timeout);
   1716    if (!ML_(fd_allowed)(ARG1, "mq_timedreceive", tid, False)) {
   1717       SET_STATUS_Failure( VKI_EBADF );
   1718    } else {
   1719       PRE_MEM_WRITE( "mq_timedreceive(msg_ptr)", ARG2, ARG3 );
   1720       if (ARG4 != 0)
   1721          PRE_MEM_WRITE( "mq_timedreceive(msg_prio)",
   1722                         ARG4, sizeof(unsigned int) );
   1723       if (ARG5 != 0)
   1724          PRE_MEM_READ( "mq_timedreceive(abs_timeout)",
   1725                         ARG5, sizeof(struct vki_timespec) );
   1726    }
   1727 }
   1728 POST(sys_mq_timedreceive)
   1729 {
   1730    POST_MEM_WRITE( ARG2, RES );
   1731    if (ARG4 != 0)
   1732       POST_MEM_WRITE( ARG4, sizeof(unsigned int) );
   1733 }
   1734 
   1735 PRE(sys_mq_notify)
   1736 {
   1737    PRINT("sys_mq_notify( %ld, %#lx )", ARG1,ARG2 );
   1738    PRE_REG_READ2(long, "mq_notify",
   1739                  vki_mqd_t, mqdes, const struct sigevent *, notification);
   1740    if (!ML_(fd_allowed)(ARG1, "mq_notify", tid, False))
   1741       SET_STATUS_Failure( VKI_EBADF );
   1742    else if (ARG2 != 0)
   1743       PRE_MEM_READ( "mq_notify(notification)",
   1744                     ARG2, sizeof(struct vki_sigevent) );
   1745 }
   1746 
   1747 PRE(sys_mq_getsetattr)
   1748 {
   1749    PRINT("sys_mq_getsetattr( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3 );
   1750    PRE_REG_READ3(long, "mq_getsetattr",
   1751                  vki_mqd_t, mqdes, const struct mq_attr *, mqstat,
   1752                  struct mq_attr *, omqstat);
   1753    if (!ML_(fd_allowed)(ARG1, "mq_getsetattr", tid, False)) {
   1754       SET_STATUS_Failure( VKI_EBADF );
   1755    } else {
   1756       if (ARG2 != 0) {
   1757          const struct vki_mq_attr *attr = (struct vki_mq_attr *)ARG2;
   1758          PRE_MEM_READ( "mq_getsetattr(mqstat->mq_flags)",
   1759                         (Addr)&attr->mq_flags, sizeof(attr->mq_flags) );
   1760       }
   1761       if (ARG3 != 0)
   1762          PRE_MEM_WRITE( "mq_getsetattr(omqstat)", ARG3,
   1763                         sizeof(struct vki_mq_attr) );
   1764    }
   1765 }
   1766 POST(sys_mq_getsetattr)
   1767 {
   1768    if (ARG3 != 0)
   1769       POST_MEM_WRITE( ARG3, sizeof(struct vki_mq_attr) );
   1770 }
   1771 
   1772 /* ---------------------------------------------------------------------
   1773    clock_* wrappers
   1774    ------------------------------------------------------------------ */
   1775 
   1776 PRE(sys_clock_settime)
   1777 {
   1778    PRINT("sys_clock_settime( %ld, %#lx )", ARG1,ARG2);
   1779    PRE_REG_READ2(long, "clock_settime",
   1780                  vki_clockid_t, clk_id, const struct timespec *, tp);
   1781    PRE_MEM_READ( "clock_settime(tp)", ARG2, sizeof(struct vki_timespec) );
   1782 }
   1783 
   1784 PRE(sys_clock_gettime)
   1785 {
   1786    PRINT("sys_clock_gettime( %ld, %#lx )" , ARG1,ARG2);
   1787    PRE_REG_READ2(long, "clock_gettime",
   1788                  vki_clockid_t, clk_id, struct timespec *, tp);
   1789    PRE_MEM_WRITE( "clock_gettime(tp)", ARG2, sizeof(struct vki_timespec) );
   1790 }
   1791 POST(sys_clock_gettime)
   1792 {
   1793    POST_MEM_WRITE( ARG2, sizeof(struct vki_timespec) );
   1794 }
   1795 
   1796 PRE(sys_clock_getres)
   1797 {
   1798    PRINT("sys_clock_getres( %ld, %#lx )" , ARG1,ARG2);
   1799    // Nb: we can't use "RES" as the param name because that's a macro
   1800    // defined above!
   1801    PRE_REG_READ2(long, "clock_getres",
   1802                  vki_clockid_t, clk_id, struct timespec *, res);
   1803    if (ARG2 != 0)
   1804       PRE_MEM_WRITE( "clock_getres(res)", ARG2, sizeof(struct vki_timespec) );
   1805 }
   1806 POST(sys_clock_getres)
   1807 {
   1808    if (ARG2 != 0)
   1809       POST_MEM_WRITE( ARG2, sizeof(struct vki_timespec) );
   1810 }
   1811 
   1812 PRE(sys_clock_nanosleep)
   1813 {
   1814    *flags |= SfMayBlock|SfPostOnFail;
   1815    PRINT("sys_clock_nanosleep( %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4);
   1816    PRE_REG_READ4(int32_t, "clock_nanosleep",
   1817                  vki_clockid_t, clkid, int, flags,
   1818                  const struct timespec *, rqtp, struct timespec *, rmtp);
   1819    PRE_MEM_READ( "clock_nanosleep(rqtp)", ARG3, sizeof(struct vki_timespec) );
   1820    if (ARG4 != 0)
   1821       PRE_MEM_WRITE( "clock_nanosleep(rmtp)", ARG4, sizeof(struct vki_timespec) );
   1822 }
   1823 POST(sys_clock_nanosleep)
   1824 {
   1825    if (ARG4 != 0 && FAILURE && ERR == VKI_EINTR)
   1826       POST_MEM_WRITE( ARG4, sizeof(struct vki_timespec) );
   1827 }
   1828 
   1829 /* ---------------------------------------------------------------------
   1830    timer_* wrappers
   1831    ------------------------------------------------------------------ */
   1832 
   1833 PRE(sys_timer_create)
   1834 {
   1835    PRINT("sys_timer_create( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3);
   1836    PRE_REG_READ3(long, "timer_create",
   1837                  vki_clockid_t, clockid, struct sigevent *, evp,
   1838                  vki_timer_t *, timerid);
   1839    if (ARG2 != 0)
   1840       PRE_MEM_READ( "timer_create(evp)", ARG2, sizeof(struct vki_sigevent) );
   1841    PRE_MEM_WRITE( "timer_create(timerid)", ARG3, sizeof(vki_timer_t) );
   1842 }
   1843 POST(sys_timer_create)
   1844 {
   1845    POST_MEM_WRITE( ARG3, sizeof(vki_timer_t) );
   1846 }
   1847 
   1848 PRE(sys_timer_settime)
   1849 {
   1850    PRINT("sys_timer_settime( %lld, %ld, %#lx, %#lx )", (ULong)ARG1,ARG2,ARG3,ARG4);
   1851    PRE_REG_READ4(long, "timer_settime",
   1852                  vki_timer_t, timerid, int, flags,
   1853                  const struct itimerspec *, value,
   1854                  struct itimerspec *, ovalue);
   1855    PRE_MEM_READ( "timer_settime(value)", ARG3,
   1856                   sizeof(struct vki_itimerspec) );
   1857    if (ARG4 != 0)
   1858        PRE_MEM_WRITE( "timer_settime(ovalue)", ARG4,
   1859                       sizeof(struct vki_itimerspec) );
   1860 }
   1861 POST(sys_timer_settime)
   1862 {
   1863    if (ARG4 != 0)
   1864       POST_MEM_WRITE( ARG4, sizeof(struct vki_itimerspec) );
   1865 }
   1866 
   1867 PRE(sys_timer_gettime)
   1868 {
   1869    PRINT("sys_timer_gettime( %lld, %#lx )", (ULong)ARG1,ARG2);
   1870    PRE_REG_READ2(long, "timer_gettime",
   1871                  vki_timer_t, timerid, struct itimerspec *, value);
   1872    PRE_MEM_WRITE( "timer_gettime(value)", ARG2,
   1873                   sizeof(struct vki_itimerspec));
   1874 }
   1875 POST(sys_timer_gettime)
   1876 {
   1877    POST_MEM_WRITE( ARG2, sizeof(struct vki_itimerspec) );
   1878 }
   1879 
   1880 PRE(sys_timer_getoverrun)
   1881 {
   1882    PRINT("sys_timer_getoverrun( %#lx )", ARG1);
   1883    PRE_REG_READ1(long, "timer_getoverrun", vki_timer_t, timerid);
   1884 }
   1885 
   1886 PRE(sys_timer_delete)
   1887 {
   1888    PRINT("sys_timer_delete( %#lx )", ARG1);
   1889    PRE_REG_READ1(long, "timer_delete", vki_timer_t, timerid);
   1890 }
   1891 
   1892 /* ---------------------------------------------------------------------
   1893    timerfd* wrappers
   1894    See also http://lwn.net/Articles/260172/ for an overview.
   1895    See also /usr/src/linux/fs/timerfd.c for the implementation.
   1896    ------------------------------------------------------------------ */
   1897 
   1898 /* Returns True if running on 2.6.22, else False (or False if
   1899    cannot be determined). */
   1900 static Bool linux_kernel_2_6_22(void)
   1901 {
   1902    static Int result = -1;
   1903    Int fd, read;
   1904    HChar release[64];
   1905    SysRes res;
   1906 
   1907    if (result == -1) {
   1908       res = VG_(open)("/proc/sys/kernel/osrelease", 0, 0);
   1909       if (sr_isError(res))
   1910          return False;
   1911       fd = sr_Res(res);
   1912       read = VG_(read)(fd, release, sizeof(release) - 1);
   1913       vg_assert(read >= 0);
   1914       release[read] = 0;
   1915       VG_(close)(fd);
   1916       //VG_(printf)("kernel release = %s\n", release);
   1917       result = (VG_(strncmp)(release, "2.6.22", 6) == 0
   1918                 && (release[6] < '0' || release[6] > '9'));
   1919    }
   1920    vg_assert(result == 0 || result == 1);
   1921    return result == 1;
   1922 }
   1923 
   1924 PRE(sys_timerfd_create)
   1925 {
   1926    if (linux_kernel_2_6_22()) {
   1927       /* 2.6.22 kernel: timerfd system call. */
   1928       PRINT("sys_timerfd ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
   1929       PRE_REG_READ3(long, "sys_timerfd",
   1930                     int, fd, int, clockid, const struct itimerspec *, tmr);
   1931       PRE_MEM_READ("timerfd(tmr)", ARG3,
   1932                    sizeof(struct vki_itimerspec) );
   1933       if ((Word)ARG1 != -1L && !ML_(fd_allowed)(ARG1, "timerfd", tid, False))
   1934          SET_STATUS_Failure( VKI_EBADF );
   1935    } else {
   1936       /* 2.6.24 and later kernels: timerfd_create system call. */
   1937       PRINT("sys_timerfd_create (%ld, %ld )", ARG1, ARG2);
   1938       PRE_REG_READ2(long, "timerfd_create", int, clockid, int, flags);
   1939    }
   1940 }
   1941 POST(sys_timerfd_create)
   1942 {
   1943    if (linux_kernel_2_6_22())
   1944    {
   1945       /* 2.6.22 kernel: timerfd system call. */
   1946       if (!ML_(fd_allowed)(RES, "timerfd", tid, True)) {
   1947          VG_(close)(RES);
   1948          SET_STATUS_Failure( VKI_EMFILE );
   1949       } else {
   1950          if (VG_(clo_track_fds))
   1951             ML_(record_fd_open_nameless) (tid, RES);
   1952       }
   1953    }
   1954    else
   1955    {
   1956       /* 2.6.24 and later kernels: timerfd_create system call. */
   1957       if (!ML_(fd_allowed)(RES, "timerfd_create", tid, True)) {
   1958          VG_(close)(RES);
   1959          SET_STATUS_Failure( VKI_EMFILE );
   1960       } else {
   1961          if (VG_(clo_track_fds))
   1962             ML_(record_fd_open_nameless) (tid, RES);
   1963       }
   1964    }
   1965 }
   1966 
   1967 PRE(sys_timerfd_gettime)
   1968 {
   1969    PRINT("sys_timerfd_gettime ( %ld, %#lx )", ARG1, ARG2);
   1970    PRE_REG_READ2(long, "timerfd_gettime",
   1971                  int, ufd,
   1972                  struct vki_itimerspec*, otmr);
   1973    if (!ML_(fd_allowed)(ARG1, "timerfd_gettime", tid, False))
   1974       SET_STATUS_Failure(VKI_EBADF);
   1975    else
   1976       PRE_MEM_WRITE("timerfd_gettime(result)",
   1977                     ARG2, sizeof(struct vki_itimerspec));
   1978 }
   1979 POST(sys_timerfd_gettime)
   1980 {
   1981    if (RES == 0)
   1982       POST_MEM_WRITE(ARG2, sizeof(struct vki_itimerspec));
   1983 }
   1984 
   1985 PRE(sys_timerfd_settime)
   1986 {
   1987    PRINT("sys_timerfd_settime ( %ld, %ld, %#lx, %#lx )", ARG1, ARG2, ARG3, ARG4);
   1988    PRE_REG_READ4(long, "timerfd_settime",
   1989                  int, ufd,
   1990                  int, flags,
   1991                  const struct vki_itimerspec*, utmr,
   1992                  struct vki_itimerspec*, otmr);
   1993    if (!ML_(fd_allowed)(ARG1, "timerfd_settime", tid, False))
   1994       SET_STATUS_Failure(VKI_EBADF);
   1995    else
   1996    {
   1997       PRE_MEM_READ("timerfd_settime(result)",
   1998                    ARG3, sizeof(struct vki_itimerspec));
   1999       if (ARG4)
   2000       {
   2001          PRE_MEM_WRITE("timerfd_settime(result)",
   2002                        ARG4, sizeof(struct vki_itimerspec));
   2003       }
   2004    }
   2005 }
   2006 POST(sys_timerfd_settime)
   2007 {
   2008    if (RES == 0 && ARG4 != 0)
   2009       POST_MEM_WRITE(ARG4, sizeof(struct vki_itimerspec));
   2010 }
   2011 
   2012 /* ---------------------------------------------------------------------
   2013    capabilities wrappers
   2014    ------------------------------------------------------------------ */
   2015 
   2016 PRE(sys_capget)
   2017 {
   2018    PRINT("sys_capget ( %#lx, %#lx )", ARG1, ARG2 );
   2019    PRE_REG_READ2(long, "capget",
   2020                  vki_cap_user_header_t, header, vki_cap_user_data_t, data);
   2021    PRE_MEM_READ( "capget(header)", ARG1,
   2022                   sizeof(struct __vki_user_cap_header_struct) );
   2023    PRE_MEM_WRITE( "capget(data)", ARG2,
   2024                   sizeof(struct __vki_user_cap_data_struct) );
   2025 }
   2026 POST(sys_capget)
   2027 {
   2028    if (ARG2 != (Addr)NULL)
   2029       POST_MEM_WRITE( ARG2, sizeof(struct __vki_user_cap_data_struct) );
   2030 }
   2031 
   2032 PRE(sys_capset)
   2033 {
   2034    PRINT("sys_capset ( %#lx, %#lx )", ARG1, ARG2 );
   2035    PRE_REG_READ2(long, "capset",
   2036                  vki_cap_user_header_t, header,
   2037                  const vki_cap_user_data_t, data);
   2038    PRE_MEM_READ( "capset(header)",
   2039                   ARG1, sizeof(struct __vki_user_cap_header_struct) );
   2040    PRE_MEM_READ( "capset(data)",
   2041                   ARG2, sizeof(struct __vki_user_cap_data_struct) );
   2042 }
   2043 
   2044 /* ---------------------------------------------------------------------
   2045    16-bit uid/gid/groups wrappers
   2046    ------------------------------------------------------------------ */
   2047 
   2048 PRE(sys_getuid16)
   2049 {
   2050    PRINT("sys_getuid16 ( )");
   2051    PRE_REG_READ0(long, "getuid16");
   2052 }
   2053 
   2054 PRE(sys_setuid16)
   2055 {
   2056    PRINT("sys_setuid16 ( %ld )", ARG1);
   2057    PRE_REG_READ1(long, "setuid16", vki_old_uid_t, uid);
   2058 }
   2059 
   2060 PRE(sys_getgid16)
   2061 {
   2062    PRINT("sys_getgid16 ( )");
   2063    PRE_REG_READ0(long, "getgid16");
   2064 }
   2065 
   2066 PRE(sys_setgid16)
   2067 {
   2068    PRINT("sys_setgid16 ( %ld )", ARG1);
   2069    PRE_REG_READ1(long, "setgid16", vki_old_gid_t, gid);
   2070 }
   2071 
   2072 PRE(sys_geteuid16)
   2073 {
   2074    PRINT("sys_geteuid16 ( )");
   2075    PRE_REG_READ0(long, "geteuid16");
   2076 }
   2077 
   2078 PRE(sys_getegid16)
   2079 {
   2080    PRINT("sys_getegid16 ( )");
   2081    PRE_REG_READ0(long, "getegid16");
   2082 }
   2083 
   2084 PRE(sys_setreuid16)
   2085 {
   2086    PRINT("setreuid16 ( 0x%lx, 0x%lx )", ARG1, ARG2);
   2087    PRE_REG_READ2(long, "setreuid16", vki_old_uid_t, ruid, vki_old_uid_t, euid);
   2088 }
   2089 
   2090 PRE(sys_setregid16)
   2091 {
   2092    PRINT("sys_setregid16 ( %ld, %ld )", ARG1, ARG2);
   2093    PRE_REG_READ2(long, "setregid16", vki_old_gid_t, rgid, vki_old_gid_t, egid);
   2094 }
   2095 
   2096 PRE(sys_getgroups16)
   2097 {
   2098    PRINT("sys_getgroups16 ( %ld, %#lx )", ARG1, ARG2);
   2099    PRE_REG_READ2(long, "getgroups16", int, size, vki_old_gid_t *, list);
   2100    if (ARG1 > 0)
   2101       PRE_MEM_WRITE( "getgroups16(list)", ARG2, ARG1 * sizeof(vki_old_gid_t) );
   2102 }
   2103 POST(sys_getgroups16)
   2104 {
   2105    vg_assert(SUCCESS);
   2106    if (ARG1 > 0 && RES > 0)
   2107       POST_MEM_WRITE( ARG2, RES * sizeof(vki_old_gid_t) );
   2108 }
   2109 
   2110 PRE(sys_setgroups16)
   2111 {
   2112    PRINT("sys_setgroups16 ( %llu, %#lx )", (ULong)ARG1, ARG2);
   2113    PRE_REG_READ2(long, "setgroups16", int, size, vki_old_gid_t *, list);
   2114    if (ARG1 > 0)
   2115       PRE_MEM_READ( "setgroups16(list)", ARG2, ARG1 * sizeof(vki_old_gid_t) );
   2116 }
   2117 
   2118 /* ---------------------------------------------------------------------
   2119    *chown16 wrappers
   2120    ------------------------------------------------------------------ */
   2121 
   2122 PRE(sys_chown16)
   2123 {
   2124    PRINT("sys_chown16 ( %#lx, 0x%lx, 0x%lx )", ARG1,ARG2,ARG3);
   2125    PRE_REG_READ3(long, "chown16",
   2126                  const char *, path,
   2127                  vki_old_uid_t, owner, vki_old_gid_t, group);
   2128    PRE_MEM_RASCIIZ( "chown16(path)", ARG1 );
   2129 }
   2130 
   2131 PRE(sys_fchown16)
   2132 {
   2133    PRINT("sys_fchown16 ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   2134    PRE_REG_READ3(long, "fchown16",
   2135                  unsigned int, fd, vki_old_uid_t, owner, vki_old_gid_t, group);
   2136 }
   2137 
   2138 /* ---------------------------------------------------------------------
   2139    *xattr wrappers
   2140    ------------------------------------------------------------------ */
   2141 
   2142 PRE(sys_setxattr)
   2143 {
   2144    *flags |= SfMayBlock;
   2145    PRINT("sys_setxattr ( %#lx, %#lx, %#lx, %llu, %ld )",
   2146          ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
   2147    PRE_REG_READ5(long, "setxattr",
   2148                  char *, path, char *, name,
   2149                  void *, value, vki_size_t, size, int, flags);
   2150    PRE_MEM_RASCIIZ( "setxattr(path)", ARG1 );
   2151    PRE_MEM_RASCIIZ( "setxattr(name)", ARG2 );
   2152    PRE_MEM_READ( "setxattr(value)", ARG3, ARG4 );
   2153 }
   2154 
   2155 PRE(sys_lsetxattr)
   2156 {
   2157    *flags |= SfMayBlock;
   2158    PRINT("sys_lsetxattr ( %#lx, %#lx, %#lx, %llu, %ld )",
   2159          ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
   2160    PRE_REG_READ5(long, "lsetxattr",
   2161                  char *, path, char *, name,
   2162                  void *, value, vki_size_t, size, int, flags);
   2163    PRE_MEM_RASCIIZ( "lsetxattr(path)", ARG1 );
   2164    PRE_MEM_RASCIIZ( "lsetxattr(name)", ARG2 );
   2165    PRE_MEM_READ( "lsetxattr(value)", ARG3, ARG4 );
   2166 }
   2167 
   2168 PRE(sys_fsetxattr)
   2169 {
   2170    *flags |= SfMayBlock;
   2171    PRINT("sys_fsetxattr ( %ld, %#lx, %#lx, %llu, %ld )",
   2172          ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
   2173    PRE_REG_READ5(long, "fsetxattr",
   2174                  int, fd, char *, name, void *, value,
   2175                  vki_size_t, size, int, flags);
   2176    PRE_MEM_RASCIIZ( "fsetxattr(name)", ARG2 );
   2177    PRE_MEM_READ( "fsetxattr(value)", ARG3, ARG4 );
   2178 }
   2179 
   2180 PRE(sys_getxattr)
   2181 {
   2182    *flags |= SfMayBlock;
   2183    PRINT("sys_getxattr ( %#lx, %#lx, %#lx, %llu )", ARG1,ARG2,ARG3, (ULong)ARG4);
   2184    PRE_REG_READ4(ssize_t, "getxattr",
   2185                  char *, path, char *, name, void *, value, vki_size_t, size);
   2186    PRE_MEM_RASCIIZ( "getxattr(path)", ARG1 );
   2187    PRE_MEM_RASCIIZ( "getxattr(name)", ARG2 );
   2188    PRE_MEM_WRITE( "getxattr(value)", ARG3, ARG4 );
   2189 }
   2190 POST(sys_getxattr)
   2191 {
   2192    vg_assert(SUCCESS);
   2193    if (RES > 0 && ARG3 != (Addr)NULL) {
   2194       POST_MEM_WRITE( ARG3, RES );
   2195    }
   2196 }
   2197 
   2198 PRE(sys_lgetxattr)
   2199 {
   2200    *flags |= SfMayBlock;
   2201    PRINT("sys_lgetxattr ( %#lx, %#lx, %#lx, %llu )", ARG1,ARG2,ARG3, (ULong)ARG4);
   2202    PRE_REG_READ4(ssize_t, "lgetxattr",
   2203                  char *, path, char *, name, void *, value, vki_size_t, size);
   2204    PRE_MEM_RASCIIZ( "lgetxattr(path)", ARG1 );
   2205    PRE_MEM_RASCIIZ( "lgetxattr(name)", ARG2 );
   2206    PRE_MEM_WRITE( "lgetxattr(value)", ARG3, ARG4 );
   2207 }
   2208 POST(sys_lgetxattr)
   2209 {
   2210    vg_assert(SUCCESS);
   2211    if (RES > 0 && ARG3 != (Addr)NULL) {
   2212       POST_MEM_WRITE( ARG3, RES );
   2213    }
   2214 }
   2215 
   2216 PRE(sys_fgetxattr)
   2217 {
   2218    *flags |= SfMayBlock;
   2219    PRINT("sys_fgetxattr ( %ld, %#lx, %#lx, %llu )", ARG1, ARG2, ARG3, (ULong)ARG4);
   2220    PRE_REG_READ4(ssize_t, "fgetxattr",
   2221                  int, fd, char *, name, void *, value, vki_size_t, size);
   2222    PRE_MEM_RASCIIZ( "fgetxattr(name)", ARG2 );
   2223    PRE_MEM_WRITE( "fgetxattr(value)", ARG3, ARG4 );
   2224 }
   2225 POST(sys_fgetxattr)
   2226 {
   2227    if (RES > 0 && ARG3 != (Addr)NULL)
   2228       POST_MEM_WRITE( ARG3, RES );
   2229 }
   2230 
   2231 PRE(sys_listxattr)
   2232 {
   2233    *flags |= SfMayBlock;
   2234    PRINT("sys_listxattr ( %#lx, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
   2235    PRE_REG_READ3(ssize_t, "listxattr",
   2236                  char *, path, char *, list, vki_size_t, size);
   2237    PRE_MEM_RASCIIZ( "listxattr(path)", ARG1 );
   2238    PRE_MEM_WRITE( "listxattr(list)", ARG2, ARG3 );
   2239 }
   2240 POST(sys_listxattr)
   2241 {
   2242    if (RES > 0 && ARG2 != (Addr)NULL)
   2243       POST_MEM_WRITE( ARG2, RES );
   2244 }
   2245 
   2246 PRE(sys_llistxattr)
   2247 {
   2248    *flags |= SfMayBlock;
   2249    PRINT("sys_llistxattr ( %#lx, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
   2250    PRE_REG_READ3(ssize_t, "llistxattr",
   2251                  char *, path, char *, list, vki_size_t, size);
   2252    PRE_MEM_RASCIIZ( "llistxattr(path)", ARG1 );
   2253    PRE_MEM_WRITE( "llistxattr(list)", ARG2, ARG3 );
   2254 }
   2255 POST(sys_llistxattr)
   2256 {
   2257    if (RES > 0 && ARG2 != (Addr)NULL)
   2258       POST_MEM_WRITE( ARG2, RES );
   2259 }
   2260 
   2261 PRE(sys_flistxattr)
   2262 {
   2263    *flags |= SfMayBlock;
   2264    PRINT("sys_flistxattr ( %ld, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
   2265    PRE_REG_READ3(ssize_t, "flistxattr",
   2266                  int, fd, char *, list, vki_size_t, size);
   2267    PRE_MEM_WRITE( "flistxattr(list)", ARG2, ARG3 );
   2268 }
   2269 POST(sys_flistxattr)
   2270 {
   2271    if (RES > 0 && ARG2 != (Addr)NULL)
   2272       POST_MEM_WRITE( ARG2, RES );
   2273 }
   2274 
   2275 PRE(sys_removexattr)
   2276 {
   2277    *flags |= SfMayBlock;
   2278    PRINT("sys_removexattr ( %#lx, %#lx )", ARG1, ARG2);
   2279    PRE_REG_READ2(long, "removexattr", char *, path, char *, name);
   2280    PRE_MEM_RASCIIZ( "removexattr(path)", ARG1 );
   2281    PRE_MEM_RASCIIZ( "removexattr(name)", ARG2 );
   2282 }
   2283 
   2284 PRE(sys_lremovexattr)
   2285 {
   2286    *flags |= SfMayBlock;
   2287    PRINT("sys_lremovexattr ( %#lx, %#lx )", ARG1, ARG2);
   2288    PRE_REG_READ2(long, "lremovexattr", char *, path, char *, name);
   2289    PRE_MEM_RASCIIZ( "lremovexattr(path)", ARG1 );
   2290    PRE_MEM_RASCIIZ( "lremovexattr(name)", ARG2 );
   2291 }
   2292 
   2293 PRE(sys_fremovexattr)
   2294 {
   2295    *flags |= SfMayBlock;
   2296    PRINT("sys_fremovexattr ( %ld, %#lx )", ARG1, ARG2);
   2297    PRE_REG_READ2(long, "fremovexattr", int, fd, char *, name);
   2298    PRE_MEM_RASCIIZ( "fremovexattr(name)", ARG2 );
   2299 }
   2300 
   2301 /* ---------------------------------------------------------------------
   2302    sched_* wrappers
   2303    ------------------------------------------------------------------ */
   2304 
   2305 PRE(sys_sched_setparam)
   2306 {
   2307    PRINT("sched_setparam ( %ld, %#lx )", ARG1, ARG2 );
   2308    PRE_REG_READ2(long, "sched_setparam",
   2309                  vki_pid_t, pid, struct sched_param *, p);
   2310    PRE_MEM_READ( "sched_setparam(p)", ARG2, sizeof(struct vki_sched_param) );
   2311 }
   2312 POST(sys_sched_setparam)
   2313 {
   2314    POST_MEM_WRITE( ARG2, sizeof(struct vki_sched_param) );
   2315 }
   2316 
   2317 PRE(sys_sched_getparam)
   2318 {
   2319    PRINT("sched_getparam ( %ld, %#lx )", ARG1, ARG2 );
   2320    PRE_REG_READ2(long, "sched_getparam",
   2321                  vki_pid_t, pid, struct sched_param *, p);
   2322    PRE_MEM_WRITE( "sched_getparam(p)", ARG2, sizeof(struct vki_sched_param) );
   2323 }
   2324 POST(sys_sched_getparam)
   2325 {
   2326    POST_MEM_WRITE( ARG2, sizeof(struct vki_sched_param) );
   2327 }
   2328 
   2329 PRE(sys_sched_getscheduler)
   2330 {
   2331    PRINT("sys_sched_getscheduler ( %ld )", ARG1);
   2332    PRE_REG_READ1(long, "sched_getscheduler", vki_pid_t, pid);
   2333 }
   2334 
   2335 PRE(sys_sched_setscheduler)
   2336 {
   2337    PRINT("sys_sched_setscheduler ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
   2338    PRE_REG_READ3(long, "sched_setscheduler",
   2339                  vki_pid_t, pid, int, policy, struct sched_param *, p);
   2340    if (ARG3 != 0)
   2341       PRE_MEM_READ( "sched_setscheduler(p)",
   2342 		    ARG3, sizeof(struct vki_sched_param));
   2343 }
   2344 
   2345 PRE(sys_sched_yield)
   2346 {
   2347    *flags |= SfMayBlock;
   2348    PRINT("sched_yield()");
   2349    PRE_REG_READ0(long, "sys_sched_yield");
   2350 }
   2351 
   2352 PRE(sys_sched_get_priority_max)
   2353 {
   2354    PRINT("sched_get_priority_max ( %ld )", ARG1);
   2355    PRE_REG_READ1(long, "sched_get_priority_max", int, policy);
   2356 }
   2357 
   2358 PRE(sys_sched_get_priority_min)
   2359 {
   2360    PRINT("sched_get_priority_min ( %ld )", ARG1);
   2361    PRE_REG_READ1(long, "sched_get_priority_min", int, policy);
   2362 }
   2363 
   2364 PRE(sys_sched_rr_get_interval)
   2365 {
   2366    PRINT("sys_sched_rr_get_interval ( %ld, %#lx )", ARG1, ARG2);
   2367    PRE_REG_READ2(int, "sched_rr_get_interval",
   2368                  vki_pid_t, pid,
   2369                  struct vki_timespec *, tp);
   2370    PRE_MEM_WRITE("sched_rr_get_interval(timespec)",
   2371                  ARG2, sizeof(struct vki_timespec));
   2372 }
   2373 
   2374 POST(sys_sched_rr_get_interval)
   2375 {
   2376    POST_MEM_WRITE(ARG2, sizeof(struct vki_timespec));
   2377 }
   2378 
   2379 PRE(sys_sched_setaffinity)
   2380 {
   2381    PRINT("sched_setaffinity ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
   2382    PRE_REG_READ3(long, "sched_setaffinity",
   2383                  vki_pid_t, pid, unsigned int, len, unsigned long *, mask);
   2384    PRE_MEM_READ( "sched_setaffinity(mask)", ARG3, ARG2);
   2385 }
   2386 
   2387 PRE(sys_sched_getaffinity)
   2388 {
   2389    PRINT("sched_getaffinity ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
   2390    PRE_REG_READ3(long, "sched_getaffinity",
   2391                  vki_pid_t, pid, unsigned int, len, unsigned long *, mask);
   2392    PRE_MEM_WRITE( "sched_getaffinity(mask)", ARG3, ARG2);
   2393 }
   2394 POST(sys_sched_getaffinity)
   2395 {
   2396    POST_MEM_WRITE(ARG3, ARG2);
   2397 }
   2398 
   2399 /* ---------------------------------------------------------------------
   2400    miscellaneous wrappers
   2401    ------------------------------------------------------------------ */
   2402 
   2403 PRE(sys_munlockall)
   2404 {
   2405    *flags |= SfMayBlock;
   2406    PRINT("sys_munlockall ( )");
   2407    PRE_REG_READ0(long, "munlockall");
   2408 }
   2409 
   2410 // This has different signatures for different platforms.
   2411 //
   2412 //  x86:   int  sys_pipe(unsigned long __user *fildes);
   2413 //  AMD64: long sys_pipe(int *fildes);
   2414 //  ppc32: int  sys_pipe(int __user *fildes);
   2415 //  ppc64: int  sys_pipe(int __user *fildes);
   2416 //
   2417 // The type of the argument is most important, and it is an array of 32 bit
   2418 // values in all cases.  (The return type differs across platforms, but it
   2419 // is not used.)  So we use 'int' as its type.  This fixed bug #113230 which
   2420 // was caused by using an array of 'unsigned long's, which didn't work on
   2421 // AMD64.
   2422 PRE(sys_pipe)
   2423 {
   2424    PRINT("sys_pipe ( %#lx )", ARG1);
   2425    PRE_REG_READ1(int, "pipe", int *, filedes);
   2426    PRE_MEM_WRITE( "pipe(filedes)", ARG1, 2*sizeof(int) );
   2427 }
   2428 POST(sys_pipe)
   2429 {
   2430    Int *p = (Int *)ARG1;
   2431    if (!ML_(fd_allowed)(p[0], "pipe", tid, True) ||
   2432        !ML_(fd_allowed)(p[1], "pipe", tid, True)) {
   2433       VG_(close)(p[0]);
   2434       VG_(close)(p[1]);
   2435       SET_STATUS_Failure( VKI_EMFILE );
   2436    } else {
   2437       POST_MEM_WRITE( ARG1, 2*sizeof(int) );
   2438       if (VG_(clo_track_fds)) {
   2439          ML_(record_fd_open_nameless)(tid, p[0]);
   2440          ML_(record_fd_open_nameless)(tid, p[1]);
   2441       }
   2442    }
   2443 }
   2444 
   2445 /* pipe2 (a kernel 2.6.twentysomething invention) is like pipe, except
   2446    there's a second arg containing flags to be applied to the new file
   2447    descriptors.  It hardly seems worth the effort to factor out the
   2448    duplicated code, hence: */
   2449 PRE(sys_pipe2)
   2450 {
   2451    PRINT("sys_pipe2 ( %#lx, %#lx )", ARG1, ARG2);
   2452    PRE_REG_READ2(int, "pipe", int *, filedes, long, flags);
   2453    PRE_MEM_WRITE( "pipe2(filedes)", ARG1, 2*sizeof(int) );
   2454 }
   2455 POST(sys_pipe2)
   2456 {
   2457    Int *p = (Int *)ARG1;
   2458    if (!ML_(fd_allowed)(p[0], "pipe2", tid, True) ||
   2459        !ML_(fd_allowed)(p[1], "pipe2", tid, True)) {
   2460       VG_(close)(p[0]);
   2461       VG_(close)(p[1]);
   2462       SET_STATUS_Failure( VKI_EMFILE );
   2463    } else {
   2464       POST_MEM_WRITE( ARG1, 2*sizeof(int) );
   2465       if (VG_(clo_track_fds)) {
   2466          ML_(record_fd_open_nameless)(tid, p[0]);
   2467          ML_(record_fd_open_nameless)(tid, p[1]);
   2468       }
   2469    }
   2470 }
   2471 
   2472 PRE(sys_dup3)
   2473 {
   2474    PRINT("sys_dup3 ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   2475    PRE_REG_READ3(long, "dup3", unsigned int, oldfd, unsigned int, newfd, int, flags);
   2476    if (!ML_(fd_allowed)(ARG2, "dup3", tid, True))
   2477       SET_STATUS_Failure( VKI_EBADF );
   2478 }
   2479 
   2480 POST(sys_dup3)
   2481 {
   2482    vg_assert(SUCCESS);
   2483    if (VG_(clo_track_fds))
   2484       ML_(record_fd_open_named)(tid, RES);
   2485 }
   2486 
   2487 PRE(sys_quotactl)
   2488 {
   2489    PRINT("sys_quotactl (0x%lx, %#lx, 0x%lx, 0x%lx )", ARG1,ARG2,ARG3, ARG4);
   2490    PRE_REG_READ4(long, "quotactl",
   2491                  unsigned int, cmd, const char *, special, vki_qid_t, id,
   2492                  void *, addr);
   2493    PRE_MEM_RASCIIZ( "quotactl(special)", ARG2 );
   2494 }
   2495 
   2496 PRE(sys_waitid)
   2497 {
   2498    *flags |= SfMayBlock;
   2499    PRINT("sys_waitid( %ld, %ld, %#lx, %ld, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
   2500    PRE_REG_READ5(int32_t, "sys_waitid",
   2501                  int, which, vki_pid_t, pid, struct vki_siginfo *, infop,
   2502                  int, options, struct vki_rusage *, ru);
   2503    PRE_MEM_WRITE( "waitid(infop)", ARG3, sizeof(struct vki_siginfo) );
   2504    if (ARG5 != 0)
   2505       PRE_MEM_WRITE( "waitid(ru)", ARG5, sizeof(struct vki_rusage) );
   2506 }
   2507 POST(sys_waitid)
   2508 {
   2509    POST_MEM_WRITE( ARG3, sizeof(struct vki_siginfo) );
   2510    if (ARG5 != 0)
   2511       POST_MEM_WRITE( ARG5, sizeof(struct vki_rusage) );
   2512 }
   2513 
   2514 PRE(sys_sync_file_range)
   2515 {
   2516    *flags |= SfMayBlock;
   2517 #if VG_WORDSIZE == 4
   2518    PRINT("sys_sync_file_range ( %ld, %lld, %lld, %ld )",
   2519          ARG1,MERGE64(ARG2,ARG3),MERGE64(ARG4,ARG5),ARG6);
   2520    PRE_REG_READ6(long, "sync_file_range",
   2521                  int, fd,
   2522                  unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
   2523                  unsigned, MERGE64_FIRST(nbytes), unsigned, MERGE64_SECOND(nbytes),
   2524                  unsigned int, flags);
   2525 #elif VG_WORDSIZE == 8
   2526    PRINT("sys_sync_file_range ( %ld, %lld, %lld, %ld )",
   2527          ARG1,(Long)ARG2,(Long)ARG3,ARG4);
   2528    PRE_REG_READ4(long, "sync_file_range",
   2529                  int, fd, vki_loff_t, offset, vki_loff_t, nbytes,
   2530                  unsigned int, flags);
   2531 #else
   2532 #  error Unexpected word size
   2533 #endif
   2534    if (!ML_(fd_allowed)(ARG1, "sync_file_range", tid, False))
   2535       SET_STATUS_Failure( VKI_EBADF );
   2536 }
   2537 
   2538 PRE(sys_sync_file_range2)
   2539 {
   2540    *flags |= SfMayBlock;
   2541 #if VG_WORDSIZE == 4
   2542    PRINT("sys_sync_file_range2 ( %ld, %ld, %lld, %lld )",
   2543          ARG1,ARG2,MERGE64(ARG3,ARG4),MERGE64(ARG5,ARG6));
   2544    PRE_REG_READ6(long, "sync_file_range2",
   2545                  int, fd, unsigned int, flags,
   2546                  unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
   2547                  unsigned, MERGE64_FIRST(nbytes), unsigned, MERGE64_SECOND(nbytes));
   2548 #elif VG_WORDSIZE == 8
   2549    PRINT("sys_sync_file_range2 ( %ld, %ld, %lld, %lld )",
   2550          ARG1,ARG2,(Long)ARG3,(Long)ARG4);
   2551    PRE_REG_READ4(long, "sync_file_range2",
   2552                  int, fd, unsigned int, flags,
   2553                  vki_loff_t, offset, vki_loff_t, nbytes);
   2554 #else
   2555 #  error Unexpected word size
   2556 #endif
   2557    if (!ML_(fd_allowed)(ARG1, "sync_file_range2", tid, False))
   2558       SET_STATUS_Failure( VKI_EBADF );
   2559 }
   2560 
   2561 PRE(sys_stime)
   2562 {
   2563    PRINT("sys_stime ( %#lx )", ARG1);
   2564    PRE_REG_READ1(int, "stime", vki_time_t*, t);
   2565    PRE_MEM_READ( "stime(t)", ARG1, sizeof(vki_time_t) );
   2566 }
   2567 
   2568 PRE(sys_perf_counter_open)
   2569 {
   2570    PRINT("sys_perf_counter_open ( %#lx, %ld, %ld, %ld, %ld )",
   2571          ARG1,ARG2,ARG3,ARG4,ARG5);
   2572    PRE_REG_READ5(long, "perf_counter_open",
   2573                  struct vki_perf_counter_attr *, attr,
   2574                  vki_pid_t, pid, int, cpu, int, group_fd,
   2575                  unsigned long, flags);
   2576    PRE_MEM_READ( "perf_counter_open(attr)",
   2577                  ARG1, sizeof(struct vki_perf_counter_attr) );
   2578 }
   2579 
   2580 POST(sys_perf_counter_open)
   2581 {
   2582    vg_assert(SUCCESS);
   2583    if (!ML_(fd_allowed)(RES, "perf_counter_open", tid, True)) {
   2584       VG_(close)(RES);
   2585       SET_STATUS_Failure( VKI_EMFILE );
   2586    } else {
   2587       if (VG_(clo_track_fds))
   2588          ML_(record_fd_open_nameless)(tid, RES);
   2589    }
   2590 }
   2591 
   2592 PRE(sys_getcpu)
   2593 {
   2594    PRINT("sys_getcpu ( %#lx, %#lx, %#lx )" , ARG1,ARG2,ARG3);
   2595    PRE_REG_READ3(int, "getcpu",
   2596                  unsigned *, cpu, unsigned *, node, struct vki_getcpu_cache *, tcache);
   2597    if (ARG1 != 0)
   2598       PRE_MEM_WRITE( "getcpu(cpu)", ARG1, sizeof(unsigned) );
   2599    if (ARG2 != 0)
   2600       PRE_MEM_WRITE( "getcpu(node)", ARG2, sizeof(unsigned) );
   2601    if (ARG3 != 0)
   2602       PRE_MEM_WRITE( "getcpu(tcache)", ARG3, sizeof(struct vki_getcpu_cache) );
   2603 }
   2604 
   2605 POST(sys_getcpu)
   2606 {
   2607    if (ARG1 != 0)
   2608       POST_MEM_WRITE( ARG1, sizeof(unsigned) );
   2609    if (ARG2 != 0)
   2610       POST_MEM_WRITE( ARG2, sizeof(unsigned) );
   2611    if (ARG3 != 0)
   2612       POST_MEM_WRITE( ARG3, sizeof(struct vki_getcpu_cache) );
   2613 }
   2614 
   2615 /* ---------------------------------------------------------------------
   2616    utime wrapper
   2617    ------------------------------------------------------------------ */
   2618 
   2619 PRE(sys_utime)
   2620 {
   2621    *flags |= SfMayBlock;
   2622    PRINT("sys_utime ( %#lx, %#lx )", ARG1,ARG2);
   2623    PRE_REG_READ2(long, "utime", char *, filename, struct utimbuf *, buf);
   2624    PRE_MEM_RASCIIZ( "utime(filename)", ARG1 );
   2625    if (ARG2 != 0)
   2626       PRE_MEM_READ( "utime(buf)", ARG2, sizeof(struct vki_utimbuf) );
   2627 }
   2628 
   2629 /* ---------------------------------------------------------------------
   2630    lseek wrapper
   2631    ------------------------------------------------------------------ */
   2632 
   2633 PRE(sys_lseek)
   2634 {
   2635    PRINT("sys_lseek ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   2636    PRE_REG_READ3(vki_off_t, "lseek",
   2637                  unsigned int, fd, vki_off_t, offset, unsigned int, whence);
   2638 }
   2639 
   2640 /* ---------------------------------------------------------------------
   2641    readahead wrapper
   2642    ------------------------------------------------------------------ */
   2643 
   2644 PRE(sys_readahead)
   2645 {
   2646    *flags |= SfMayBlock;
   2647 #if VG_WORDSIZE == 4
   2648    PRINT("sys_readahead ( %ld, %lld, %ld )", ARG1, MERGE64(ARG2,ARG3), ARG4);
   2649    PRE_REG_READ4(vki_off_t, "readahead",
   2650                  int, fd, unsigned, MERGE64_FIRST(offset),
   2651                  unsigned, MERGE64_SECOND(offset), vki_size_t, count);
   2652 #elif VG_WORDSIZE == 8
   2653    PRINT("sys_readahead ( %ld, %lld, %ld )", ARG1, (Long)ARG2, ARG3);
   2654    PRE_REG_READ3(vki_off_t, "readahead",
   2655                  int, fd, vki_loff_t, offset, vki_size_t, count);
   2656 #else
   2657 #  error Unexpected word size
   2658 #endif
   2659    if (!ML_(fd_allowed)(ARG1, "readahead", tid, False))
   2660       SET_STATUS_Failure( VKI_EBADF );
   2661 }
   2662 
   2663 /* ---------------------------------------------------------------------
   2664    sig* wrappers
   2665    ------------------------------------------------------------------ */
   2666 
   2667 PRE(sys_sigpending)
   2668 {
   2669    PRINT( "sys_sigpending ( %#lx )", ARG1 );
   2670    PRE_REG_READ1(long, "sigpending", vki_old_sigset_t *, set);
   2671    PRE_MEM_WRITE( "sigpending(set)", ARG1, sizeof(vki_old_sigset_t));
   2672 }
   2673 POST(sys_sigpending)
   2674 {
   2675    POST_MEM_WRITE( ARG1, sizeof(vki_old_sigset_t) ) ;
   2676 }
   2677 
   2678 // This syscall is not used on amd64/Linux -- it only provides
   2679 // sys_rt_sigprocmask, which uses sigset_t rather than old_sigset_t.
   2680 // This wrapper is only suitable for 32-bit architectures.
   2681 // (XXX: so how is it that PRE(sys_sigpending) above doesn't need
   2682 // conditional compilation like this?)
   2683 #if defined(VGP_x86_linux) || defined(VGP_ppc32_linux) || defined(VGP_arm_linux)
   2684 PRE(sys_sigprocmask)
   2685 {
   2686    vki_old_sigset_t* set;
   2687    vki_old_sigset_t* oldset;
   2688    vki_sigset_t bigger_set;
   2689    vki_sigset_t bigger_oldset;
   2690 
   2691    PRINT("sys_sigprocmask ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
   2692    PRE_REG_READ3(long, "sigprocmask",
   2693                  int, how, vki_old_sigset_t *, set, vki_old_sigset_t *, oldset);
   2694    if (ARG2 != 0)
   2695       PRE_MEM_READ( "sigprocmask(set)", ARG2, sizeof(vki_old_sigset_t));
   2696    if (ARG3 != 0)
   2697       PRE_MEM_WRITE( "sigprocmask(oldset)", ARG3, sizeof(vki_old_sigset_t));
   2698 
   2699    // Nb: We must convert the smaller vki_old_sigset_t params into bigger
   2700    // vki_sigset_t params.
   2701    set    = (vki_old_sigset_t*)ARG2;
   2702    oldset = (vki_old_sigset_t*)ARG3;
   2703 
   2704    VG_(memset)(&bigger_set,    0, sizeof(vki_sigset_t));
   2705    VG_(memset)(&bigger_oldset, 0, sizeof(vki_sigset_t));
   2706    if (set)
   2707       bigger_set.sig[0] = *(vki_old_sigset_t*)set;
   2708 
   2709    SET_STATUS_from_SysRes(
   2710       VG_(do_sys_sigprocmask) ( tid, ARG1 /*how*/,
   2711                                 set ? &bigger_set    : NULL,
   2712                              oldset ? &bigger_oldset : NULL)
   2713    );
   2714 
   2715    if (oldset)
   2716       *oldset = bigger_oldset.sig[0];
   2717 
   2718    if (SUCCESS)
   2719       *flags |= SfPollAfter;
   2720 }
   2721 POST(sys_sigprocmask)
   2722 {
   2723    vg_assert(SUCCESS);
   2724    if (RES == 0 && ARG3 != 0)
   2725       POST_MEM_WRITE( ARG3, sizeof(vki_old_sigset_t));
   2726 }
   2727 
   2728 /* Convert from non-RT to RT sigset_t's */
   2729 static
   2730 void convert_sigset_to_rt(const vki_old_sigset_t *oldset, vki_sigset_t *set)
   2731 {
   2732    VG_(sigemptyset)(set);
   2733    set->sig[0] = *oldset;
   2734 }
   2735 PRE(sys_sigaction)
   2736 {
   2737    vki_sigaction_toK_t   new, *newp;
   2738    vki_sigaction_fromK_t old, *oldp;
   2739 
   2740    PRINT("sys_sigaction ( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3);
   2741    PRE_REG_READ3(int, "sigaction",
   2742                  int, signum, const struct old_sigaction *, act,
   2743                  struct old_sigaction *, oldact);
   2744 
   2745    newp = oldp = NULL;
   2746 
   2747    if (ARG2 != 0) {
   2748       struct vki_old_sigaction *sa = (struct vki_old_sigaction *)ARG2;
   2749       PRE_MEM_READ( "sigaction(act->sa_handler)", (Addr)&sa->ksa_handler, sizeof(sa->ksa_handler));
   2750       PRE_MEM_READ( "sigaction(act->sa_mask)", (Addr)&sa->sa_mask, sizeof(sa->sa_mask));
   2751       PRE_MEM_READ( "sigaction(act->sa_flags)", (Addr)&sa->sa_flags, sizeof(sa->sa_flags));
   2752       if (ML_(safe_to_deref)(sa,sizeof(sa))
   2753           && (sa->sa_flags & VKI_SA_RESTORER))
   2754          PRE_MEM_READ( "sigaction(act->sa_restorer)", (Addr)&sa->sa_restorer, sizeof(sa->sa_restorer));
   2755    }
   2756 
   2757    if (ARG3 != 0) {
   2758       PRE_MEM_WRITE( "sigaction(oldact)", ARG3, sizeof(struct vki_old_sigaction));
   2759       oldp = &old;
   2760    }
   2761 
   2762    //jrs 20050207: what?!  how can this make any sense?
   2763    //if (VG_(is_kerror)(SYSRES))
   2764    //   return;
   2765 
   2766    if (ARG2 != 0) {
   2767       struct vki_old_sigaction *oldnew = (struct vki_old_sigaction *)ARG2;
   2768       new.ksa_handler = oldnew->ksa_handler;
   2769       new.sa_flags    = oldnew->sa_flags;
   2770       new.sa_restorer = oldnew->sa_restorer;
   2771       convert_sigset_to_rt(&oldnew->sa_mask, &new.sa_mask);
   2772       newp = &new;
   2773    }
   2774 
   2775    SET_STATUS_from_SysRes( VG_(do_sys_sigaction)(ARG1, newp, oldp) );
   2776 
   2777    if (ARG3 != 0 && SUCCESS && RES == 0) {
   2778       struct vki_old_sigaction *oldold = (struct vki_old_sigaction *)ARG3;
   2779       oldold->ksa_handler = oldp->ksa_handler;
   2780       oldold->sa_flags    = oldp->sa_flags;
   2781       oldold->sa_restorer = oldp->sa_restorer;
   2782       oldold->sa_mask = oldp->sa_mask.sig[0];
   2783    }
   2784 }
   2785 
   2786 POST(sys_sigaction)
   2787 {
   2788    vg_assert(SUCCESS);
   2789    if (RES == 0 && ARG3 != 0)
   2790       POST_MEM_WRITE( ARG3, sizeof(struct vki_old_sigaction));
   2791 }
   2792 
   2793 PRE(sys_sigsuspend)
   2794 {
   2795    /* The C library interface to sigsuspend just takes a pointer to
   2796       a signal mask but this system call has three arguments - the first
   2797       two don't appear to be used by the kernel and are always passed as
   2798       zero by glibc and the third is the first word of the signal mask
   2799       so only 32 signals are supported.
   2800 
   2801       In fact glibc normally uses rt_sigsuspend if it is available as
   2802       that takes a pointer to the signal mask so supports more signals.
   2803     */
   2804    *flags |= SfMayBlock;
   2805    PRINT("sys_sigsuspend ( %ld, %ld, %ld )", ARG1,ARG2,ARG3 );
   2806    PRE_REG_READ3(int, "sigsuspend",
   2807                  int, history0, int, history1,
   2808                  vki_old_sigset_t, mask);
   2809 }
   2810 #endif
   2811 
   2812 PRE(sys_signalfd)
   2813 {
   2814    PRINT("sys_signalfd ( %d, %#lx, %llu )", (Int)ARG1,ARG2,(ULong)ARG3);
   2815    PRE_REG_READ3(long, "sys_signalfd",
   2816                  int, fd, vki_sigset_t *, sigmask, vki_size_t, sigsetsize);
   2817    PRE_MEM_READ( "signalfd(sigmask)", ARG2, sizeof(vki_sigset_t) );
   2818    if ((int)ARG1 != -1 && !ML_(fd_allowed)(ARG1, "signalfd", tid, False))
   2819       SET_STATUS_Failure( VKI_EBADF );
   2820 }
   2821 POST(sys_signalfd)
   2822 {
   2823    if (!ML_(fd_allowed)(RES, "signalfd", tid, True)) {
   2824       VG_(close)(RES);
   2825       SET_STATUS_Failure( VKI_EMFILE );
   2826    } else {
   2827       if (VG_(clo_track_fds))
   2828          ML_(record_fd_open_nameless) (tid, RES);
   2829    }
   2830 }
   2831 
   2832 PRE(sys_signalfd4)
   2833 {
   2834    PRINT("sys_signalfd4 ( %d, %#lx, %llu, %ld )", (Int)ARG1,ARG2,(ULong)ARG3,ARG4);
   2835    PRE_REG_READ4(long, "sys_signalfd4",
   2836                  int, fd, vki_sigset_t *, sigmask, vki_size_t, sigsetsize, int, flags);
   2837    PRE_MEM_READ( "signalfd(sigmask)", ARG2, sizeof(vki_sigset_t) );
   2838    if ((int)ARG1 != -1 && !ML_(fd_allowed)(ARG1, "signalfd", tid, False))
   2839       SET_STATUS_Failure( VKI_EBADF );
   2840 }
   2841 POST(sys_signalfd4)
   2842 {
   2843    if (!ML_(fd_allowed)(RES, "signalfd4", tid, True)) {
   2844       VG_(close)(RES);
   2845       SET_STATUS_Failure( VKI_EMFILE );
   2846    } else {
   2847       if (VG_(clo_track_fds))
   2848          ML_(record_fd_open_nameless) (tid, RES);
   2849    }
   2850 }
   2851 
   2852 
   2853 /* ---------------------------------------------------------------------
   2854    rt_sig* wrappers
   2855    ------------------------------------------------------------------ */
   2856 
   2857 PRE(sys_rt_sigaction)
   2858 {
   2859    PRINT("sys_rt_sigaction ( %ld, %#lx, %#lx, %ld )", ARG1,ARG2,ARG3,ARG4);
   2860    PRE_REG_READ4(long, "rt_sigaction",
   2861                  int, signum, const struct sigaction *, act,
   2862                  struct sigaction *, oldact, vki_size_t, sigsetsize);
   2863 
   2864    if (ARG2 != 0) {
   2865       vki_sigaction_toK_t *sa = (vki_sigaction_toK_t *)ARG2;
   2866       PRE_MEM_READ( "rt_sigaction(act->sa_handler)", (Addr)&sa->ksa_handler, sizeof(sa->ksa_handler));
   2867       PRE_MEM_READ( "rt_sigaction(act->sa_mask)", (Addr)&sa->sa_mask, sizeof(sa->sa_mask));
   2868       PRE_MEM_READ( "rt_sigaction(act->sa_flags)", (Addr)&sa->sa_flags, sizeof(sa->sa_flags));
   2869       if (sa->sa_flags & VKI_SA_RESTORER)
   2870          PRE_MEM_READ( "rt_sigaction(act->sa_restorer)", (Addr)&sa->sa_restorer, sizeof(sa->sa_restorer));
   2871    }
   2872    if (ARG3 != 0)
   2873       PRE_MEM_WRITE( "rt_sigaction(oldact)", ARG3, sizeof(vki_sigaction_fromK_t));
   2874 
   2875    // XXX: doesn't seem right to be calling do_sys_sigaction for
   2876    // sys_rt_sigaction... perhaps this function should be renamed
   2877    // VG_(do_sys_rt_sigaction)()  --njn
   2878 
   2879    SET_STATUS_from_SysRes(
   2880       VG_(do_sys_sigaction)(ARG1, (const vki_sigaction_toK_t *)ARG2,
   2881                             (vki_sigaction_fromK_t *)ARG3)
   2882    );
   2883 }
   2884 POST(sys_rt_sigaction)
   2885 {
   2886    vg_assert(SUCCESS);
   2887    if (RES == 0 && ARG3 != 0)
   2888       POST_MEM_WRITE( ARG3, sizeof(vki_sigaction_fromK_t));
   2889 }
   2890 
   2891 PRE(sys_rt_sigprocmask)
   2892 {
   2893    PRINT("sys_rt_sigprocmask ( %ld, %#lx, %#lx, %llu )",ARG1,ARG2,ARG3,(ULong)ARG4);
   2894    PRE_REG_READ4(long, "rt_sigprocmask",
   2895                  int, how, vki_sigset_t *, set, vki_sigset_t *, oldset,
   2896                  vki_size_t, sigsetsize);
   2897    if (ARG2 != 0)
   2898       PRE_MEM_READ( "rt_sigprocmask(set)", ARG2, sizeof(vki_sigset_t));
   2899    if (ARG3 != 0)
   2900       PRE_MEM_WRITE( "rt_sigprocmask(oldset)", ARG3, sizeof(vki_sigset_t));
   2901 
   2902    // Like the kernel, we fail if the sigsetsize is not exactly what we expect.
   2903    if (sizeof(vki_sigset_t) != ARG4)
   2904       SET_STATUS_Failure( VKI_EMFILE );
   2905    else {
   2906       SET_STATUS_from_SysRes(
   2907                   VG_(do_sys_sigprocmask) ( tid, ARG1 /*how*/,
   2908                                             (vki_sigset_t*) ARG2,
   2909                                             (vki_sigset_t*) ARG3 )
   2910       );
   2911    }
   2912 
   2913    if (SUCCESS)
   2914       *flags |= SfPollAfter;
   2915 }
   2916 POST(sys_rt_sigprocmask)
   2917 {
   2918    vg_assert(SUCCESS);
   2919    if (RES == 0 && ARG3 != 0)
   2920       POST_MEM_WRITE( ARG3, sizeof(vki_sigset_t));
   2921 }
   2922 
   2923 PRE(sys_rt_sigpending)
   2924 {
   2925    PRINT( "sys_rt_sigpending ( %#lx )", ARG1 );
   2926    PRE_REG_READ2(long, "rt_sigpending",
   2927                  vki_sigset_t *, set, vki_size_t, sigsetsize);
   2928    PRE_MEM_WRITE( "rt_sigpending(set)", ARG1, sizeof(vki_sigset_t));
   2929 }
   2930 POST(sys_rt_sigpending)
   2931 {
   2932    POST_MEM_WRITE( ARG1, sizeof(vki_sigset_t) ) ;
   2933 }
   2934 
   2935 PRE(sys_rt_sigtimedwait)
   2936 {
   2937    *flags |= SfMayBlock;
   2938    PRINT("sys_rt_sigtimedwait ( %#lx, %#lx, %#lx, %lld )",
   2939          ARG1,ARG2,ARG3,(ULong)ARG4);
   2940    PRE_REG_READ4(long, "rt_sigtimedwait",
   2941                  const vki_sigset_t *, set, vki_siginfo_t *, info,
   2942                  const struct timespec *, timeout, vki_size_t, sigsetsize);
   2943    if (ARG1 != 0)
   2944       PRE_MEM_READ(  "rt_sigtimedwait(set)",  ARG1, sizeof(vki_sigset_t));
   2945    if (ARG2 != 0)
   2946       PRE_MEM_WRITE( "rt_sigtimedwait(info)", ARG2, sizeof(vki_siginfo_t) );
   2947    if (ARG3 != 0)
   2948       PRE_MEM_READ( "rt_sigtimedwait(timeout)",
   2949                     ARG3, sizeof(struct vki_timespec) );
   2950 }
   2951 POST(sys_rt_sigtimedwait)
   2952 {
   2953    if (ARG2 != 0)
   2954       POST_MEM_WRITE( ARG2, sizeof(vki_siginfo_t) );
   2955 }
   2956 
   2957 PRE(sys_rt_sigqueueinfo)
   2958 {
   2959    PRINT("sys_rt_sigqueueinfo(%ld, %ld, %#lx)", ARG1, ARG2, ARG3);
   2960    PRE_REG_READ3(long, "rt_sigqueueinfo",
   2961                  int, pid, int, sig, vki_siginfo_t *, uinfo);
   2962    if (ARG2 != 0)
   2963       PRE_MEM_READ( "rt_sigqueueinfo(uinfo)", ARG3, VKI_SI_MAX_SIZE );
   2964 }
   2965 POST(sys_rt_sigqueueinfo)
   2966 {
   2967    if (!ML_(client_signal_OK)(ARG2))
   2968       SET_STATUS_Failure( VKI_EINVAL );
   2969 }
   2970 
   2971 PRE(sys_rt_tgsigqueueinfo)
   2972 {
   2973    PRINT("sys_rt_tgsigqueueinfo(%ld, %ld, %ld, %#lx)", ARG1, ARG2, ARG3, ARG4);
   2974    PRE_REG_READ4(long, "rt_tgsigqueueinfo",
   2975                  int, tgid, int, pid, int, sig, vki_siginfo_t *, uinfo);
   2976    if (ARG3 != 0)
   2977       PRE_MEM_READ( "rt_tgsigqueueinfo(uinfo)", ARG4, VKI_SI_MAX_SIZE );
   2978 }
   2979 
   2980 POST(sys_rt_tgsigqueueinfo)
   2981 {
   2982    if (!ML_(client_signal_OK)(ARG3))
   2983       SET_STATUS_Failure( VKI_EINVAL );
   2984 }
   2985 
   2986 // XXX: x86-specific?  The kernel prototypes for the different archs are
   2987 //      hard to decipher.
   2988 PRE(sys_rt_sigsuspend)
   2989 {
   2990    /* The C library interface to sigsuspend just takes a pointer to
   2991       a signal mask but this system call has two arguments - a pointer
   2992       to the mask and the number of bytes used by it. The kernel insists
   2993       on the size being equal to sizeof(sigset_t) however and will just
   2994       return EINVAL if it isn't.
   2995     */
   2996    *flags |= SfMayBlock;
   2997    PRINT("sys_rt_sigsuspend ( %#lx, %ld )", ARG1,ARG2 );
   2998    PRE_REG_READ2(int, "rt_sigsuspend", vki_sigset_t *, mask, vki_size_t, size)
   2999    if (ARG1 != (Addr)NULL) {
   3000       PRE_MEM_READ( "rt_sigsuspend(mask)", ARG1, sizeof(vki_sigset_t) );
   3001    }
   3002 }
   3003 
   3004 /* ---------------------------------------------------------------------
   3005    linux msg* wrapper helpers
   3006    ------------------------------------------------------------------ */
   3007 
   3008 void
   3009 ML_(linux_PRE_sys_msgsnd) ( ThreadId tid,
   3010                             UWord arg0, UWord arg1, UWord arg2, UWord arg3 )
   3011 {
   3012    /* int msgsnd(int msqid, struct msgbuf *msgp, size_t msgsz, int msgflg); */
   3013    struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
   3014    PRE_MEM_READ( "msgsnd(msgp->mtype)", (Addr)&msgp->mtype, sizeof(msgp->mtype) );
   3015    PRE_MEM_READ( "msgsnd(msgp->mtext)", (Addr)&msgp->mtext, arg2 );
   3016 }
   3017 
   3018 void
   3019 ML_(linux_PRE_sys_msgrcv) ( ThreadId tid,
   3020                             UWord arg0, UWord arg1, UWord arg2,
   3021                             UWord arg3, UWord arg4 )
   3022 {
   3023    /* ssize_t msgrcv(int msqid, struct msgbuf *msgp, size_t msgsz,
   3024                      long msgtyp, int msgflg); */
   3025    struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
   3026    PRE_MEM_WRITE( "msgrcv(msgp->mtype)", (Addr)&msgp->mtype, sizeof(msgp->mtype) );
   3027    PRE_MEM_WRITE( "msgrcv(msgp->mtext)", (Addr)&msgp->mtext, arg2 );
   3028 }
   3029 void
   3030 ML_(linux_POST_sys_msgrcv) ( ThreadId tid,
   3031                              UWord res,
   3032                              UWord arg0, UWord arg1, UWord arg2,
   3033                              UWord arg3, UWord arg4 )
   3034 {
   3035    struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
   3036    POST_MEM_WRITE( (Addr)&msgp->mtype, sizeof(msgp->mtype) );
   3037    POST_MEM_WRITE( (Addr)&msgp->mtext, res );
   3038 }
   3039 
   3040 void
   3041 ML_(linux_PRE_sys_msgctl) ( ThreadId tid,
   3042                             UWord arg0, UWord arg1, UWord arg2 )
   3043 {
   3044    /* int msgctl(int msqid, int cmd, struct msqid_ds *buf); */
   3045    switch (arg1 /* cmd */) {
   3046    case VKI_IPC_INFO:
   3047    case VKI_MSG_INFO:
   3048    case VKI_IPC_INFO|VKI_IPC_64:
   3049    case VKI_MSG_INFO|VKI_IPC_64:
   3050       PRE_MEM_WRITE( "msgctl(IPC_INFO, buf)",
   3051                      arg2, sizeof(struct vki_msginfo) );
   3052       break;
   3053    case VKI_IPC_STAT:
   3054    case VKI_MSG_STAT:
   3055       PRE_MEM_WRITE( "msgctl(IPC_STAT, buf)",
   3056                      arg2, sizeof(struct vki_msqid_ds) );
   3057       break;
   3058    case VKI_IPC_STAT|VKI_IPC_64:
   3059    case VKI_MSG_STAT|VKI_IPC_64:
   3060       PRE_MEM_WRITE( "msgctl(IPC_STAT, arg.buf)",
   3061                      arg2, sizeof(struct vki_msqid64_ds) );
   3062       break;
   3063    case VKI_IPC_SET:
   3064       PRE_MEM_READ( "msgctl(IPC_SET, arg.buf)",
   3065                     arg2, sizeof(struct vki_msqid_ds) );
   3066       break;
   3067    case VKI_IPC_SET|VKI_IPC_64:
   3068       PRE_MEM_READ( "msgctl(IPC_SET, arg.buf)",
   3069                     arg2, sizeof(struct vki_msqid64_ds) );
   3070       break;
   3071    }
   3072 }
   3073 void
   3074 ML_(linux_POST_sys_msgctl) ( ThreadId tid,
   3075                              UWord res,
   3076                              UWord arg0, UWord arg1, UWord arg2 )
   3077 {
   3078    switch (arg1 /* cmd */) {
   3079    case VKI_IPC_INFO:
   3080    case VKI_MSG_INFO:
   3081    case VKI_IPC_INFO|VKI_IPC_64:
   3082    case VKI_MSG_INFO|VKI_IPC_64:
   3083       POST_MEM_WRITE( arg2, sizeof(struct vki_msginfo) );
   3084       break;
   3085    case VKI_IPC_STAT:
   3086    case VKI_MSG_STAT:
   3087       POST_MEM_WRITE( arg2, sizeof(struct vki_msqid_ds) );
   3088       break;
   3089    case VKI_IPC_STAT|VKI_IPC_64:
   3090    case VKI_MSG_STAT|VKI_IPC_64:
   3091       POST_MEM_WRITE( arg2, sizeof(struct vki_msqid64_ds) );
   3092       break;
   3093    }
   3094 }
   3095 
   3096 /* ---------------------------------------------------------------------
   3097    *at wrappers
   3098    ------------------------------------------------------------------ */
   3099 
   3100 PRE(sys_openat)
   3101 {
   3102    HChar  name[30];
   3103    SysRes sres;
   3104 
   3105    if (ARG3 & VKI_O_CREAT) {
   3106       // 4-arg version
   3107       PRINT("sys_openat ( %ld, %#lx(%s), %ld, %ld )",ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
   3108       PRE_REG_READ4(long, "openat",
   3109                     int, dfd, const char *, filename, int, flags, int, mode);
   3110    } else {
   3111       // 3-arg version
   3112       PRINT("sys_openat ( %ld, %#lx(%s), %ld )",ARG1,ARG2,(char*)ARG2,ARG3);
   3113       PRE_REG_READ3(long, "openat",
   3114                     int, dfd, const char *, filename, int, flags);
   3115    }
   3116 
   3117    if (ARG1 != VKI_AT_FDCWD && !ML_(fd_allowed)(ARG1, "openat", tid, False))
   3118       SET_STATUS_Failure( VKI_EBADF );
   3119    else
   3120       PRE_MEM_RASCIIZ( "openat(filename)", ARG2 );
   3121 
   3122    /* Handle the case where the open is of /proc/self/cmdline or
   3123       /proc/<pid>/cmdline, and just give it a copy of the fd for the
   3124       fake file we cooked up at startup (in m_main).  Also, seek the
   3125       cloned fd back to the start. */
   3126 
   3127    VG_(sprintf)(name, "/proc/%d/cmdline", VG_(getpid)());
   3128    if (ML_(safe_to_deref)( (void*)ARG2, 1 )
   3129        && (VG_(strcmp)((Char *)ARG2, name) == 0
   3130            || VG_(strcmp)((Char *)ARG2, "/proc/self/cmdline") == 0)) {
   3131       sres = VG_(dup)( VG_(cl_cmdline_fd) );
   3132       SET_STATUS_from_SysRes( sres );
   3133       if (!sr_isError(sres)) {
   3134          OffT off = VG_(lseek)( sr_Res(sres), 0, VKI_SEEK_SET );
   3135          if (off < 0)
   3136             SET_STATUS_Failure( VKI_EMFILE );
   3137       }
   3138       return;
   3139    }
   3140 
   3141    /* Otherwise handle normally */
   3142    *flags |= SfMayBlock;
   3143 }
   3144 
   3145 POST(sys_openat)
   3146 {
   3147    vg_assert(SUCCESS);
   3148    if (!ML_(fd_allowed)(RES, "openat", tid, True)) {
   3149       VG_(close)(RES);
   3150       SET_STATUS_Failure( VKI_EMFILE );
   3151    } else {
   3152       if (VG_(clo_track_fds))
   3153          ML_(record_fd_open_with_given_name)(tid, RES, (Char*)ARG2);
   3154    }
   3155 }
   3156 
   3157 PRE(sys_mkdirat)
   3158 {
   3159    *flags |= SfMayBlock;
   3160    PRINT("sys_mkdirat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
   3161    PRE_REG_READ3(long, "mkdirat",
   3162                  int, dfd, const char *, pathname, int, mode);
   3163    PRE_MEM_RASCIIZ( "mkdirat(pathname)", ARG2 );
   3164 }
   3165 
   3166 PRE(sys_mknodat)
   3167 {
   3168   PRINT("sys_mknodat ( %ld, %#lx(%s), 0x%lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4 );
   3169    PRE_REG_READ4(long, "mknodat",
   3170                  int, dfd, const char *, pathname, int, mode, unsigned, dev);
   3171    PRE_MEM_RASCIIZ( "mknodat(pathname)", ARG2 );
   3172 }
   3173 
   3174 PRE(sys_fchownat)
   3175 {
   3176    PRINT("sys_fchownat ( %ld, %#lx(%s), 0x%lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
   3177    PRE_REG_READ4(long, "fchownat",
   3178                  int, dfd, const char *, path,
   3179                  vki_uid_t, owner, vki_gid_t, group);
   3180    PRE_MEM_RASCIIZ( "fchownat(path)", ARG2 );
   3181 }
   3182 
   3183 PRE(sys_futimesat)
   3184 {
   3185    PRINT("sys_futimesat ( %ld, %#lx(%s), %#lx )", ARG1,ARG2,(char*)ARG2,ARG3);
   3186    PRE_REG_READ3(long, "futimesat",
   3187                  int, dfd, char *, filename, struct timeval *, tvp);
   3188    if (ARG2 != 0)
   3189       PRE_MEM_RASCIIZ( "futimesat(filename)", ARG2 );
   3190    if (ARG3 != 0)
   3191       PRE_MEM_READ( "futimesat(tvp)", ARG3, 2 * sizeof(struct vki_timeval) );
   3192 }
   3193 
   3194 PRE(sys_utimensat)
   3195 {
   3196    PRINT("sys_utimensat ( %ld, %#lx(%s), %#lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
   3197    PRE_REG_READ4(long, "utimensat",
   3198                  int, dfd, char *, filename, struct timespec *, utimes, int, flags);
   3199    if (ARG2 != 0)
   3200       PRE_MEM_RASCIIZ( "utimensat(filename)", ARG2 );
   3201    if (ARG3 != 0)
   3202       PRE_MEM_READ( "utimensat(tvp)", ARG3, 2 * sizeof(struct vki_timespec) );
   3203 }
   3204 
   3205 PRE(sys_newfstatat)
   3206 {
   3207    PRINT("sys_newfstatat ( %ld, %#lx(%s), %#lx )", ARG1,ARG2,(char*)ARG2,ARG3);
   3208    PRE_REG_READ3(long, "fstatat",
   3209                  int, dfd, char *, file_name, struct stat *, buf);
   3210    PRE_MEM_RASCIIZ( "fstatat(file_name)", ARG2 );
   3211    PRE_MEM_WRITE( "fstatat(buf)", ARG3, sizeof(struct vki_stat) );
   3212 }
   3213 
   3214 POST(sys_newfstatat)
   3215 {
   3216    POST_MEM_WRITE( ARG3, sizeof(struct vki_stat) );
   3217 }
   3218 
   3219 PRE(sys_unlinkat)
   3220 {
   3221    *flags |= SfMayBlock;
   3222    PRINT("sys_unlinkat ( %ld, %#lx(%s) )", ARG1,ARG2,(char*)ARG2);
   3223    PRE_REG_READ2(long, "unlinkat", int, dfd, const char *, pathname);
   3224    PRE_MEM_RASCIIZ( "unlinkat(pathname)", ARG2 );
   3225 }
   3226 
   3227 PRE(sys_renameat)
   3228 {
   3229    PRINT("sys_renameat ( %ld, %#lx(%s), %ld, %#lx(%s) )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4,(char*)ARG4);
   3230    PRE_REG_READ4(long, "renameat",
   3231                  int, olddfd, const char *, oldpath,
   3232                  int, newdfd, const char *, newpath);
   3233    PRE_MEM_RASCIIZ( "renameat(oldpath)", ARG2 );
   3234    PRE_MEM_RASCIIZ( "renameat(newpath)", ARG4 );
   3235 }
   3236 
   3237 PRE(sys_linkat)
   3238 {
   3239    *flags |= SfMayBlock;
   3240    PRINT("sys_linkat ( %ld, %#lx(%s), %ld, %#lx(%s), %ld )",ARG1,ARG2,(char*)ARG2,ARG3,ARG4,(char*)ARG4,ARG5);
   3241    PRE_REG_READ5(long, "linkat",
   3242                  int, olddfd, const char *, oldpath,
   3243                  int, newdfd, const char *, newpath,
   3244                  int, flags);
   3245    PRE_MEM_RASCIIZ( "linkat(oldpath)", ARG2);
   3246    PRE_MEM_RASCIIZ( "linkat(newpath)", ARG4);
   3247 }
   3248 
   3249 PRE(sys_symlinkat)
   3250 {
   3251    *flags |= SfMayBlock;
   3252    PRINT("sys_symlinkat ( %#lx(%s), %ld, %#lx(%s) )",ARG1,(char*)ARG1,ARG2,ARG3,(char*)ARG3);
   3253    PRE_REG_READ3(long, "symlinkat",
   3254                  const char *, oldpath, int, newdfd, const char *, newpath);
   3255    PRE_MEM_RASCIIZ( "symlinkat(oldpath)", ARG1 );
   3256    PRE_MEM_RASCIIZ( "symlinkat(newpath)", ARG3 );
   3257 }
   3258 
   3259 PRE(sys_readlinkat)
   3260 {
   3261    HChar name[25];
   3262    Word  saved = SYSNO;
   3263 
   3264    PRINT("sys_readlinkat ( %ld, %#lx(%s), %#lx, %llu )", ARG1,ARG2,(char*)ARG2,ARG3,(ULong)ARG4);
   3265    PRE_REG_READ4(long, "readlinkat",
   3266                  int, dfd, const char *, path, char *, buf, int, bufsiz);
   3267    PRE_MEM_RASCIIZ( "readlinkat(path)", ARG2 );
   3268    PRE_MEM_WRITE( "readlinkat(buf)", ARG3,ARG4 );
   3269 
   3270    /*
   3271     * Handle the case where readlinkat is looking at /proc/self/exe or
   3272     * /proc/<pid>/exe.
   3273     */
   3274    VG_(sprintf)(name, "/proc/%d/exe", VG_(getpid)());
   3275    if (ML_(safe_to_deref)((void*)ARG2, 1)
   3276        && (VG_(strcmp)((Char *)ARG2, name) == 0
   3277            || VG_(strcmp)((Char *)ARG2, "/proc/self/exe") == 0)) {
   3278       VG_(sprintf)(name, "/proc/self/fd/%d", VG_(cl_exec_fd));
   3279       SET_STATUS_from_SysRes( VG_(do_syscall4)(saved, ARG1, (UWord)name,
   3280                                                       ARG3, ARG4));
   3281    } else {
   3282       /* Normal case */
   3283       SET_STATUS_from_SysRes( VG_(do_syscall4)(saved, ARG1, ARG2, ARG3, ARG4));
   3284    }
   3285 
   3286    if (SUCCESS && RES > 0)
   3287       POST_MEM_WRITE( ARG3, RES );
   3288 }
   3289 
   3290 PRE(sys_fchmodat)
   3291 {
   3292    PRINT("sys_fchmodat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
   3293    PRE_REG_READ3(long, "fchmodat",
   3294                  int, dfd, const char *, path, vki_mode_t, mode);
   3295    PRE_MEM_RASCIIZ( "fchmodat(path)", ARG2 );
   3296 }
   3297 
   3298 PRE(sys_faccessat)
   3299 {
   3300    PRINT("sys_faccessat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
   3301    PRE_REG_READ3(long, "faccessat",
   3302                  int, dfd, const char *, pathname, int, mode);
   3303    PRE_MEM_RASCIIZ( "faccessat(pathname)", ARG2 );
   3304 }
   3305 
   3306 /* ---------------------------------------------------------------------
   3307    p{read,write}v wrappers
   3308    ------------------------------------------------------------------ */
   3309 
   3310 PRE(sys_preadv)
   3311 {
   3312    Int i;
   3313    struct vki_iovec * vec;
   3314    *flags |= SfMayBlock;
   3315 #if VG_WORDSIZE == 4
   3316    /* Note that the offset argument here is in lo+hi order on both
   3317       big and little endian platforms... */
   3318    PRINT("sys_preadv ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,LOHI64(ARG4,ARG5));
   3319    PRE_REG_READ5(ssize_t, "preadv",
   3320                  unsigned long, fd, const struct iovec *, vector,
   3321                  unsigned long, count, vki_u32, offset_low,
   3322                  vki_u32, offset_high);
   3323 #elif VG_WORDSIZE == 8
   3324    PRINT("sys_preadv ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,(Long)ARG4);
   3325    PRE_REG_READ4(ssize_t, "preadv",
   3326                  unsigned long, fd, const struct iovec *, vector,
   3327                  unsigned long, count, Word, offset);
   3328 #else
   3329 #  error Unexpected word size
   3330 #endif
   3331    if (!ML_(fd_allowed)(ARG1, "preadv", tid, False)) {
   3332       SET_STATUS_Failure( VKI_EBADF );
   3333    } else {
   3334       PRE_MEM_READ( "preadv(vector)", ARG2, ARG3 * sizeof(struct vki_iovec) );
   3335 
   3336       if (ARG2 != 0) {
   3337          /* ToDo: don't do any of the following if the vector is invalid */
   3338          vec = (struct vki_iovec *)ARG2;
   3339          for (i = 0; i < (Int)ARG3; i++)
   3340             PRE_MEM_WRITE( "preadv(vector[...])",
   3341                            (Addr)vec[i].iov_base, vec[i].iov_len );
   3342       }
   3343    }
   3344 }
   3345 
   3346 POST(sys_preadv)
   3347 {
   3348    vg_assert(SUCCESS);
   3349    if (RES > 0) {
   3350       Int i;
   3351       struct vki_iovec * vec = (struct vki_iovec *)ARG2;
   3352       Int remains = RES;
   3353 
   3354       /* RES holds the number of bytes read. */
   3355       for (i = 0; i < (Int)ARG3; i++) {
   3356 	 Int nReadThisBuf = vec[i].iov_len;
   3357 	 if (nReadThisBuf > remains) nReadThisBuf = remains;
   3358 	 POST_MEM_WRITE( (Addr)vec[i].iov_base, nReadThisBuf );
   3359 	 remains -= nReadThisBuf;
   3360 	 if (remains < 0) VG_(core_panic)("preadv: remains < 0");
   3361       }
   3362    }
   3363 }
   3364 
   3365 PRE(sys_pwritev)
   3366 {
   3367    Int i;
   3368    struct vki_iovec * vec;
   3369    *flags |= SfMayBlock;
   3370 #if VG_WORDSIZE == 4
   3371    /* Note that the offset argument here is in lo+hi order on both
   3372       big and little endian platforms... */
   3373    PRINT("sys_pwritev ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,LOHI64(ARG4,ARG5));
   3374    PRE_REG_READ5(ssize_t, "pwritev",
   3375                  unsigned long, fd, const struct iovec *, vector,
   3376                  unsigned long, count, vki_u32, offset_low,
   3377                  vki_u32, offset_high);
   3378 #elif VG_WORDSIZE == 8
   3379    PRINT("sys_pwritev ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,(Long)ARG4);
   3380    PRE_REG_READ4(ssize_t, "pwritev",
   3381                  unsigned long, fd, const struct iovec *, vector,
   3382                  unsigned long, count, Word, offset);
   3383 #else
   3384 #  error Unexpected word size
   3385 #endif
   3386    if (!ML_(fd_allowed)(ARG1, "pwritev", tid, False)) {
   3387       SET_STATUS_Failure( VKI_EBADF );
   3388    } else {
   3389       PRE_MEM_READ( "pwritev(vector)",
   3390 		     ARG2, ARG3 * sizeof(struct vki_iovec) );
   3391       if (ARG2 != 0) {
   3392          /* ToDo: don't do any of the following if the vector is invalid */
   3393          vec = (struct vki_iovec *)ARG2;
   3394          for (i = 0; i < (Int)ARG3; i++)
   3395             PRE_MEM_READ( "pwritev(vector[...])",
   3396                            (Addr)vec[i].iov_base, vec[i].iov_len );
   3397       }
   3398    }
   3399 }
   3400 
   3401 /* ---------------------------------------------------------------------
   3402    key retention service wrappers
   3403    ------------------------------------------------------------------ */
   3404 
   3405 PRE(sys_request_key)
   3406 {
   3407    PRINT("sys_request_key ( %#lx(%s), %#lx(%s), %#lx(%s), %ld )",
   3408          ARG1,(char*)ARG1,ARG2,(char*)ARG2,ARG3,(char*)ARG3,ARG4);
   3409    PRE_REG_READ4(long, "request_key",
   3410                  const char *, type, const char *, description,
   3411                  const char *, callout_info, vki_key_serial_t, keyring);
   3412    PRE_MEM_RASCIIZ( "request_key(type)", ARG1);
   3413    PRE_MEM_RASCIIZ( "request_key(description)", ARG2);
   3414    if (ARG3 != (UWord)NULL)
   3415       PRE_MEM_RASCIIZ( "request_key(callout_info)", ARG3);
   3416 }
   3417 
   3418 PRE(sys_add_key)
   3419 {
   3420    PRINT("sys_add_key ( %#lx(%s), %#lx(%s), %#lx, %ld, %ld )",
   3421          ARG1,(char*)ARG1,ARG2,(char*)ARG2,ARG3,ARG4,ARG5);
   3422    PRE_REG_READ5(long, "add_key",
   3423                  const char *, type, const char *, description,
   3424                  const void *, payload, vki_size_t, plen,
   3425                  vki_key_serial_t, keyring);
   3426    PRE_MEM_RASCIIZ( "add_key(type)", ARG1);
   3427    PRE_MEM_RASCIIZ( "add_key(description)", ARG2);
   3428    if (ARG3 != (UWord)NULL)
   3429       PRE_MEM_READ( "request_key(payload)", ARG3, ARG4);
   3430 }
   3431 
   3432 PRE(sys_keyctl)
   3433 {
   3434    switch (ARG1 /* option */) {
   3435    case VKI_KEYCTL_GET_KEYRING_ID:
   3436       PRINT("sys_keyctl ( KEYCTL_GET_KEYRING_ID, %ld, %ld )", ARG2,ARG3);
   3437       PRE_REG_READ3(long, "keyctl(KEYCTL_GET_KEYRING_ID)",
   3438                     int, option, vki_key_serial_t, id, int, create);
   3439       break;
   3440    case VKI_KEYCTL_JOIN_SESSION_KEYRING:
   3441       PRINT("sys_keyctl ( KEYCTL_JOIN_SESSION_KEYRING, %#lx(%s) )", ARG2,(char*)ARG2);
   3442       PRE_REG_READ2(long, "keyctl(KEYCTL_JOIN_SESSION_KEYRING)",
   3443                     int, option, const char *, name);
   3444       if (ARG2 != (UWord)NULL)
   3445          PRE_MEM_RASCIIZ("keyctl(KEYCTL_JOIN_SESSION_KEYRING, name)", ARG2);
   3446       break;
   3447    case VKI_KEYCTL_UPDATE:
   3448       PRINT("sys_keyctl ( KEYCTL_UPDATE, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
   3449       PRE_REG_READ4(long, "keyctl(KEYCTL_UPDATE)",
   3450                     int, option, vki_key_serial_t, key,
   3451                     const void *, payload, vki_size_t, plen);
   3452       if (ARG3 != (UWord)NULL)
   3453          PRE_MEM_READ("keyctl(KEYCTL_UPDATE, payload)", ARG3, ARG4);
   3454       break;
   3455    case VKI_KEYCTL_REVOKE:
   3456       PRINT("sys_keyctl ( KEYCTL_REVOKE, %ld )", ARG2);
   3457       PRE_REG_READ2(long, "keyctl(KEYCTL_REVOKE)",
   3458                     int, option, vki_key_serial_t, id);
   3459       break;
   3460    case VKI_KEYCTL_CHOWN:
   3461       PRINT("sys_keyctl ( KEYCTL_CHOWN, %ld, %ld, %ld )", ARG2,ARG3,ARG4);
   3462       PRE_REG_READ4(long, "keyctl(KEYCTL_CHOWN)",
   3463                     int, option, vki_key_serial_t, id,
   3464                     vki_uid_t, uid, vki_gid_t, gid);
   3465       break;
   3466    case VKI_KEYCTL_SETPERM:
   3467       PRINT("sys_keyctl ( KEYCTL_SETPERM, %ld, %ld )", ARG2,ARG3);
   3468       PRE_REG_READ3(long, "keyctl(KEYCTL_SETPERM)",
   3469                     int, option, vki_key_serial_t, id, vki_key_perm_t, perm);
   3470       break;
   3471    case VKI_KEYCTL_DESCRIBE:
   3472       PRINT("sys_keyctl ( KEYCTL_DESCRIBE, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
   3473       PRE_REG_READ4(long, "keyctl(KEYCTL_DESCRIBE)",
   3474                     int, option, vki_key_serial_t, id,
   3475                     char *, buffer, vki_size_t, buflen);
   3476       if (ARG3 != (UWord)NULL)
   3477          PRE_MEM_WRITE("keyctl(KEYCTL_DESCRIBE, buffer)", ARG3, ARG4);
   3478       break;
   3479    case VKI_KEYCTL_CLEAR:
   3480       PRINT("sys_keyctl ( KEYCTL_CLEAR, %ld )", ARG2);
   3481       PRE_REG_READ2(long, "keyctl(KEYCTL_CLEAR)",
   3482                     int, option, vki_key_serial_t, keyring);
   3483       break;
   3484    case VKI_KEYCTL_LINK:
   3485       PRINT("sys_keyctl ( KEYCTL_LINK, %ld, %ld )", ARG2,ARG3);
   3486       PRE_REG_READ3(long, "keyctl(KEYCTL_LINK)", int, option,
   3487                     vki_key_serial_t, keyring, vki_key_serial_t, key);
   3488       break;
   3489    case VKI_KEYCTL_UNLINK:
   3490       PRINT("sys_keyctl ( KEYCTL_UNLINK, %ld, %ld )", ARG2,ARG3);
   3491       PRE_REG_READ3(long, "keyctl(KEYCTL_UNLINK)", int, option,
   3492                     vki_key_serial_t, keyring, vki_key_serial_t, key);
   3493       break;
   3494    case VKI_KEYCTL_SEARCH:
   3495       PRINT("sys_keyctl ( KEYCTL_SEARCH, %ld, %#lx(%s), %#lx(%s), %ld )",
   3496             ARG2,ARG3,(char*)ARG3,ARG4,(char*)ARG4,ARG5);
   3497       PRE_REG_READ5(long, "keyctl(KEYCTL_SEARCH)",
   3498                     int, option, vki_key_serial_t, keyring,
   3499                     const char *, type, const char *, description,
   3500                     vki_key_serial_t, destring);
   3501       PRE_MEM_RASCIIZ("sys_keyctl(KEYCTL_SEARCH, type)", ARG3);
   3502       PRE_MEM_RASCIIZ("sys_keyctl(KEYCTL_SEARCH, description)", ARG4);
   3503       break;
   3504    case VKI_KEYCTL_READ:
   3505       PRINT("sys_keyctl ( KEYCTL_READ, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
   3506       PRE_REG_READ4(long, "keyctl(KEYCTL_READ)",
   3507                     int, option, vki_key_serial_t, keyring,
   3508                     char *, buffer, vki_size_t, buflen);
   3509       if (ARG3 != (UWord)NULL)
   3510          PRE_MEM_WRITE("keyctl(KEYCTL_READ, buffer)", ARG3, ARG4);
   3511       break;
   3512    case VKI_KEYCTL_INSTANTIATE:
   3513       PRINT("sys_keyctl ( KEYCTL_INSTANTIATE, %ld, %#lx, %ld, %ld )",
   3514             ARG2,ARG3,ARG4,ARG5);
   3515       PRE_REG_READ5(long, "keyctl(KEYCTL_INSTANTIATE)",
   3516                     int, option, vki_key_serial_t, key,
   3517                     char *, payload, vki_size_t, plen,
   3518                     vki_key_serial_t, keyring);
   3519       if (ARG3 != (UWord)NULL)
   3520          PRE_MEM_READ("keyctl(KEYCTL_INSTANTIATE, payload)", ARG3, ARG4);
   3521       break;
   3522    case VKI_KEYCTL_NEGATE:
   3523       PRINT("sys_keyctl ( KEYCTL_NEGATE, %ld, %lu, %ld )", ARG2,ARG3,ARG4);
   3524       PRE_REG_READ4(long, "keyctl(KEYCTL_NEGATE)",
   3525                     int, option, vki_key_serial_t, key,
   3526                     unsigned, timeout, vki_key_serial_t, keyring);
   3527       break;
   3528    case VKI_KEYCTL_SET_REQKEY_KEYRING:
   3529       PRINT("sys_keyctl ( KEYCTL_SET_REQKEY_KEYRING, %ld )", ARG2);
   3530       PRE_REG_READ2(long, "keyctl(KEYCTL_SET_REQKEY_KEYRING)",
   3531                     int, option, int, reqkey_defl);
   3532       break;
   3533    case VKI_KEYCTL_SET_TIMEOUT:
   3534       PRINT("sys_keyctl ( KEYCTL_SET_TIMEOUT, %ld, %ld )", ARG2,ARG3);
   3535       PRE_REG_READ3(long, "keyctl(KEYCTL_SET_TIMEOUT)",
   3536                     int, option, vki_key_serial_t, key, unsigned, timeout);
   3537       break;
   3538    case VKI_KEYCTL_ASSUME_AUTHORITY:
   3539       PRINT("sys_keyctl ( KEYCTL_ASSUME_AUTHORITY, %ld )", ARG2);
   3540       PRE_REG_READ2(long, "keyctl(KEYCTL_ASSUME_AUTHORITY)",
   3541                     int, option, vki_key_serial_t, key);
   3542       break;
   3543    default:
   3544       PRINT("sys_keyctl ( %ld ) ", ARG1);
   3545       PRE_REG_READ1(long, "keyctl", int, option);
   3546       break;
   3547    }
   3548 }
   3549 
   3550 POST(sys_keyctl)
   3551 {
   3552    vg_assert(SUCCESS);
   3553    switch (ARG1 /* option */) {
   3554    case VKI_KEYCTL_DESCRIBE:
   3555    case VKI_KEYCTL_READ:
   3556       if (RES > ARG4)
   3557          POST_MEM_WRITE(ARG3, ARG4);
   3558       else
   3559          POST_MEM_WRITE(ARG3, RES);
   3560       break;
   3561    default:
   3562       break;
   3563    }
   3564 }
   3565 
   3566 /* ---------------------------------------------------------------------
   3567    ioprio_ wrappers
   3568    ------------------------------------------------------------------ */
   3569 
   3570 PRE(sys_ioprio_set)
   3571 {
   3572    PRINT("sys_ioprio_set ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   3573    PRE_REG_READ3(int, "ioprio_set", int, which, int, who, int, ioprio);
   3574 }
   3575 
   3576 PRE(sys_ioprio_get)
   3577 {
   3578    PRINT("sys_ioprio_get ( %ld, %ld )", ARG1,ARG2);
   3579    PRE_REG_READ2(int, "ioprio_get", int, which, int, who);
   3580 }
   3581 
   3582 /* ---------------------------------------------------------------------
   3583    _module wrappers
   3584    ------------------------------------------------------------------ */
   3585 
   3586 PRE(sys_init_module)
   3587 {
   3588    *flags |= SfMayBlock;
   3589    PRINT("sys_init_module ( %#lx, %llu, %#lx(\"%s\") )",
   3590          ARG1, (ULong)ARG2, ARG3, (char*)ARG3);
   3591    PRE_REG_READ3(long, "init_module",
   3592                  void *, umod, unsigned long, len, const char *, uargs);
   3593    PRE_MEM_READ( "init_module(umod)", ARG1, ARG2 );
   3594    PRE_MEM_RASCIIZ( "init_module(uargs)", ARG3 );
   3595 }
   3596 
   3597 PRE(sys_delete_module)
   3598 {
   3599    *flags |= SfMayBlock;
   3600    PRINT("sys_delete_module ( %#lx(\"%s\"), 0x%lx )", ARG1,(char*)ARG1, ARG2);
   3601    PRE_REG_READ2(long, "delete_module",
   3602                  const char *, name_user, unsigned int, flags);
   3603    PRE_MEM_RASCIIZ("delete_module(name_user)", ARG1);
   3604 }
   3605 
   3606 /* ---------------------------------------------------------------------
   3607    splice wrappers
   3608    ------------------------------------------------------------------ */
   3609 
   3610 PRE(sys_splice)
   3611 {
   3612    *flags |= SfMayBlock;
   3613    PRINT("sys_splice ( %ld, %#lx, %ld, %#lx, %ld, %ld )",
   3614          ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
   3615    PRE_REG_READ6(int32_t, "splice",
   3616                  int, fd_in, vki_loff_t *, off_in,
   3617                  int, fd_out, vki_loff_t *, off_out,
   3618                  vki_size_t, len, unsigned int, flags);
   3619    if (!ML_(fd_allowed)(ARG1, "splice(fd_in)", tid, False) ||
   3620        !ML_(fd_allowed)(ARG3, "splice(fd_out)", tid, False)) {
   3621       SET_STATUS_Failure( VKI_EBADF );
   3622    } else {
   3623       if (ARG2 != 0)
   3624          PRE_MEM_READ( "splice(off_in)", ARG2, sizeof(vki_loff_t));
   3625       if (ARG4 != 0)
   3626          PRE_MEM_READ( "splice(off_out)", ARG4, sizeof(vki_loff_t));
   3627    }
   3628 }
   3629 
   3630 /* ---------------------------------------------------------------------
   3631    oprofile-related wrappers
   3632    ------------------------------------------------------------------ */
   3633 
   3634 #if defined(VGP_x86_linux)
   3635 PRE(sys_lookup_dcookie)
   3636 {
   3637    PRINT("sys_lookup_dcookie (0x%llx, %#lx, %ld)",
   3638          MERGE64(ARG1,ARG2), ARG3, ARG4);
   3639    PRE_REG_READ4(long, "lookup_dcookie",
   3640                  vki_u32, MERGE64_FIRST(cookie), vki_u32, MERGE64_SECOND(cookie),
   3641                  char *, buf, vki_size_t, len);
   3642    PRE_MEM_WRITE( "lookup_dcookie(buf)", ARG3, ARG4);
   3643 }
   3644 POST(sys_lookup_dcookie)
   3645 {
   3646    vg_assert(SUCCESS);
   3647    if (ARG3 != (Addr)NULL)
   3648       POST_MEM_WRITE( ARG3, RES);
   3649 }
   3650 #endif
   3651 
   3652 #if defined(VGP_amd64_linux)
   3653 PRE(sys_lookup_dcookie)
   3654 {
   3655    *flags |= SfMayBlock;
   3656    PRINT("sys_lookup_dcookie ( %llu, %#lx, %llu )",
   3657 	 (ULong)ARG1, ARG2, (ULong)ARG3);
   3658    PRE_REG_READ3(int, "lookup_dcookie",
   3659                  unsigned long long, cookie, char *, buf, vki_size_t, len);
   3660 
   3661    PRE_MEM_WRITE( "sys_lookup_dcookie(buf)", ARG2, ARG3 );
   3662 }
   3663 
   3664 POST(sys_lookup_dcookie)
   3665 {
   3666    vg_assert(SUCCESS);
   3667    if (ARG2 != (Addr)NULL)
   3668      POST_MEM_WRITE( ARG2, RES );
   3669 }
   3670 #endif
   3671 
   3672 /* ---------------------------------------------------------------------
   3673    fcntl wrappers
   3674    ------------------------------------------------------------------ */
   3675 
   3676 PRE(sys_fcntl)
   3677 {
   3678    switch (ARG2) {
   3679    // These ones ignore ARG3.
   3680    case VKI_F_GETFD:
   3681    case VKI_F_GETFL:
   3682    case VKI_F_GETOWN:
   3683    case VKI_F_GETSIG:
   3684    case VKI_F_GETLEASE:
   3685       PRINT("sys_fcntl ( %ld, %ld )", ARG1,ARG2);
   3686       PRE_REG_READ2(long, "fcntl", unsigned int, fd, unsigned int, cmd);
   3687       break;
   3688 
   3689    // These ones use ARG3 as "arg".
   3690    case VKI_F_DUPFD:
   3691    case VKI_F_DUPFD_CLOEXEC:
   3692    case VKI_F_SETFD:
   3693    case VKI_F_SETFL:
   3694    case VKI_F_SETLEASE:
   3695    case VKI_F_NOTIFY:
   3696    case VKI_F_SETOWN:
   3697    case VKI_F_SETSIG:
   3698       PRINT("sys_fcntl[ARG3=='arg'] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   3699       PRE_REG_READ3(long, "fcntl",
   3700                     unsigned int, fd, unsigned int, cmd, unsigned long, arg);
   3701       break;
   3702 
   3703    // These ones use ARG3 as "lock".
   3704    case VKI_F_GETLK:
   3705    case VKI_F_SETLK:
   3706    case VKI_F_SETLKW:
   3707 #  if defined(VGP_x86_linux)
   3708    case VKI_F_GETLK64:
   3709    case VKI_F_SETLK64:
   3710    case VKI_F_SETLKW64:
   3711 #  endif
   3712       PRINT("sys_fcntl[ARG3=='lock'] ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
   3713       PRE_REG_READ3(long, "fcntl",
   3714                     unsigned int, fd, unsigned int, cmd,
   3715                     struct flock64 *, lock);
   3716       break;
   3717 
   3718    default:
   3719       PRINT("sys_fcntl[UNKNOWN] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   3720       I_die_here;
   3721       break;
   3722    }
   3723 
   3724 #  if defined(VGP_x86_linux)
   3725    if (ARG2 == VKI_F_SETLKW || ARG2 == VKI_F_SETLKW64)
   3726 #  else
   3727    if (ARG2 == VKI_F_SETLKW)
   3728 #  endif
   3729       *flags |= SfMayBlock;
   3730 }
   3731 
   3732 POST(sys_fcntl)
   3733 {
   3734    vg_assert(SUCCESS);
   3735    if (ARG2 == VKI_F_DUPFD) {
   3736       if (!ML_(fd_allowed)(RES, "fcntl(DUPFD)", tid, True)) {
   3737          VG_(close)(RES);
   3738          SET_STATUS_Failure( VKI_EMFILE );
   3739       } else {
   3740          if (VG_(clo_track_fds))
   3741             ML_(record_fd_open_named)(tid, RES);
   3742       }
   3743    }
   3744    else if (ARG2 == VKI_F_DUPFD_CLOEXEC) {
   3745       if (!ML_(fd_allowed)(RES, "fcntl(DUPFD_CLOEXEC)", tid, True)) {
   3746          VG_(close)(RES);
   3747          SET_STATUS_Failure( VKI_EMFILE );
   3748       } else {
   3749          if (VG_(clo_track_fds))
   3750             ML_(record_fd_open_named)(tid, RES);
   3751       }
   3752    }
   3753 }
   3754 
   3755 // XXX: wrapper only suitable for 32-bit systems
   3756 PRE(sys_fcntl64)
   3757 {
   3758    switch (ARG2) {
   3759    // These ones ignore ARG3.
   3760    case VKI_F_GETFD:
   3761    case VKI_F_GETFL:
   3762    case VKI_F_GETOWN:
   3763    case VKI_F_SETOWN:
   3764    case VKI_F_GETSIG:
   3765    case VKI_F_SETSIG:
   3766    case VKI_F_GETLEASE:
   3767       PRINT("sys_fcntl64 ( %ld, %ld )", ARG1,ARG2);
   3768       PRE_REG_READ2(long, "fcntl64", unsigned int, fd, unsigned int, cmd);
   3769       break;
   3770 
   3771    // These ones use ARG3 as "arg".
   3772    case VKI_F_DUPFD:
   3773    case VKI_F_DUPFD_CLOEXEC:
   3774    case VKI_F_SETFD:
   3775    case VKI_F_SETFL:
   3776    case VKI_F_SETLEASE:
   3777    case VKI_F_NOTIFY:
   3778       PRINT("sys_fcntl64[ARG3=='arg'] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
   3779       PRE_REG_READ3(long, "fcntl64",
   3780                     unsigned int, fd, unsigned int, cmd, unsigned long, arg);
   3781       break;
   3782 
   3783    // These ones use ARG3 as "lock".
   3784    case VKI_F_GETLK:
   3785    case VKI_F_SETLK:
   3786    case VKI_F_SETLKW:
   3787 #  if defined(VGP_x86_linux)
   3788    case VKI_F_GETLK64:
   3789    case VKI_F_SETLK64:
   3790    case VKI_F_SETLKW64:
   3791 #  endif
   3792       PRINT("sys_fcntl64[ARG3=='lock'] ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
   3793       PRE_REG_READ3(long, "fcntl64",
   3794                     unsigned int, fd, unsigned int, cmd,
   3795                     struct flock64 *, lock);
   3796       break;
   3797    }
   3798 
   3799 #  if defined(VGP_x86_linux)
   3800    if (ARG2 == VKI_F_SETLKW || ARG2 == VKI_F_SETLKW64)
   3801 #  else
   3802    if (ARG2 == VKI_F_SETLKW)
   3803 #  endif
   3804       *flags |= SfMayBlock;
   3805 }
   3806 
   3807 POST(sys_fcntl64)
   3808 {
   3809    vg_assert(SUCCESS);
   3810    if (ARG2 == VKI_F_DUPFD) {
   3811       if (!ML_(fd_allowed)(RES, "fcntl64(DUPFD)", tid, True)) {
   3812          VG_(close)(RES);
   3813          SET_STATUS_Failure( VKI_EMFILE );
   3814       } else {
   3815          if (VG_(clo_track_fds))
   3816             ML_(record_fd_open_named)(tid, RES);
   3817       }
   3818    }
   3819    else if (ARG2 == VKI_F_DUPFD_CLOEXEC) {
   3820       if (!ML_(fd_allowed)(RES, "fcntl64(DUPFD_CLOEXEC)", tid, True)) {
   3821          VG_(close)(RES);
   3822          SET_STATUS_Failure( VKI_EMFILE );
   3823       } else {
   3824          if (VG_(clo_track_fds))
   3825             ML_(record_fd_open_named)(tid, RES);
   3826       }
   3827    }
   3828 }
   3829 
   3830 /* ---------------------------------------------------------------------
   3831    ioctl wrappers
   3832    ------------------------------------------------------------------ */
   3833 
   3834 PRE(sys_ioctl)
   3835 {
   3836    *flags |= SfMayBlock;
   3837    PRINT("sys_ioctl ( %ld, 0x%lx, %#lx )",ARG1,ARG2,ARG3);
   3838    PRE_REG_READ3(long, "ioctl",
   3839                  unsigned int, fd, unsigned int, request, unsigned long, arg);
   3840 
   3841    // We first handle the ones that don't use ARG3 (even as a
   3842    // scalar/non-pointer argument).
   3843    switch (ARG2 /* request */) {
   3844 
   3845       /* linux/soundcard interface (ALSA) */
   3846    case VKI_SNDRV_PCM_IOCTL_HW_FREE:
   3847    case VKI_SNDRV_PCM_IOCTL_HWSYNC:
   3848    case VKI_SNDRV_PCM_IOCTL_PREPARE:
   3849    case VKI_SNDRV_PCM_IOCTL_RESET:
   3850    case VKI_SNDRV_PCM_IOCTL_START:
   3851    case VKI_SNDRV_PCM_IOCTL_DROP:
   3852    case VKI_SNDRV_PCM_IOCTL_DRAIN:
   3853    case VKI_SNDRV_PCM_IOCTL_RESUME:
   3854    case VKI_SNDRV_PCM_IOCTL_XRUN:
   3855    case VKI_SNDRV_PCM_IOCTL_UNLINK:
   3856    case VKI_SNDRV_TIMER_IOCTL_START:
   3857    case VKI_SNDRV_TIMER_IOCTL_STOP:
   3858    case VKI_SNDRV_TIMER_IOCTL_CONTINUE:
   3859    case VKI_SNDRV_TIMER_IOCTL_PAUSE:
   3860       PRINT("sys_ioctl ( %ld, 0x%lx )",ARG1,ARG2);
   3861       PRE_REG_READ2(long, "ioctl",
   3862                     unsigned int, fd, unsigned int, request);
   3863       return;
   3864 
   3865    default:
   3866       PRINT("sys_ioctl ( %ld, 0x%lx, 0x%lx )",ARG1,ARG2,ARG3);
   3867       PRE_REG_READ3(long, "ioctl",
   3868                     unsigned int, fd, unsigned int, request, unsigned long, arg);
   3869       break;
   3870    }
   3871 
   3872    // We now handle those that do look at ARG3 (and unknown ones fall into
   3873    // this category).  Nb: some of these may well belong in the
   3874    // doesn't-use-ARG3 switch above.
   3875    switch (ARG2 /* request */) {
   3876    case VKI_TCSETS:
   3877    case VKI_TCSETSW:
   3878    case VKI_TCSETSF:
   3879       PRE_MEM_READ( "ioctl(TCSET{S,SW,SF})", ARG3, sizeof(struct vki_termios) );
   3880       break;
   3881    case VKI_TCGETS:
   3882       PRE_MEM_WRITE( "ioctl(TCGETS)", ARG3, sizeof(struct vki_termios) );
   3883       break;
   3884    case VKI_TCSETA:
   3885    case VKI_TCSETAW:
   3886    case VKI_TCSETAF:
   3887       PRE_MEM_READ( "ioctl(TCSET{A,AW,AF})", ARG3, sizeof(struct vki_termio) );
   3888       break;
   3889    case VKI_TCGETA:
   3890       PRE_MEM_WRITE( "ioctl(TCGETA)", ARG3, sizeof(struct vki_termio) );
   3891       break;
   3892    case VKI_TCSBRK:
   3893    case VKI_TCXONC:
   3894    case VKI_TCSBRKP:
   3895    case VKI_TCFLSH:
   3896       /* These just take an int by value */
   3897       break;
   3898    case VKI_TIOCGWINSZ:
   3899       PRE_MEM_WRITE( "ioctl(TIOCGWINSZ)", ARG3, sizeof(struct vki_winsize) );
   3900       break;
   3901    case VKI_TIOCSWINSZ:
   3902       PRE_MEM_READ( "ioctl(TIOCSWINSZ)",  ARG3, sizeof(struct vki_winsize) );
   3903       break;
   3904    case VKI_TIOCMBIS:
   3905       PRE_MEM_READ( "ioctl(TIOCMBIS)",    ARG3, sizeof(unsigned int) );
   3906       break;
   3907    case VKI_TIOCMBIC:
   3908       PRE_MEM_READ( "ioctl(TIOCMBIC)",    ARG3, sizeof(unsigned int) );
   3909       break;
   3910    case VKI_TIOCMSET:
   3911       PRE_MEM_READ( "ioctl(TIOCMSET)",    ARG3, sizeof(unsigned int) );
   3912       break;
   3913    case VKI_TIOCMGET:
   3914       PRE_MEM_WRITE( "ioctl(TIOCMGET)",   ARG3, sizeof(unsigned int) );
   3915       break;
   3916    case VKI_TIOCLINUX:
   3917       PRE_MEM_READ( "ioctl(TIOCLINUX)",   ARG3, sizeof(char *) );
   3918       if (*(char *)ARG3 == 11) {
   3919 	 PRE_MEM_READ( "ioctl(TIOCLINUX, 11)", ARG3, 2 * sizeof(char *) );
   3920       }
   3921       break;
   3922    case VKI_TIOCGPGRP:
   3923       /* Get process group ID for foreground processing group. */
   3924       PRE_MEM_WRITE( "ioctl(TIOCGPGRP)", ARG3, sizeof(vki_pid_t) );
   3925       break;
   3926    case VKI_TIOCSPGRP:
   3927       /* Set a process group ID? */
   3928       PRE_MEM_WRITE( "ioctl(TIOCGPGRP)", ARG3, sizeof(vki_pid_t) );
   3929       break;
   3930    case VKI_TIOCGPTN: /* Get Pty Number (of pty-mux device) */
   3931       PRE_MEM_WRITE( "ioctl(TIOCGPTN)", ARG3, sizeof(int) );
   3932       break;
   3933    case VKI_TIOCSCTTY:
   3934       /* Just takes an int value.  */
   3935       break;
   3936    case VKI_TIOCSPTLCK: /* Lock/unlock Pty */
   3937       PRE_MEM_READ( "ioctl(TIOCSPTLCK)", ARG3, sizeof(int) );
   3938       break;
   3939    case VKI_FIONBIO:
   3940       PRE_MEM_READ( "ioctl(FIONBIO)",    ARG3, sizeof(int) );
   3941       break;
   3942    case VKI_FIOASYNC:
   3943       PRE_MEM_READ( "ioctl(FIOASYNC)",   ARG3, sizeof(int) );
   3944       break;
   3945    case VKI_FIONREAD:                /* identical to SIOCINQ */
   3946       PRE_MEM_WRITE( "ioctl(FIONREAD)",  ARG3, sizeof(int) );
   3947       break;
   3948 
   3949    case VKI_TIOCSERGETLSR:
   3950       PRE_MEM_WRITE( "ioctl(TIOCSERGETLSR)", ARG3, sizeof(int) );
   3951       break;
   3952    case VKI_TIOCGICOUNT:
   3953       PRE_MEM_WRITE( "ioctl(TIOCGICOUNT)", ARG3,
   3954                      sizeof(struct vki_serial_icounter_struct) );
   3955       break;
   3956 
   3957    case VKI_SG_SET_COMMAND_Q:
   3958       PRE_MEM_READ( "ioctl(SG_SET_COMMAND_Q)", ARG3, sizeof(int) );
   3959       break;
   3960    case VKI_SG_IO:
   3961       PRE_MEM_WRITE( "ioctl(SG_IO)", ARG3, sizeof(vki_sg_io_hdr_t) );
   3962       break;
   3963    case VKI_SG_GET_SCSI_ID:
   3964       PRE_MEM_WRITE( "ioctl(SG_GET_SCSI_ID)", ARG3, sizeof(vki_sg_scsi_id_t) );
   3965       break;
   3966    case VKI_SG_SET_RESERVED_SIZE:
   3967       PRE_MEM_READ( "ioctl(SG_SET_RESERVED_SIZE)", ARG3, sizeof(int) );
   3968       break;
   3969    case VKI_SG_SET_TIMEOUT:
   3970       PRE_MEM_READ( "ioctl(SG_SET_TIMEOUT)", ARG3, sizeof(int) );
   3971       break;
   3972    case VKI_SG_GET_RESERVED_SIZE:
   3973       PRE_MEM_WRITE( "ioctl(SG_GET_RESERVED_SIZE)", ARG3, sizeof(int) );
   3974       break;
   3975    case VKI_SG_GET_TIMEOUT:
   3976       break;
   3977    case VKI_SG_GET_VERSION_NUM:
   3978       PRE_MEM_WRITE(  "ioctl(SG_GET_VERSION_NUM)",  ARG3, sizeof(int) );
   3979       break;
   3980    case VKI_SG_EMULATED_HOST: /* 0x2203 */
   3981       PRE_MEM_WRITE( "ioctl(SG_EMULATED_HOST)",    ARG3, sizeof(int) );
   3982       break;
   3983    case VKI_SG_GET_SG_TABLESIZE: /* 0x227f */
   3984       PRE_MEM_WRITE( "ioctl(SG_GET_SG_TABLESIZE)", ARG3, sizeof(int) );
   3985       break;
   3986 
   3987    case VKI_IIOCGETCPS:
   3988       PRE_MEM_WRITE( "ioctl(IIOCGETCPS)", ARG3,
   3989 		     VKI_ISDN_MAX_CHANNELS * 2 * sizeof(unsigned long) );
   3990       break;
   3991    case VKI_IIOCNETGPN:
   3992       PRE_MEM_READ( "ioctl(IIOCNETGPN)",
   3993 		     (Addr)&((vki_isdn_net_ioctl_phone *)ARG3)->name,
   3994 		     sizeof(((vki_isdn_net_ioctl_phone *)ARG3)->name) );
   3995       PRE_MEM_WRITE( "ioctl(IIOCNETGPN)", ARG3,
   3996 		     sizeof(vki_isdn_net_ioctl_phone) );
   3997       break;
   3998 
   3999       /* These all use struct ifreq AFAIK */
   4000    case VKI_SIOCGIFINDEX:        /* get iface index              */
   4001       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFINDEX)",
   4002                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4003       PRE_MEM_WRITE( "ioctl(SIOCGIFINDEX)", ARG3, sizeof(struct vki_ifreq));
   4004       break;
   4005    case VKI_SIOCGIFFLAGS:        /* get flags                    */
   4006       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFFLAGS)",
   4007                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4008       PRE_MEM_WRITE( "ioctl(SIOCGIFFLAGS)", ARG3, sizeof(struct vki_ifreq));
   4009       break;
   4010    case VKI_SIOCGIFHWADDR:       /* Get hardware address         */
   4011       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFHWADDR)",
   4012                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4013       PRE_MEM_WRITE( "ioctl(SIOCGIFHWADDR)", ARG3, sizeof(struct vki_ifreq));
   4014       break;
   4015    case VKI_SIOCGIFMTU:          /* get MTU size                 */
   4016       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMTU)",
   4017                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4018       PRE_MEM_WRITE( "ioctl(SIOCGIFMTU)", ARG3, sizeof(struct vki_ifreq));
   4019       break;
   4020    case VKI_SIOCGIFADDR:         /* get PA address               */
   4021       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFADDR)",
   4022                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4023       PRE_MEM_WRITE( "ioctl(SIOCGIFADDR)", ARG3, sizeof(struct vki_ifreq));
   4024       break;
   4025    case VKI_SIOCGIFNETMASK:      /* get network PA mask          */
   4026       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFNETMASK)",
   4027                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4028       PRE_MEM_WRITE( "ioctl(SIOCGIFNETMASK)", ARG3, sizeof(struct vki_ifreq));
   4029       break;
   4030    case VKI_SIOCGIFMETRIC:       /* get metric                   */
   4031       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMETRIC)",
   4032                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4033       PRE_MEM_WRITE( "ioctl(SIOCGIFMETRIC)", ARG3, sizeof(struct vki_ifreq));
   4034       break;
   4035    case VKI_SIOCGIFMAP:          /* Get device parameters        */
   4036       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMAP)",
   4037                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4038       PRE_MEM_WRITE( "ioctl(SIOCGIFMAP)", ARG3, sizeof(struct vki_ifreq));
   4039       break;
   4040    case VKI_SIOCGIFTXQLEN:       /* Get the tx queue length      */
   4041       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFTXQLEN)",
   4042                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4043       PRE_MEM_WRITE( "ioctl(SIOCGIFTXQLEN)", ARG3, sizeof(struct vki_ifreq));
   4044       break;
   4045    case VKI_SIOCGIFDSTADDR:      /* get remote PA address        */
   4046       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFDSTADDR)",
   4047                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4048       PRE_MEM_WRITE( "ioctl(SIOCGIFDSTADDR)", ARG3, sizeof(struct vki_ifreq));
   4049       break;
   4050    case VKI_SIOCGIFBRDADDR:      /* get broadcast PA address     */
   4051       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFBRDADDR)",
   4052                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4053       PRE_MEM_WRITE( "ioctl(SIOCGIFBRDADDR)", ARG3, sizeof(struct vki_ifreq));
   4054       break;
   4055    case VKI_SIOCGIFNAME:         /* get iface name               */
   4056       PRE_MEM_READ( "ioctl(SIOCGIFNAME)",
   4057                      (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_ifindex,
   4058                      sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_ifindex) );
   4059       PRE_MEM_WRITE( "ioctl(SIOCGIFNAME)", ARG3, sizeof(struct vki_ifreq));
   4060       break;
   4061    case VKI_SIOCGMIIPHY:         /* get hardware entry           */
   4062       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMIIPHY)",
   4063                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4064       PRE_MEM_WRITE( "ioctl(SIOCGIFMIIPHY)", ARG3, sizeof(struct vki_ifreq));
   4065       break;
   4066    case VKI_SIOCGMIIREG:         /* get hardware entry registers */
   4067       PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMIIREG)",
   4068                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4069       PRE_MEM_READ( "ioctl(SIOCGIFMIIREG)",
   4070                      (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
   4071                      sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
   4072       PRE_MEM_READ( "ioctl(SIOCGIFMIIREG)",
   4073                      (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num,
   4074                      sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num) );
   4075       PRE_MEM_WRITE( "ioctl(SIOCGIFMIIREG)", ARG3,
   4076 		     sizeof(struct vki_ifreq));
   4077       break;
   4078    case VKI_SIOCGIFCONF:         /* get iface list               */
   4079       /* WAS:
   4080 	 PRE_MEM_WRITE( "ioctl(SIOCGIFCONF)", ARG3, sizeof(struct ifconf));
   4081 	 KERNEL_DO_SYSCALL(tid,RES);
   4082 	 if (!VG_(is_kerror)(RES) && RES == 0)
   4083 	 POST_MEM_WRITE(ARG3, sizeof(struct ifconf));
   4084       */
   4085       PRE_MEM_READ( "ioctl(SIOCGIFCONF)",
   4086                     (Addr)&((struct vki_ifconf *)ARG3)->ifc_len,
   4087                     sizeof(((struct vki_ifconf *)ARG3)->ifc_len));
   4088       PRE_MEM_READ( "ioctl(SIOCGIFCONF)",
   4089                     (Addr)&((struct vki_ifconf *)ARG3)->vki_ifc_buf,
   4090                     sizeof(((struct vki_ifconf *)ARG3)->vki_ifc_buf));
   4091       if ( ARG3 ) {
   4092 	 // TODO len must be readable and writable
   4093 	 // buf pointer only needs to be readable
   4094 	 struct vki_ifconf *ifc = (struct vki_ifconf *) ARG3;
   4095 	 PRE_MEM_WRITE( "ioctl(SIOCGIFCONF).ifc_buf",
   4096 			(Addr)(ifc->vki_ifc_buf), ifc->ifc_len );
   4097       }
   4098       break;
   4099    case VKI_SIOCGSTAMP:
   4100       PRE_MEM_WRITE( "ioctl(SIOCGSTAMP)", ARG3, sizeof(struct vki_timeval));
   4101       break;
   4102    case VKI_SIOCGSTAMPNS:
   4103       PRE_MEM_WRITE( "ioctl(SIOCGSTAMPNS)", ARG3, sizeof(struct vki_timespec));
   4104       break;
   4105       /* SIOCOUTQ is an ioctl that, when called on a socket, returns
   4106 	 the number of bytes currently in that socket's send buffer.
   4107 	 It writes this value as an int to the memory location
   4108 	 indicated by the third argument of ioctl(2). */
   4109    case VKI_SIOCOUTQ:
   4110       PRE_MEM_WRITE( "ioctl(SIOCOUTQ)", ARG3, sizeof(int));
   4111       break;
   4112    case VKI_SIOCGRARP:           /* get RARP table entry         */
   4113    case VKI_SIOCGARP:            /* get ARP table entry          */
   4114       PRE_MEM_WRITE( "ioctl(SIOCGARP)", ARG3, sizeof(struct vki_arpreq));
   4115       break;
   4116 
   4117    case VKI_SIOCSIFFLAGS:        /* set flags                    */
   4118       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFFLAGS)",
   4119                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4120       PRE_MEM_READ( "ioctl(SIOCSIFFLAGS)",
   4121                      (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
   4122                      sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
   4123       break;
   4124    case VKI_SIOCSIFMAP:          /* Set device parameters        */
   4125       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMAP)",
   4126                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4127       PRE_MEM_READ( "ioctl(SIOCSIFMAP)",
   4128                      (Addr)&((struct vki_ifreq *)ARG3)->ifr_map,
   4129                      sizeof(((struct vki_ifreq *)ARG3)->ifr_map) );
   4130       break;
   4131    case VKI_SIOCSIFTXQLEN:       /* Set the tx queue length      */
   4132       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFTXQLEN)",
   4133                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4134       PRE_MEM_READ( "ioctl(SIOCSIFTXQLEN)",
   4135                      (Addr)&((struct vki_ifreq *)ARG3)->ifr_qlen,
   4136                      sizeof(((struct vki_ifreq *)ARG3)->ifr_qlen) );
   4137       break;
   4138    case VKI_SIOCSIFADDR:         /* set PA address               */
   4139    case VKI_SIOCSIFDSTADDR:      /* set remote PA address        */
   4140    case VKI_SIOCSIFBRDADDR:      /* set broadcast PA address     */
   4141    case VKI_SIOCSIFNETMASK:      /* set network PA mask          */
   4142       PRE_MEM_RASCIIZ( "ioctl(SIOCSIF*ADDR)",
   4143                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4144       PRE_MEM_READ( "ioctl(SIOCSIF*ADDR)",
   4145                      (Addr)&((struct vki_ifreq *)ARG3)->ifr_addr,
   4146                      sizeof(((struct vki_ifreq *)ARG3)->ifr_addr) );
   4147       break;
   4148    case VKI_SIOCSIFMETRIC:       /* set metric                   */
   4149       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMETRIC)",
   4150                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4151       PRE_MEM_READ( "ioctl(SIOCSIFMETRIC)",
   4152                      (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_metric,
   4153                      sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_metric) );
   4154       break;
   4155    case VKI_SIOCSIFMTU:          /* set MTU size                 */
   4156       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMTU)",
   4157                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4158       PRE_MEM_READ( "ioctl(SIOCSIFMTU)",
   4159                      (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_mtu,
   4160                      sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_mtu) );
   4161       break;
   4162    case VKI_SIOCSIFHWADDR:       /* set hardware address         */
   4163       PRE_MEM_RASCIIZ( "ioctl(SIOCSIFHWADDR)",
   4164                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4165       PRE_MEM_READ( "ioctl(SIOCSIFHWADDR)",
   4166                      (Addr)&((struct vki_ifreq *)ARG3)->ifr_hwaddr,
   4167                      sizeof(((struct vki_ifreq *)ARG3)->ifr_hwaddr) );
   4168       break;
   4169    case VKI_SIOCSMIIREG:         /* set hardware entry registers */
   4170       PRE_MEM_RASCIIZ( "ioctl(SIOCSMIIREG)",
   4171                      (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
   4172       PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
   4173                      (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
   4174                      sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
   4175       PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
   4176                      (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num,
   4177                      sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num) );
   4178       PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
   4179                      (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_in,
   4180                      sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_in) );
   4181       break;
   4182       /* Routing table calls.  */
   4183    case VKI_SIOCADDRT:           /* add routing table entry      */
   4184    case VKI_SIOCDELRT:           /* delete routing table entry   */
   4185       PRE_MEM_READ( "ioctl(SIOCADDRT/DELRT)", ARG3,
   4186 		    sizeof(struct vki_rtentry));
   4187       break;
   4188 
   4189       /* RARP cache control calls. */
   4190    case VKI_SIOCDRARP:           /* delete RARP table entry      */
   4191    case VKI_SIOCSRARP:           /* set RARP table entry         */
   4192       /* ARP cache control calls. */
   4193    case VKI_SIOCSARP:            /* set ARP table entry          */
   4194    case VKI_SIOCDARP:            /* delete ARP table entry       */
   4195       PRE_MEM_READ( "ioctl(SIOCSIFFLAGS)", ARG3, sizeof(struct vki_ifreq));
   4196       break;
   4197 
   4198    case VKI_SIOCGPGRP:
   4199       PRE_MEM_WRITE( "ioctl(SIOCGPGRP)", ARG3, sizeof(int) );
   4200       break;
   4201    case VKI_SIOCSPGRP:
   4202       PRE_MEM_READ( "ioctl(SIOCSPGRP)", ARG3, sizeof(int) );
   4203       //tst->sys_flags &= ~SfMayBlock;
   4204       break;
   4205 
   4206       /* linux/soundcard interface (OSS) */
   4207    case VKI_SNDCTL_SEQ_GETOUTCOUNT:
   4208    case VKI_SNDCTL_SEQ_GETINCOUNT:
   4209    case VKI_SNDCTL_SEQ_PERCMODE:
   4210    case VKI_SNDCTL_SEQ_TESTMIDI:
   4211    case VKI_SNDCTL_SEQ_RESETSAMPLES:
   4212    case VKI_SNDCTL_SEQ_NRSYNTHS:
   4213    case VKI_SNDCTL_SEQ_NRMIDIS:
   4214    case VKI_SNDCTL_SEQ_GETTIME:
   4215    case VKI_SNDCTL_DSP_GETBLKSIZE:
   4216    case VKI_SNDCTL_DSP_GETFMTS:
   4217    case VKI_SNDCTL_DSP_GETTRIGGER:
   4218    case VKI_SNDCTL_DSP_GETODELAY:
   4219    case VKI_SNDCTL_DSP_GETSPDIF:
   4220    case VKI_SNDCTL_DSP_GETCAPS:
   4221    case VKI_SOUND_PCM_READ_RATE:
   4222    case VKI_SOUND_PCM_READ_CHANNELS:
   4223    case VKI_SOUND_PCM_READ_BITS:
   4224    case VKI_SOUND_PCM_READ_FILTER:
   4225       PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOR, int))",
   4226 		     ARG3, sizeof(int));
   4227       break;
   4228    case VKI_SNDCTL_SEQ_CTRLRATE:
   4229    case VKI_SNDCTL_DSP_SPEED:
   4230    case VKI_SNDCTL_DSP_STEREO:
   4231    case VKI_SNDCTL_DSP_CHANNELS:
   4232    case VKI_SOUND_PCM_WRITE_FILTER:
   4233    case VKI_SNDCTL_DSP_SUBDIVIDE:
   4234    case VKI_SNDCTL_DSP_SETFRAGMENT:
   4235    case VKI_SNDCTL_DSP_SETFMT:
   4236    case VKI_SNDCTL_DSP_GETCHANNELMASK:
   4237    case VKI_SNDCTL_DSP_BIND_CHANNEL:
   4238    case VKI_SNDCTL_TMR_TIMEBASE:
   4239    case VKI_SNDCTL_TMR_TEMPO:
   4240    case VKI_SNDCTL_TMR_SOURCE:
   4241    case VKI_SNDCTL_MIDI_PRETIME:
   4242    case VKI_SNDCTL_MIDI_MPUMODE:
   4243       PRE_MEM_READ( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOWR, int))",
   4244 		     ARG3, sizeof(int));
   4245       PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOWR, int))",
   4246 		     ARG3, sizeof(int));
   4247       break;
   4248    case VKI_SNDCTL_DSP_GETOSPACE:
   4249    case VKI_SNDCTL_DSP_GETISPACE:
   4250       PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOR, audio_buf_info))",
   4251                      ARG3, sizeof(vki_audio_buf_info));
   4252       break;
   4253    case VKI_SNDCTL_DSP_NONBLOCK:
   4254       break;
   4255    case VKI_SNDCTL_DSP_SETTRIGGER:
   4256       PRE_MEM_READ( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOW, int))",
   4257 		     ARG3, sizeof(int));
   4258       break;
   4259 
   4260    case VKI_SNDCTL_DSP_POST:
   4261    case VKI_SNDCTL_DSP_RESET:
   4262    case VKI_SNDCTL_DSP_SYNC:
   4263    case VKI_SNDCTL_DSP_SETSYNCRO:
   4264    case VKI_SNDCTL_DSP_SETDUPLEX:
   4265       break;
   4266 
   4267       /* linux/soundcard interface (ALSA) */
   4268    case VKI_SNDRV_PCM_IOCTL_PAUSE:
   4269    case VKI_SNDRV_PCM_IOCTL_LINK:
   4270       /* these just take an int by value */
   4271       break;
   4272 
   4273       /* Real Time Clock (/dev/rtc) ioctls */
   4274    case VKI_RTC_UIE_ON:
   4275    case VKI_RTC_UIE_OFF:
   4276    case VKI_RTC_AIE_ON:
   4277    case VKI_RTC_AIE_OFF:
   4278    case VKI_RTC_PIE_ON:
   4279    case VKI_RTC_PIE_OFF:
   4280    case VKI_RTC_IRQP_SET:
   4281       break;
   4282    case VKI_RTC_RD_TIME:
   4283    case VKI_RTC_ALM_READ:
   4284       PRE_MEM_WRITE( "ioctl(RTC_RD_TIME/ALM_READ)",
   4285 		     ARG3, sizeof(struct vki_rtc_time));
   4286       break;
   4287    case VKI_RTC_ALM_SET:
   4288       PRE_MEM_READ( "ioctl(RTC_ALM_SET)", ARG3, sizeof(struct vki_rtc_time));
   4289       break;
   4290    case VKI_RTC_IRQP_READ:
   4291       PRE_MEM_WRITE( "ioctl(RTC_IRQP_READ)", ARG3, sizeof(unsigned long));
   4292       break;
   4293 
   4294       /* Block devices */
   4295    case VKI_BLKROSET:
   4296       PRE_MEM_READ( "ioctl(BLKROSET)", ARG3, sizeof(int));
   4297       break;
   4298    case VKI_BLKROGET:
   4299       PRE_MEM_WRITE( "ioctl(BLKROGET)", ARG3, sizeof(int));
   4300       break;
   4301    case VKI_BLKGETSIZE:
   4302       PRE_MEM_WRITE( "ioctl(BLKGETSIZE)", ARG3, sizeof(unsigned long));
   4303       break;
   4304    case VKI_BLKRASET:
   4305       break;
   4306    case VKI_BLKRAGET:
   4307       PRE_MEM_WRITE( "ioctl(BLKRAGET)", ARG3, sizeof(long));
   4308       break;
   4309    case VKI_BLKFRASET:
   4310       break;
   4311    case VKI_BLKFRAGET:
   4312       PRE_MEM_WRITE( "ioctl(BLKFRAGET)", ARG3, sizeof(long));
   4313       break;
   4314    case VKI_BLKSECTGET:
   4315       PRE_MEM_WRITE( "ioctl(BLKSECTGET)", ARG3, sizeof(unsigned short));
   4316       break;
   4317    case VKI_BLKSSZGET:
   4318       PRE_MEM_WRITE( "ioctl(BLKSSZGET)", ARG3, sizeof(int));
   4319       break;
   4320    case VKI_BLKBSZGET:
   4321       PRE_MEM_WRITE( "ioctl(BLKBSZGET)", ARG3, sizeof(int));
   4322       break;
   4323    case VKI_BLKBSZSET:
   4324       PRE_MEM_READ( "ioctl(BLKBSZSET)", ARG3, sizeof(int));
   4325       break;
   4326    case VKI_BLKGETSIZE64:
   4327       PRE_MEM_WRITE( "ioctl(BLKGETSIZE64)", ARG3, sizeof(unsigned long long));
   4328       break;
   4329 
   4330       /* Hard disks */
   4331    case VKI_HDIO_GETGEO: /* 0x0301 */
   4332       PRE_MEM_WRITE( "ioctl(HDIO_GETGEO)", ARG3, sizeof(struct vki_hd_geometry));
   4333       break;
   4334    case VKI_HDIO_GET_DMA: /* 0x030b */
   4335       PRE_MEM_WRITE( "ioctl(HDIO_GET_DMA)", ARG3, sizeof(long));
   4336       break;
   4337    case VKI_HDIO_GET_IDENTITY: /* 0x030d */
   4338       PRE_MEM_WRITE( "ioctl(HDIO_GET_IDENTITY)", ARG3,
   4339                      VKI_SIZEOF_STRUCT_HD_DRIVEID );
   4340       break;
   4341 
   4342       /* CD ROM stuff (??)  */
   4343    case VKI_CDROM_GET_MCN:
   4344       PRE_MEM_READ( "ioctl(CDROM_GET_MCN)", ARG3,
   4345                     sizeof(struct vki_cdrom_mcn) );
   4346       break;
   4347    case VKI_CDROM_SEND_PACKET:
   4348       PRE_MEM_READ( "ioctl(CDROM_SEND_PACKET)", ARG3,
   4349                     sizeof(struct vki_cdrom_generic_command));
   4350       break;
   4351    case VKI_CDROMSUBCHNL:
   4352       PRE_MEM_READ( "ioctl(CDROMSUBCHNL (cdsc_format, char))",
   4353 		    (Addr) &(((struct vki_cdrom_subchnl*) ARG3)->cdsc_format),
   4354 		    sizeof(((struct vki_cdrom_subchnl*) ARG3)->cdsc_format));
   4355       PRE_MEM_WRITE( "ioctl(CDROMSUBCHNL)", ARG3,
   4356 		     sizeof(struct vki_cdrom_subchnl));
   4357       break;
   4358    case VKI_CDROMREADMODE2:
   4359       PRE_MEM_READ( "ioctl(CDROMREADMODE2)", ARG3, VKI_CD_FRAMESIZE_RAW0 );
   4360       break;
   4361    case VKI_CDROMREADTOCHDR:
   4362       PRE_MEM_WRITE( "ioctl(CDROMREADTOCHDR)", ARG3,
   4363 		     sizeof(struct vki_cdrom_tochdr));
   4364       break;
   4365    case VKI_CDROMREADTOCENTRY:
   4366       PRE_MEM_READ( "ioctl(CDROMREADTOCENTRY (cdte_format, char))",
   4367 		    (Addr) &(((struct vki_cdrom_tocentry*) ARG3)->cdte_format),
   4368 		    sizeof(((struct vki_cdrom_tocentry*) ARG3)->cdte_format));
   4369       PRE_MEM_READ( "ioctl(CDROMREADTOCENTRY (cdte_track, char))",
   4370 		    (Addr) &(((struct vki_cdrom_tocentry*) ARG3)->cdte_track),
   4371 		    sizeof(((struct vki_cdrom_tocentry*) ARG3)->cdte_track));
   4372       PRE_MEM_WRITE( "ioctl(CDROMREADTOCENTRY)", ARG3,
   4373 		     sizeof(struct vki_cdrom_tocentry));
   4374       break;
   4375    case VKI_CDROMMULTISESSION: /* 0x5310 */
   4376       PRE_MEM_WRITE( "ioctl(CDROMMULTISESSION)", ARG3,
   4377 		     sizeof(struct vki_cdrom_multisession));
   4378       break;
   4379    case VKI_CDROMVOLREAD: /* 0x5313 */
   4380       PRE_MEM_WRITE( "ioctl(CDROMVOLREAD)", ARG3,
   4381 		     sizeof(struct vki_cdrom_volctrl));
   4382       break;
   4383    case VKI_CDROMREADRAW: /* 0x5314 */
   4384       PRE_MEM_READ( "ioctl(CDROMREADRAW)", ARG3, sizeof(struct vki_cdrom_msf));
   4385       PRE_MEM_WRITE( "ioctl(CDROMREADRAW)", ARG3, VKI_CD_FRAMESIZE_RAW);
   4386       break;
   4387    case VKI_CDROMREADAUDIO: /* 0x530e */
   4388       PRE_MEM_READ( "ioctl(CDROMREADAUDIO)", ARG3,
   4389 		     sizeof (struct vki_cdrom_read_audio));
   4390       if ( ARG3 ) {
   4391          /* ToDo: don't do any of the following if the structure is invalid */
   4392          struct vki_cdrom_read_audio *cra = (struct vki_cdrom_read_audio *) ARG3;
   4393 	 PRE_MEM_WRITE( "ioctl(CDROMREADAUDIO).buf",
   4394 	                (Addr)(cra->buf), cra->nframes * VKI_CD_FRAMESIZE_RAW);
   4395       }
   4396       break;
   4397    case VKI_CDROMPLAYMSF:
   4398       PRE_MEM_READ( "ioctl(CDROMPLAYMSF)", ARG3, sizeof(struct vki_cdrom_msf));
   4399       break;
   4400       /* The following two are probably bogus (should check args
   4401 	 for readability).  JRS 20021117 */
   4402    case VKI_CDROM_DRIVE_STATUS: /* 0x5326 */
   4403    case VKI_CDROM_CLEAR_OPTIONS: /* 0x5321 */
   4404       break;
   4405 
   4406    case VKI_FIGETBSZ:
   4407       PRE_MEM_WRITE( "ioctl(FIGETBSZ)", ARG3, sizeof(unsigned long));
   4408       break;
   4409    case VKI_FIBMAP:
   4410       PRE_MEM_READ( "ioctl(FIBMAP)", ARG3, sizeof(int));
   4411       break;
   4412 
   4413    case VKI_FBIOGET_VSCREENINFO: /* 0x4600 */
   4414       PRE_MEM_WRITE( "ioctl(FBIOGET_VSCREENINFO)", ARG3,
   4415                      sizeof(struct vki_fb_var_screeninfo));
   4416       break;
   4417    case VKI_FBIOGET_FSCREENINFO: /* 0x4602 */
   4418       PRE_MEM_WRITE( "ioctl(FBIOGET_FSCREENINFO)", ARG3,
   4419                      sizeof(struct vki_fb_fix_screeninfo));
   4420       break;
   4421 
   4422    case VKI_PPCLAIM:
   4423    case VKI_PPEXCL:
   4424    case VKI_PPYIELD:
   4425    case VKI_PPRELEASE:
   4426       break;
   4427    case VKI_PPSETMODE:
   4428       PRE_MEM_READ( "ioctl(PPSETMODE)",   ARG3, sizeof(int) );
   4429       break;
   4430    case VKI_PPGETMODE:
   4431       PRE_MEM_WRITE( "ioctl(PPGETMODE)",  ARG3, sizeof(int) );
   4432       break;
   4433    case VKI_PPSETPHASE:
   4434       PRE_MEM_READ(  "ioctl(PPSETPHASE)", ARG3, sizeof(int) );
   4435       break;
   4436    case VKI_PPGETPHASE:
   4437       PRE_MEM_WRITE( "ioctl(PPGETPHASE)", ARG3, sizeof(int) );
   4438       break;
   4439    case VKI_PPGETMODES:
   4440       PRE_MEM_WRITE( "ioctl(PPGETMODES)", ARG3, sizeof(unsigned int) );
   4441       break;
   4442    case VKI_PPSETFLAGS:
   4443       PRE_MEM_READ(  "ioctl(PPSETFLAGS)", ARG3, sizeof(int) );
   4444       break;
   4445    case VKI_PPGETFLAGS:
   4446       PRE_MEM_WRITE( "ioctl(PPGETFLAGS)", ARG3, sizeof(int) );
   4447       break;
   4448    case VKI_PPRSTATUS:
   4449       PRE_MEM_WRITE( "ioctl(PPRSTATUS)",  ARG3, sizeof(unsigned char) );
   4450       break;
   4451    case VKI_PPRDATA:
   4452       PRE_MEM_WRITE( "ioctl(PPRDATA)",    ARG3, sizeof(unsigned char) );
   4453       break;
   4454    case VKI_PPRCONTROL:
   4455       PRE_MEM_WRITE( "ioctl(PPRCONTROL)", ARG3, sizeof(unsigned char) );
   4456       break;
   4457    case VKI_PPWDATA:
   4458       PRE_MEM_READ(  "ioctl(PPWDATA)",    ARG3, sizeof(unsigned char) );
   4459       break;
   4460    case VKI_PPWCONTROL:
   4461       PRE_MEM_READ(  "ioctl(PPWCONTROL)", ARG3, sizeof(unsigned char) );
   4462       break;
   4463    case VKI_PPFCONTROL:
   4464       PRE_MEM_READ(  "ioctl(PPFCONTROL)", ARG3, 2 * sizeof(unsigned char) );
   4465       break;
   4466    case VKI_PPDATADIR:
   4467       PRE_MEM_READ(  "ioctl(PPDATADIR)",  ARG3, sizeof(int) );
   4468       break;
   4469    case VKI_PPNEGOT:
   4470       PRE_MEM_READ(  "ioctl(PPNEGOT)",    ARG3, sizeof(int) );
   4471       break;
   4472    case VKI_PPWCTLONIRQ:
   4473       PRE_MEM_READ(  "ioctl(PPWCTLONIRQ)",ARG3, sizeof(unsigned char) );
   4474       break;
   4475    case VKI_PPCLRIRQ:
   4476       PRE_MEM_WRITE( "ioctl(PPCLRIRQ)",   ARG3, sizeof(int) );
   4477       break;
   4478    case VKI_PPSETTIME:
   4479       PRE_MEM_READ(  "ioctl(PPSETTIME)",  ARG3, sizeof(struct vki_timeval) );
   4480       break;
   4481    case VKI_PPGETTIME:
   4482       PRE_MEM_WRITE( "ioctl(PPGETTIME)",  ARG3, sizeof(struct vki_timeval) );
   4483       break;
   4484 
   4485    case VKI_GIO_FONT:
   4486       PRE_MEM_WRITE( "ioctl(GIO_FONT)", ARG3, 32 * 256 );
   4487       break;
   4488    case VKI_PIO_FONT:
   4489       PRE_MEM_READ( "ioctl(PIO_FONT)", ARG3, 32 * 256 );
   4490       break;
   4491 
   4492    case VKI_GIO_FONTX:
   4493       PRE_MEM_READ( "ioctl(GIO_FONTX)", ARG3, sizeof(struct vki_consolefontdesc) );
   4494       if ( ARG3 ) {
   4495          /* ToDo: don't do any of the following if the structure is invalid */
   4496          struct vki_consolefontdesc *cfd = (struct vki_consolefontdesc *)ARG3;
   4497          PRE_MEM_WRITE( "ioctl(GIO_FONTX).chardata", (Addr)cfd->chardata,
   4498                         32 * cfd->charcount );
   4499       }
   4500       break;
   4501    case VKI_PIO_FONTX:
   4502       PRE_MEM_READ( "ioctl(PIO_FONTX)", ARG3, sizeof(struct vki_consolefontdesc) );
   4503       if ( ARG3 ) {
   4504          /* ToDo: don't do any of the following if the structure is invalid */
   4505          struct vki_consolefontdesc *cfd = (struct vki_consolefontdesc *)ARG3;
   4506          PRE_MEM_READ( "ioctl(PIO_FONTX).chardata", (Addr)cfd->chardata,
   4507                        32 * cfd->charcount );
   4508       }
   4509       break;
   4510 
   4511    case VKI_PIO_FONTRESET:
   4512       break;
   4513 
   4514    case VKI_GIO_CMAP:
   4515       PRE_MEM_WRITE( "ioctl(GIO_CMAP)", ARG3, 16 * 3 );
   4516       break;
   4517    case VKI_PIO_CMAP:
   4518       PRE_MEM_READ( "ioctl(PIO_CMAP)", ARG3, 16 * 3 );
   4519       break;
   4520 
   4521    case VKI_KIOCSOUND:
   4522    case VKI_KDMKTONE:
   4523       break;
   4524 
   4525    case VKI_KDGETLED:
   4526       PRE_MEM_WRITE( "ioctl(KDGETLED)", ARG3, sizeof(char) );
   4527       break;
   4528    case VKI_KDSETLED:
   4529       break;
   4530 
   4531    case VKI_KDGKBTYPE:
   4532       PRE_MEM_WRITE( "ioctl(KDGKBTYPE)", ARG3, sizeof(char) );
   4533       break;
   4534 
   4535    case VKI_KDADDIO:
   4536    case VKI_KDDELIO:
   4537    case VKI_KDENABIO:
   4538    case VKI_KDDISABIO:
   4539       break;
   4540 
   4541    case VKI_KDSETMODE:
   4542       break;
   4543    case VKI_KDGETMODE:
   4544       PRE_MEM_WRITE( "ioctl(KDGETMODE)", ARG3, sizeof(int) );
   4545       break;
   4546 
   4547    case VKI_KDMAPDISP:
   4548    case VKI_KDUNMAPDISP:
   4549       break;
   4550 
   4551    case VKI_GIO_SCRNMAP:
   4552       PRE_MEM_WRITE( "ioctl(GIO_SCRNMAP)", ARG3, VKI_E_TABSZ );
   4553       break;
   4554    case VKI_PIO_SCRNMAP:
   4555       PRE_MEM_READ( "ioctl(PIO_SCRNMAP)", ARG3, VKI_E_TABSZ  );
   4556       break;
   4557    case VKI_GIO_UNISCRNMAP:
   4558       PRE_MEM_WRITE( "ioctl(GIO_UNISCRNMAP)", ARG3,
   4559                      VKI_E_TABSZ * sizeof(unsigned short) );
   4560       break;
   4561    case VKI_PIO_UNISCRNMAP:
   4562       PRE_MEM_READ( "ioctl(PIO_UNISCRNMAP)", ARG3,
   4563                     VKI_E_TABSZ * sizeof(unsigned short) );
   4564       break;
   4565 
   4566    case VKI_GIO_UNIMAP:
   4567       if ( ARG3 ) {
   4568          struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
   4569          PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entry_ct,
   4570                        sizeof(unsigned short));
   4571          PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entries,
   4572                        sizeof(struct vki_unipair *));
   4573          PRE_MEM_WRITE( "ioctl(GIO_UNIMAP).entries", (Addr)desc->entries,
   4574                         desc->entry_ct * sizeof(struct vki_unipair));
   4575       }
   4576       break;
   4577    case VKI_PIO_UNIMAP:
   4578       if ( ARG3 ) {
   4579          struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
   4580          PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entry_ct,
   4581                        sizeof(unsigned short) );
   4582          PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entries,
   4583                        sizeof(struct vki_unipair *) );
   4584          PRE_MEM_READ( "ioctl(PIO_UNIMAP).entries", (Addr)desc->entries,
   4585                        desc->entry_ct * sizeof(struct vki_unipair) );
   4586       }
   4587       break;
   4588    case VKI_PIO_UNIMAPCLR:
   4589       PRE_MEM_READ( "ioctl(GIO_UNIMAP)", ARG3, sizeof(struct vki_unimapinit));
   4590       break;
   4591 
   4592    case VKI_KDGKBMODE:
   4593       PRE_MEM_WRITE( "ioctl(KDGKBMODE)", ARG3, sizeof(int) );
   4594       break;
   4595    case VKI_KDSKBMODE:
   4596       break;
   4597 
   4598    case VKI_KDGKBMETA:
   4599       PRE_MEM_WRITE( "ioctl(KDGKBMETA)", ARG3, sizeof(int) );
   4600       break;
   4601    case VKI_KDSKBMETA:
   4602       break;
   4603 
   4604    case VKI_KDGKBLED:
   4605       PRE_MEM_WRITE( "ioctl(KDGKBLED)", ARG3, sizeof(char) );
   4606       break;
   4607    case VKI_KDSKBLED:
   4608       break;
   4609 
   4610    case VKI_KDGKBENT:
   4611       PRE_MEM_READ( "ioctl(KDGKBENT).kb_table",
   4612                     (Addr)&((struct vki_kbentry *)ARG3)->kb_table,
   4613                     sizeof(((struct vki_kbentry *)ARG3)->kb_table) );
   4614       PRE_MEM_READ( "ioctl(KDGKBENT).kb_index",
   4615                     (Addr)&((struct vki_kbentry *)ARG3)->kb_index,
   4616                     sizeof(((struct vki_kbentry *)ARG3)->kb_index) );
   4617       PRE_MEM_WRITE( "ioctl(KDGKBENT).kb_value",
   4618 		     (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
   4619 		     sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
   4620       break;
   4621    case VKI_KDSKBENT:
   4622       PRE_MEM_READ( "ioctl(KDSKBENT).kb_table",
   4623                     (Addr)&((struct vki_kbentry *)ARG3)->kb_table,
   4624                     sizeof(((struct vki_kbentry *)ARG3)->kb_table) );
   4625       PRE_MEM_READ( "ioctl(KDSKBENT).kb_index",
   4626                     (Addr)&((struct vki_kbentry *)ARG3)->kb_index,
   4627                     sizeof(((struct vki_kbentry *)ARG3)->kb_index) );
   4628       PRE_MEM_READ( "ioctl(KDSKBENT).kb_value",
   4629                     (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
   4630                     sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
   4631       break;
   4632 
   4633    case VKI_KDGKBSENT:
   4634       PRE_MEM_READ( "ioctl(KDGKBSENT).kb_func",
   4635                     (Addr)&((struct vki_kbsentry *)ARG3)->kb_func,
   4636                     sizeof(((struct vki_kbsentry *)ARG3)->kb_func) );
   4637       PRE_MEM_WRITE( "ioctl(KDGKSENT).kb_string",
   4638 		     (Addr)((struct vki_kbsentry *)ARG3)->kb_string,
   4639 		     sizeof(((struct vki_kbsentry *)ARG3)->kb_string) );
   4640       break;
   4641    case VKI_KDSKBSENT:
   4642       PRE_MEM_READ( "ioctl(KDSKBSENT).kb_func",
   4643                     (Addr)&((struct vki_kbsentry *)ARG3)->kb_func,
   4644                     sizeof(((struct vki_kbsentry *)ARG3)->kb_func) );
   4645       PRE_MEM_RASCIIZ( "ioctl(KDSKBSENT).kb_string",
   4646                        (Addr)((struct vki_kbsentry *)ARG3)->kb_string );
   4647       break;
   4648 
   4649    case VKI_KDGKBDIACR:
   4650       PRE_MEM_WRITE( "ioctl(KDGKBDIACR)", ARG3, sizeof(struct vki_kbdiacrs) );
   4651       break;
   4652    case VKI_KDSKBDIACR:
   4653       PRE_MEM_READ( "ioctl(KDSKBDIACR)", ARG3, sizeof(struct vki_kbdiacrs) );
   4654       break;
   4655 
   4656    case VKI_KDGETKEYCODE:
   4657       PRE_MEM_READ( "ioctl(KDGETKEYCODE).scancode",
   4658                     (Addr)&((struct vki_kbkeycode *)ARG3)->scancode,
   4659                     sizeof(((struct vki_kbkeycode *)ARG3)->scancode) );
   4660       PRE_MEM_WRITE( "ioctl(KDGETKEYCODE).keycode",
   4661 		     (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
   4662 		     sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
   4663       break;
   4664    case VKI_KDSETKEYCODE:
   4665       PRE_MEM_READ( "ioctl(KDSETKEYCODE).scancode",
   4666                     (Addr)&((struct vki_kbkeycode *)ARG3)->scancode,
   4667                     sizeof(((struct vki_kbkeycode *)ARG3)->scancode) );
   4668       PRE_MEM_READ( "ioctl(KDSETKEYCODE).keycode",
   4669                     (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
   4670                     sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
   4671       break;
   4672 
   4673    case VKI_KDSIGACCEPT:
   4674       break;
   4675 
   4676    case VKI_KDKBDREP:
   4677       PRE_MEM_READ( "ioctl(KBKBDREP)", ARG3, sizeof(struct vki_kbd_repeat) );
   4678       break;
   4679 
   4680    case VKI_KDFONTOP:
   4681       if ( ARG3 ) {
   4682          struct vki_console_font_op *op = (struct vki_console_font_op *) ARG3;
   4683          PRE_MEM_READ( "ioctl(KDFONTOP)", (Addr)op,
   4684                        sizeof(struct vki_console_font_op) );
   4685          switch ( op->op ) {
   4686             case VKI_KD_FONT_OP_SET:
   4687                PRE_MEM_READ( "ioctl(KDFONTOP,KD_FONT_OP_SET).data",
   4688                              (Addr)op->data,
   4689                              (op->width + 7) / 8 * 32 * op->charcount );
   4690                break;
   4691             case VKI_KD_FONT_OP_GET:
   4692                if ( op->data )
   4693                   PRE_MEM_WRITE( "ioctl(KDFONTOP,KD_FONT_OP_GET).data",
   4694                                  (Addr)op->data,
   4695                                  (op->width + 7) / 8 * 32 * op->charcount );
   4696                break;
   4697             case VKI_KD_FONT_OP_SET_DEFAULT:
   4698                if ( op->data )
   4699                   PRE_MEM_RASCIIZ( "ioctl(KDFONTOP,KD_FONT_OP_SET_DEFAULT).data",
   4700                                    (Addr)op->data );
   4701                break;
   4702             case VKI_KD_FONT_OP_COPY:
   4703                break;
   4704          }
   4705       }
   4706       break;
   4707 
   4708    case VKI_VT_OPENQRY:
   4709       PRE_MEM_WRITE( "ioctl(VT_OPENQRY)", ARG3, sizeof(int) );
   4710       break;
   4711    case VKI_VT_GETMODE:
   4712       PRE_MEM_WRITE( "ioctl(VT_GETMODE)", ARG3, sizeof(struct vki_vt_mode) );
   4713       break;
   4714    case VKI_VT_SETMODE:
   4715       PRE_MEM_READ( "ioctl(VT_SETMODE)", ARG3, sizeof(struct vki_vt_mode) );
   4716       break;
   4717    case VKI_VT_GETSTATE:
   4718       PRE_MEM_WRITE( "ioctl(VT_GETSTATE).v_active",
   4719                      (Addr) &(((struct vki_vt_stat*) ARG3)->v_active),
   4720                      sizeof(((struct vki_vt_stat*) ARG3)->v_active));
   4721       PRE_MEM_WRITE( "ioctl(VT_GETSTATE).v_state",
   4722                      (Addr) &(((struct vki_vt_stat*) ARG3)->v_state),
   4723                      sizeof(((struct vki_vt_stat*) ARG3)->v_state));
   4724       break;
   4725    case VKI_VT_RELDISP:
   4726    case VKI_VT_ACTIVATE:
   4727    case VKI_VT_WAITACTIVE:
   4728    case VKI_VT_DISALLOCATE:
   4729       break;
   4730    case VKI_VT_RESIZE:
   4731       PRE_MEM_READ( "ioctl(VT_RESIZE)", ARG3, sizeof(struct vki_vt_sizes) );
   4732       break;
   4733    case VKI_VT_RESIZEX:
   4734       PRE_MEM_READ( "ioctl(VT_RESIZEX)", ARG3, sizeof(struct vki_vt_consize) );
   4735       break;
   4736    case VKI_VT_LOCKSWITCH:
   4737    case VKI_VT_UNLOCKSWITCH:
   4738       break;
   4739 
   4740    case VKI_USBDEVFS_CONTROL:
   4741       if ( ARG3 ) {
   4742          struct vki_usbdevfs_ctrltransfer *vkuc = (struct vki_usbdevfs_ctrltransfer *)ARG3;
   4743          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).bRequestType", (Addr)&vkuc->bRequestType, sizeof(vkuc->bRequestType));
   4744          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).bRequest", (Addr)&vkuc->bRequest, sizeof(vkuc->bRequest));
   4745          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wValue", (Addr)&vkuc->wValue, sizeof(vkuc->wValue));
   4746          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wIndex", (Addr)&vkuc->wIndex, sizeof(vkuc->wIndex));
   4747          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wLength", (Addr)&vkuc->wLength, sizeof(vkuc->wLength));
   4748          PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).timeout", (Addr)&vkuc->timeout, sizeof(vkuc->timeout));
   4749          if (vkuc->bRequestType & 0x80)
   4750             PRE_MEM_WRITE( "ioctl(USBDEVFS_CONTROL).data", (Addr)vkuc->data, vkuc->wLength);
   4751          else
   4752             PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).data", (Addr)vkuc->data, vkuc->wLength);
   4753       }
   4754       break;
   4755    case VKI_USBDEVFS_BULK:
   4756       if ( ARG3 ) {
   4757          struct vki_usbdevfs_bulktransfer *vkub = (struct vki_usbdevfs_bulktransfer *)ARG3;
   4758          PRE_MEM_READ( "ioctl(USBDEVFS_BULK)", ARG3, sizeof(struct vki_usbdevfs_bulktransfer));
   4759          if (vkub->ep & 0x80)
   4760             PRE_MEM_WRITE( "ioctl(USBDEVFS_BULK).data", (Addr)vkub->data, vkub->len);
   4761          else
   4762             PRE_MEM_READ( "ioctl(USBDEVFS_BULK).data", (Addr)vkub->data, vkub->len);
   4763          break;
   4764       }
   4765    case VKI_USBDEVFS_GETDRIVER:
   4766       if ( ARG3 ) {
   4767          struct vki_usbdevfs_getdriver *vkugd = (struct vki_usbdevfs_getdriver *) ARG3;
   4768          PRE_MEM_WRITE( "ioctl(USBDEVFS_GETDRIVER)", (Addr)&vkugd->driver, sizeof(vkugd->driver));
   4769          break;
   4770       }
   4771    case VKI_USBDEVFS_SUBMITURB:
   4772       if ( ARG3 ) {
   4773          struct vki_usbdevfs_urb *vkuu = (struct vki_usbdevfs_urb *)ARG3;
   4774 
   4775          /* Not the whole struct needs to be initialized */
   4776          PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).endpoint", (Addr)&vkuu->endpoint, sizeof(vkuu->endpoint));
   4777          PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).type", (Addr)&vkuu->type, sizeof(vkuu->type));
   4778          PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).flags", (Addr)&vkuu->flags, sizeof(vkuu->flags));
   4779          PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)&vkuu->buffer, sizeof(vkuu->buffer));
   4780          PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).signr", (Addr)&vkuu->signr, sizeof(vkuu->signr));
   4781          PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).status", (Addr)&vkuu->status, sizeof(vkuu->status));
   4782          if (vkuu->type == VKI_USBDEVFS_URB_TYPE_CONTROL) {
   4783             struct vki_usbdevfs_setuppacket *vkusp = (struct vki_usbdevfs_setuppacket *)vkuu->buffer;
   4784             PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer_length", (Addr)&vkuu->buffer_length, sizeof(vkuu->buffer_length));
   4785             PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer.setup_packet", (Addr)vkusp, sizeof(*vkusp));
   4786             if (vkusp->bRequestType & 0x80)
   4787                PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer.data", (Addr)(vkusp+1), vkuu->buffer_length - sizeof(*vkusp));
   4788             else
   4789                PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer.data", (Addr)(vkusp+1), vkuu->buffer_length - sizeof(*vkusp));
   4790             PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).actual_length", (Addr)&vkuu->actual_length, sizeof(vkuu->actual_length));
   4791          } else if (vkuu->type == VKI_USBDEVFS_URB_TYPE_ISO) {
   4792             int total_length = 0;
   4793             int i;
   4794             PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).number_of_packets", (Addr)&vkuu->number_of_packets, sizeof(vkuu->number_of_packets));
   4795             for(i=0; i<vkuu->number_of_packets; i++) {
   4796                PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).iso_frame_desc[].length", (Addr)&vkuu->iso_frame_desc[i].length, sizeof(vkuu->iso_frame_desc[i].length));
   4797                PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).iso_frame_desc[].actual_length", (Addr)&vkuu->iso_frame_desc[i].actual_length, sizeof(vkuu->iso_frame_desc[i].actual_length));
   4798                PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).iso_frame_desc[].status", (Addr)&vkuu->iso_frame_desc[i].status, sizeof(vkuu->iso_frame_desc[i].status));
   4799                total_length += vkuu->iso_frame_desc[i].length;
   4800             }
   4801             if (vkuu->endpoint & 0x80)
   4802                PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, total_length);
   4803             else
   4804                PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, total_length);
   4805             PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).error_count", (Addr)&vkuu->error_count, sizeof(vkuu->error_count));
   4806          } else {
   4807             PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer_length", (Addr)&vkuu->buffer_length, sizeof(vkuu->buffer_length));
   4808             if (vkuu->endpoint & 0x80)
   4809                PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, vkuu->buffer_length);
   4810             else
   4811                PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, vkuu->buffer_length);
   4812             PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).actual_length", (Addr)&vkuu->actual_length, sizeof(vkuu->actual_length));
   4813          }
   4814          break;
   4815       }
   4816    case VKI_USBDEVFS_DISCARDURB:
   4817       break;
   4818    case VKI_USBDEVFS_REAPURB:
   4819       if ( ARG3 ) {
   4820          PRE_MEM_WRITE( "ioctl(USBDEVFS_REAPURB)", ARG3, sizeof(struct vki_usbdevfs_urb **));
   4821          break;
   4822       }
   4823    case VKI_USBDEVFS_REAPURBNDELAY:
   4824       if ( ARG3 ) {
   4825          PRE_MEM_WRITE( "ioctl(USBDEVFS_REAPURBNDELAY)", ARG3, sizeof(struct vki_usbdevfs_urb **));
   4826          break;
   4827       }
   4828    case VKI_USBDEVFS_CONNECTINFO:
   4829       PRE_MEM_WRITE( "ioctl(USBDEVFS_CONNECTINFO)", ARG3, sizeof(struct vki_usbdevfs_connectinfo));
   4830       break;
   4831    case VKI_USBDEVFS_IOCTL:
   4832       if ( ARG3 ) {
   4833          struct vki_usbdevfs_ioctl *vkui = (struct vki_usbdevfs_ioctl *)ARG3;
   4834          UInt dir2, size2;
   4835          PRE_MEM_READ("ioctl(USBDEVFS_IOCTL)", (Addr)vkui, sizeof(struct vki_usbdevfs_ioctl));
   4836          dir2  = _VKI_IOC_DIR(vkui->ioctl_code);
   4837          size2 = _VKI_IOC_SIZE(vkui->ioctl_code);
   4838          if (size2 > 0) {
   4839             if (dir2 & _VKI_IOC_WRITE)
   4840                PRE_MEM_READ("ioctl(USBDEVFS_IOCTL).dataWrite", (Addr)vkui->data, size2);
   4841             else if (dir2 & _VKI_IOC_READ)
   4842                PRE_MEM_WRITE("ioctl(USBDEVFS_IOCTL).dataRead", (Addr)vkui->data, size2);
   4843          }
   4844       }
   4845       break;
   4846 
   4847       /* I2C (/dev/i2c-*) ioctls */
   4848    case VKI_I2C_SLAVE:
   4849    case VKI_I2C_SLAVE_FORCE:
   4850    case VKI_I2C_TENBIT:
   4851    case VKI_I2C_PEC:
   4852       break;
   4853    case VKI_I2C_FUNCS:
   4854       PRE_MEM_WRITE( "ioctl(I2C_FUNCS)", ARG3, sizeof(unsigned long) );
   4855       break;
   4856 
   4857       /* Wireless extensions ioctls */
   4858    case VKI_SIOCSIWCOMMIT:
   4859    case VKI_SIOCSIWNWID:
   4860    case VKI_SIOCSIWFREQ:
   4861    case VKI_SIOCSIWMODE:
   4862    case VKI_SIOCSIWSENS:
   4863    case VKI_SIOCSIWRANGE:
   4864    case VKI_SIOCSIWPRIV:
   4865    case VKI_SIOCSIWSTATS:
   4866    case VKI_SIOCSIWSPY:
   4867    case VKI_SIOCSIWTHRSPY:
   4868    case VKI_SIOCSIWAP:
   4869    case VKI_SIOCSIWSCAN:
   4870    case VKI_SIOCSIWESSID:
   4871    case VKI_SIOCSIWRATE:
   4872    case VKI_SIOCSIWNICKN:
   4873    case VKI_SIOCSIWRTS:
   4874    case VKI_SIOCSIWFRAG:
   4875    case VKI_SIOCSIWTXPOW:
   4876    case VKI_SIOCSIWRETRY:
   4877    case VKI_SIOCSIWENCODE:
   4878    case VKI_SIOCSIWPOWER:
   4879    case VKI_SIOCSIWGENIE:
   4880    case VKI_SIOCSIWMLME:
   4881    case VKI_SIOCSIWAUTH:
   4882    case VKI_SIOCSIWENCODEEXT:
   4883    case VKI_SIOCSIWPMKSA:
   4884       break;
   4885    case VKI_SIOCGIWNAME:
   4886       if (ARG3) {
   4887          PRE_MEM_WRITE("ioctl(SIOCGIWNAME)",
   4888                        (Addr)((struct vki_iwreq *)ARG3)->u.name,
   4889                        sizeof(((struct vki_iwreq *)ARG3)->u.name));
   4890       }
   4891       break;
   4892    case VKI_SIOCGIWNWID:
   4893    case VKI_SIOCGIWSENS:
   4894    case VKI_SIOCGIWRATE:
   4895    case VKI_SIOCGIWRTS:
   4896    case VKI_SIOCGIWFRAG:
   4897    case VKI_SIOCGIWTXPOW:
   4898    case VKI_SIOCGIWRETRY:
   4899    case VKI_SIOCGIWPOWER:
   4900    case VKI_SIOCGIWAUTH:
   4901       if (ARG3) {
   4902          PRE_MEM_WRITE("ioctl(SIOCGIW[NWID|SENS|RATE|RTS|FRAG|TXPOW|"
   4903                        "RETRY|PARAM|AUTH])",
   4904                        (Addr)&((struct vki_iwreq *)ARG3)->u.nwid,
   4905                        sizeof(struct vki_iw_param));
   4906       }
   4907       break;
   4908    case VKI_SIOCGIWFREQ:
   4909       if (ARG3) {
   4910          PRE_MEM_WRITE("ioctl(SIOCGIWFREQ",
   4911                        (Addr)&((struct vki_iwreq *)ARG3)->u.freq,
   4912                        sizeof(struct vki_iw_freq));
   4913       }
   4914       break;
   4915    case VKI_SIOCGIWMODE:
   4916       if (ARG3) {
   4917          PRE_MEM_WRITE("ioctl(SIOCGIWMODE",
   4918                        (Addr)&((struct vki_iwreq *)ARG3)->u.mode,
   4919                        sizeof(__vki_u32));
   4920       }
   4921       break;
   4922    case VKI_SIOCGIWRANGE:
   4923    case VKI_SIOCGIWPRIV:
   4924    case VKI_SIOCGIWSTATS:
   4925    case VKI_SIOCGIWSPY:
   4926    case VKI_SIOCGIWTHRSPY:
   4927    case VKI_SIOCGIWAPLIST:
   4928    case VKI_SIOCGIWSCAN:
   4929    case VKI_SIOCGIWESSID:
   4930    case VKI_SIOCGIWNICKN:
   4931    case VKI_SIOCGIWENCODE:
   4932    case VKI_SIOCGIWGENIE:
   4933    case VKI_SIOCGIWENCODEEXT:
   4934       if (ARG3) {
   4935          struct vki_iw_point* point;
   4936          point = &((struct vki_iwreq *)ARG3)->u.data;
   4937          PRE_MEM_WRITE("ioctl(SIOCGIW[RANGE|PRIV|STATS|SPY|THRSPY|"
   4938                        "APLIST|SCAN|ESSID|NICKN|ENCODE|GENIE|ENCODEEXT])",
   4939                        (Addr)point->pointer, point->length);
   4940       }
   4941       break;
   4942    case VKI_SIOCGIWAP:
   4943       if (ARG3) {
   4944          PRE_MEM_WRITE("ioctl(SIOCGIWAP)",
   4945                        (Addr)&((struct vki_iwreq *)ARG3)->u.ap_addr,
   4946                        sizeof(struct vki_sockaddr));
   4947       }
   4948       break;
   4949 
   4950 #ifdef ANDROID
   4951       /* ashmem */
   4952    case VKI_ASHMEM_GET_SIZE:
   4953    case VKI_ASHMEM_SET_SIZE:
   4954    case VKI_ASHMEM_GET_PROT_MASK:
   4955    case VKI_ASHMEM_SET_PROT_MASK:
   4956    case VKI_ASHMEM_GET_PIN_STATUS:
   4957    case VKI_ASHMEM_PURGE_ALL_CACHES:
   4958        break;
   4959    case VKI_ASHMEM_GET_NAME:
   4960        PRE_MEM_WRITE( "ioctl(ASHMEM_SET_NAME)", ARG3, VKI_ASHMEM_NAME_LEN );
   4961        break;
   4962    case VKI_ASHMEM_SET_NAME:
   4963        PRE_MEM_RASCIIZ( "ioctl(ASHMEM_SET_NAME)", ARG3);
   4964        break;
   4965    case VKI_ASHMEM_PIN:
   4966    case VKI_ASHMEM_UNPIN:
   4967        PRE_MEM_READ( "ioctl(ASHMEM_PIN|ASHMEM_UNPIN)", ARG3, sizeof(struct vki_ashmem_pin) );
   4968        break;
   4969 
   4970      /* binder */
   4971    case VKI_BINDER_WRITE_READ:
   4972        if (ARG3) {
   4973            struct vki_binder_write_read* bwr = (struct vki_binder_write_read*)ARG3;
   4974 
   4975            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_buffer",
   4976                           bwr->write_buffer);
   4977            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_size",
   4978                           bwr->write_size);
   4979            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_consumed",
   4980                           bwr->write_consumed);
   4981            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_buffer",
   4982                           bwr->read_buffer);
   4983            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_size",
   4984                           bwr->read_size);
   4985            PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_consumed",
   4986                           bwr->read_consumed);
   4987 
   4988            PRE_FIELD_WRITE("ioctl(BINDER_WRITE_READ).write_consumed",
   4989                            bwr->write_consumed);
   4990            PRE_FIELD_WRITE("ioctl(BINDER_WRITE_READ).read_consumed",
   4991                            bwr->read_consumed);
   4992 
   4993            if (bwr->read_size)
   4994                PRE_MEM_WRITE("ioctl(BINDER_WRITE_READ).read_buffer[]",
   4995                              (Addr)bwr->read_buffer, bwr->read_size);
   4996            if (bwr->write_size)
   4997                PRE_MEM_READ("ioctl(BINDER_WRITE_READ).write_buffer[]",
   4998                             (Addr)bwr->write_buffer, bwr->write_size);
   4999        }
   5000        break;
   5001 
   5002    case VKI_BINDER_SET_IDLE_TIMEOUT:
   5003    case VKI_BINDER_SET_MAX_THREADS:
   5004    case VKI_BINDER_SET_IDLE_PRIORITY:
   5005    case VKI_BINDER_SET_CONTEXT_MGR:
   5006    case VKI_BINDER_THREAD_EXIT:
   5007        break;
   5008    case VKI_BINDER_VERSION:
   5009        if (ARG3) {
   5010            struct vki_binder_version* bv = (struct vki_binder_version*)ARG3;
   5011            PRE_FIELD_WRITE("ioctl(BINDER_VERSION)", bv->protocol_version);
   5012        }
   5013        break;
   5014 #endif
   5015 
   5016    default:
   5017       /* EVIOC* are variable length and return size written on success */
   5018       switch (ARG2 & ~(_VKI_IOC_SIZEMASK << _VKI_IOC_SIZESHIFT)) {
   5019       case VKI_EVIOCGNAME(0):
   5020       case VKI_EVIOCGPHYS(0):
   5021       case VKI_EVIOCGUNIQ(0):
   5022       case VKI_EVIOCGKEY(0):
   5023       case VKI_EVIOCGLED(0):
   5024       case VKI_EVIOCGSND(0):
   5025       case VKI_EVIOCGSW(0):
   5026       case VKI_EVIOCGBIT(VKI_EV_SYN,0):
   5027       case VKI_EVIOCGBIT(VKI_EV_KEY,0):
   5028       case VKI_EVIOCGBIT(VKI_EV_REL,0):
   5029       case VKI_EVIOCGBIT(VKI_EV_ABS,0):
   5030       case VKI_EVIOCGBIT(VKI_EV_MSC,0):
   5031       case VKI_EVIOCGBIT(VKI_EV_SW,0):
   5032       case VKI_EVIOCGBIT(VKI_EV_LED,0):
   5033       case VKI_EVIOCGBIT(VKI_EV_SND,0):
   5034       case VKI_EVIOCGBIT(VKI_EV_REP,0):
   5035       case VKI_EVIOCGBIT(VKI_EV_FF,0):
   5036       case VKI_EVIOCGBIT(VKI_EV_PWR,0):
   5037       case VKI_EVIOCGBIT(VKI_EV_FF_STATUS,0):
   5038          PRE_MEM_WRITE("ioctl(EVIO*)", ARG3, _VKI_IOC_SIZE(ARG2));
   5039          break;
   5040       default:
   5041          ML_(PRE_unknown_ioctl)(tid, ARG2, ARG3);
   5042          break;
   5043       }
   5044       break;
   5045    }
   5046 }
   5047 
   5048 POST(sys_ioctl)
   5049 {
   5050    vg_assert(SUCCESS);
   5051    switch (ARG2 /* request */) {
   5052    case VKI_TCSETS:
   5053    case VKI_TCSETSW:
   5054    case VKI_TCSETSF:
   5055       break;
   5056    case VKI_TCGETS:
   5057       POST_MEM_WRITE( ARG3, sizeof(struct vki_termios) );
   5058       break;
   5059    case VKI_TCSETA:
   5060    case VKI_TCSETAW:
   5061    case VKI_TCSETAF:
   5062       break;
   5063    case VKI_TCGETA:
   5064       POST_MEM_WRITE( ARG3, sizeof(struct vki_termio) );
   5065       break;
   5066    case VKI_TCSBRK:
   5067    case VKI_TCXONC:
   5068    case VKI_TCSBRKP:
   5069    case VKI_TCFLSH:
   5070       break;
   5071    case VKI_TIOCGWINSZ:
   5072       POST_MEM_WRITE( ARG3, sizeof(struct vki_winsize) );
   5073       break;
   5074    case VKI_TIOCSWINSZ:
   5075    case VKI_TIOCMBIS:
   5076    case VKI_TIOCMBIC:
   5077    case VKI_TIOCMSET:
   5078       break;
   5079    case VKI_TIOCMGET:
   5080       POST_MEM_WRITE( ARG3, sizeof(unsigned int) );
   5081       break;
   5082    case VKI_TIOCLINUX:
   5083       POST_MEM_WRITE( ARG3, sizeof(char *) );
   5084       break;
   5085    case VKI_TIOCGPGRP:
   5086       /* Get process group ID for foreground processing group. */
   5087       POST_MEM_WRITE( ARG3, sizeof(vki_pid_t) );
   5088       break;
   5089    case VKI_TIOCSPGRP:
   5090       /* Set a process group ID? */
   5091       POST_MEM_WRITE( ARG3, sizeof(vki_pid_t) );
   5092       break;
   5093    case VKI_TIOCGPTN: /* Get Pty Number (of pty-mux device) */
   5094       POST_MEM_WRITE( ARG3, sizeof(int));
   5095       break;
   5096    case VKI_TIOCSCTTY:
   5097       break;
   5098    case VKI_TIOCSPTLCK: /* Lock/unlock Pty */
   5099       break;
   5100    case VKI_FIONBIO:
   5101       break;
   5102    case VKI_FIOASYNC:
   5103       break;
   5104    case VKI_FIONREAD:                /* identical to SIOCINQ */
   5105       POST_MEM_WRITE( ARG3, sizeof(int) );
   5106       break;
   5107 
   5108    case VKI_TIOCSERGETLSR:
   5109       POST_MEM_WRITE( ARG3, sizeof(int) );
   5110       break;
   5111    case VKI_TIOCGICOUNT:
   5112       POST_MEM_WRITE( ARG3, sizeof(struct vki_serial_icounter_struct) );
   5113       break;
   5114 
   5115    case VKI_SG_SET_COMMAND_Q:
   5116       break;
   5117    case VKI_SG_IO:
   5118       POST_MEM_WRITE(ARG3, sizeof(vki_sg_io_hdr_t));
   5119       break;
   5120    case VKI_SG_GET_SCSI_ID:
   5121       POST_MEM_WRITE(ARG3, sizeof(vki_sg_scsi_id_t));
   5122       break;
   5123    case VKI_SG_SET_RESERVED_SIZE:
   5124       break;
   5125    case VKI_SG_SET_TIMEOUT:
   5126       break;
   5127    case VKI_SG_GET_RESERVED_SIZE:
   5128       POST_MEM_WRITE(ARG3, sizeof(int));
   5129       break;
   5130    case VKI_SG_GET_TIMEOUT:
   5131       break;
   5132    case VKI_SG_GET_VERSION_NUM:
   5133       POST_MEM_WRITE(ARG3, sizeof(int));
   5134       break;
   5135    case VKI_SG_EMULATED_HOST:
   5136       POST_MEM_WRITE(ARG3, sizeof(int));
   5137       break;
   5138    case VKI_SG_GET_SG_TABLESIZE:
   5139       POST_MEM_WRITE(ARG3, sizeof(int));
   5140       break;
   5141 
   5142    case VKI_IIOCGETCPS:
   5143       POST_MEM_WRITE( ARG3, VKI_ISDN_MAX_CHANNELS * 2 * sizeof(unsigned long) );
   5144       break;
   5145    case VKI_IIOCNETGPN:
   5146       POST_MEM_WRITE( ARG3, sizeof(vki_isdn_net_ioctl_phone) );
   5147       break;
   5148 
   5149       /* These all use struct ifreq AFAIK */
   5150    case VKI_SIOCGIFINDEX:        /* get iface index              */
   5151       POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_ifindex,
   5152                       sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_ifindex) );
   5153       break;
   5154    case VKI_SIOCGIFFLAGS:        /* get flags                    */
   5155       POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
   5156                       sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
   5157       break;
   5158    case VKI_SIOCGIFHWADDR:       /* Get hardware address         */
   5159       POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->ifr_hwaddr,
   5160                       sizeof(((struct vki_ifreq *)ARG3)->ifr_hwaddr) );
   5161       break;
   5162    case VKI_SIOCGIFMTU:          /* get MTU size                 */
   5163       POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_mtu,
   5164                       sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_mtu) );
   5165       break;
   5166    case VKI_SIOCGIFADDR:         /* get PA address               */
   5167    case VKI_SIOCGIFDSTADDR:      /* get remote PA address        */
   5168    case VKI_SIOCGIFBRDADDR:      /* get broadcast PA address     */
   5169    case VKI_SIOCGIFNETMASK:      /* get network PA mask          */
   5170       POST_MEM_WRITE(
   5171                 (Addr)&((struct vki_ifreq *)ARG3)->ifr_addr,
   5172                 sizeof(((struct vki_ifreq *)ARG3)->ifr_addr) );
   5173       break;
   5174    case VKI_SIOCGIFMETRIC:       /* get metric                   */
   5175       POST_MEM_WRITE(
   5176                 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_metric,
   5177                 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_metric) );
   5178       break;
   5179    case VKI_SIOCGIFMAP:          /* Get device parameters        */
   5180       POST_MEM_WRITE(
   5181                 (Addr)&((struct vki_ifreq *)ARG3)->ifr_map,
   5182                 sizeof(((struct vki_ifreq *)ARG3)->ifr_map) );
   5183       break;
   5184      break;
   5185    case VKI_SIOCGIFTXQLEN:       /* Get the tx queue length      */
   5186       POST_MEM_WRITE(
   5187                 (Addr)&((struct vki_ifreq *)ARG3)->ifr_qlen,
   5188                 sizeof(((struct vki_ifreq *)ARG3)->ifr_qlen) );
   5189       break;
   5190    case VKI_SIOCGIFNAME:         /* get iface name               */
   5191       POST_MEM_WRITE(
   5192                 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_name,
   5193                 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_name) );
   5194       break;
   5195    case VKI_SIOCGMIIPHY:         /* get hardware entry           */
   5196       POST_MEM_WRITE(
   5197                 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
   5198                 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
   5199       break;
   5200    case VKI_SIOCGMIIREG:         /* get hardware entry registers */
   5201       POST_MEM_WRITE(
   5202                 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_out,
   5203                 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_out) );
   5204       break;
   5205    case VKI_SIOCGIFCONF:         /* get iface list               */
   5206       /* WAS:
   5207 	 PRE_MEM_WRITE("ioctl(SIOCGIFCONF)", ARG3, sizeof(struct ifconf));
   5208 	 KERNEL_DO_SYSCALL(tid,RES);
   5209 	 if (!VG_(is_kerror)(RES) && RES == 0)
   5210 	 POST_MEM_WRITE(ARG3, sizeof(struct ifconf));
   5211       */
   5212       if (RES == 0 && ARG3 ) {
   5213 	 struct vki_ifconf *ifc = (struct vki_ifconf *) ARG3;
   5214 	 if (ifc->vki_ifc_buf != NULL)
   5215 	    POST_MEM_WRITE( (Addr)(ifc->vki_ifc_buf), ifc->ifc_len );
   5216       }
   5217       break;
   5218    case VKI_SIOCGSTAMP:
   5219       POST_MEM_WRITE( ARG3, sizeof(struct vki_timeval) );
   5220       break;
   5221    case VKI_SIOCGSTAMPNS:
   5222       POST_MEM_WRITE( ARG3, sizeof(struct vki_timespec) );
   5223       break;
   5224       /* SIOCOUTQ is an ioctl that, when called on a socket, returns
   5225 	 the number of bytes currently in that socket's send buffer.
   5226 	 It writes this value as an int to the memory location
   5227 	 indicated by the third argument of ioctl(2). */
   5228    case VKI_SIOCOUTQ:
   5229       POST_MEM_WRITE(ARG3, sizeof(int));
   5230       break;
   5231    case VKI_SIOCGRARP:           /* get RARP table entry         */
   5232    case VKI_SIOCGARP:            /* get ARP table entry          */
   5233       POST_MEM_WRITE(ARG3, sizeof(struct vki_arpreq));
   5234       break;
   5235 
   5236    case VKI_SIOCSIFFLAGS:        /* set flags                    */
   5237    case VKI_SIOCSIFMAP:          /* Set device parameters        */
   5238    case VKI_SIOCSIFTXQLEN:       /* Set the tx queue length      */
   5239    case VKI_SIOCSIFDSTADDR:      /* set remote PA address        */
   5240    case VKI_SIOCSIFBRDADDR:      /* set broadcast PA address     */
   5241    case VKI_SIOCSIFNETMASK:      /* set network PA mask          */
   5242    case VKI_SIOCSIFMETRIC:       /* set metric                   */
   5243    case VKI_SIOCSIFADDR:         /* set PA address               */
   5244    case VKI_SIOCSIFMTU:          /* set MTU size                 */
   5245    case VKI_SIOCSIFHWADDR:       /* set hardware address         */
   5246    case VKI_SIOCSMIIREG:         /* set hardware entry registers */
   5247       break;
   5248       /* Routing table calls.  */
   5249    case VKI_SIOCADDRT:           /* add routing table entry      */
   5250    case VKI_SIOCDELRT:           /* delete routing table entry   */
   5251       break;
   5252 
   5253       /* RARP cache control calls. */
   5254    case VKI_SIOCDRARP:           /* delete RARP table entry      */
   5255    case VKI_SIOCSRARP:           /* set RARP table entry         */
   5256       /* ARP cache control calls. */
   5257    case VKI_SIOCSARP:            /* set ARP table entry          */
   5258    case VKI_SIOCDARP:            /* delete ARP table entry       */
   5259       break;
   5260 
   5261    case VKI_SIOCGPGRP:
   5262       POST_MEM_WRITE(ARG3, sizeof(int));
   5263       break;
   5264    case VKI_SIOCSPGRP:
   5265       break;
   5266 
   5267       /* linux/soundcard interface (OSS) */
   5268    case VKI_SNDCTL_SEQ_GETOUTCOUNT:
   5269    case VKI_SNDCTL_SEQ_GETINCOUNT:
   5270    case VKI_SNDCTL_SEQ_PERCMODE:
   5271    case VKI_SNDCTL_SEQ_TESTMIDI:
   5272    case VKI_SNDCTL_SEQ_RESETSAMPLES:
   5273    case VKI_SNDCTL_SEQ_NRSYNTHS:
   5274    case VKI_SNDCTL_SEQ_NRMIDIS:
   5275    case VKI_SNDCTL_SEQ_GETTIME:
   5276    case VKI_SNDCTL_DSP_GETBLKSIZE:
   5277    case VKI_SNDCTL_DSP_GETFMTS:
   5278    case VKI_SNDCTL_DSP_SETFMT:
   5279    case VKI_SNDCTL_DSP_GETTRIGGER:
   5280    case VKI_SNDCTL_DSP_GETODELAY:
   5281    case VKI_SNDCTL_DSP_GETSPDIF:
   5282    case VKI_SNDCTL_DSP_GETCAPS:
   5283    case VKI_SOUND_PCM_READ_RATE:
   5284    case VKI_SOUND_PCM_READ_CHANNELS:
   5285    case VKI_SOUND_PCM_READ_BITS:
   5286    case VKI_SOUND_PCM_READ_FILTER:
   5287       POST_MEM_WRITE(ARG3, sizeof(int));
   5288       break;
   5289    case VKI_SNDCTL_SEQ_CTRLRATE:
   5290    case VKI_SNDCTL_DSP_SPEED:
   5291    case VKI_SNDCTL_DSP_STEREO:
   5292    case VKI_SNDCTL_DSP_CHANNELS:
   5293    case VKI_SOUND_PCM_WRITE_FILTER:
   5294    case VKI_SNDCTL_DSP_SUBDIVIDE:
   5295    case VKI_SNDCTL_DSP_SETFRAGMENT:
   5296    case VKI_SNDCTL_DSP_GETCHANNELMASK:
   5297    case VKI_SNDCTL_DSP_BIND_CHANNEL:
   5298    case VKI_SNDCTL_TMR_TIMEBASE:
   5299    case VKI_SNDCTL_TMR_TEMPO:
   5300    case VKI_SNDCTL_TMR_SOURCE:
   5301    case VKI_SNDCTL_MIDI_PRETIME:
   5302    case VKI_SNDCTL_MIDI_MPUMODE:
   5303       break;
   5304    case VKI_SNDCTL_DSP_GETOSPACE:
   5305    case VKI_SNDCTL_DSP_GETISPACE:
   5306       POST_MEM_WRITE(ARG3, sizeof(vki_audio_buf_info));
   5307       break;
   5308    case VKI_SNDCTL_DSP_NONBLOCK:
   5309       break;
   5310    case VKI_SNDCTL_DSP_SETTRIGGER:
   5311       break;
   5312 
   5313    case VKI_SNDCTL_DSP_POST:
   5314    case VKI_SNDCTL_DSP_RESET:
   5315    case VKI_SNDCTL_DSP_SYNC:
   5316    case VKI_SNDCTL_DSP_SETSYNCRO:
   5317    case VKI_SNDCTL_DSP_SETDUPLEX:
   5318       break;
   5319 
   5320       /* linux/soundcard interface (ALSA) */
   5321    case VKI_SNDRV_PCM_IOCTL_HW_FREE:
   5322    case VKI_SNDRV_PCM_IOCTL_HWSYNC:
   5323    case VKI_SNDRV_PCM_IOCTL_PREPARE:
   5324    case VKI_SNDRV_PCM_IOCTL_RESET:
   5325    case VKI_SNDRV_PCM_IOCTL_START:
   5326    case VKI_SNDRV_PCM_IOCTL_DROP:
   5327    case VKI_SNDRV_PCM_IOCTL_DRAIN:
   5328    case VKI_SNDRV_PCM_IOCTL_RESUME:
   5329    case VKI_SNDRV_PCM_IOCTL_XRUN:
   5330    case VKI_SNDRV_PCM_IOCTL_UNLINK:
   5331    case VKI_SNDRV_TIMER_IOCTL_START:
   5332    case VKI_SNDRV_TIMER_IOCTL_STOP:
   5333    case VKI_SNDRV_TIMER_IOCTL_CONTINUE:
   5334    case VKI_SNDRV_TIMER_IOCTL_PAUSE:
   5335       break;
   5336 
   5337       /* Real Time Clock (/dev/rtc) ioctls */
   5338    case VKI_RTC_UIE_ON:
   5339    case VKI_RTC_UIE_OFF:
   5340    case VKI_RTC_AIE_ON:
   5341    case VKI_RTC_AIE_OFF:
   5342    case VKI_RTC_PIE_ON:
   5343    case VKI_RTC_PIE_OFF:
   5344    case VKI_RTC_IRQP_SET:
   5345       break;
   5346    case VKI_RTC_RD_TIME:
   5347    case VKI_RTC_ALM_READ:
   5348       POST_MEM_WRITE(ARG3, sizeof(struct vki_rtc_time));
   5349       break;
   5350    case VKI_RTC_ALM_SET:
   5351       break;
   5352    case VKI_RTC_IRQP_READ:
   5353       POST_MEM_WRITE(ARG3, sizeof(unsigned long));
   5354       break;
   5355 
   5356       /* Block devices */
   5357    case VKI_BLKROSET:
   5358       break;
   5359    case VKI_BLKROGET:
   5360       POST_MEM_WRITE(ARG3, sizeof(int));
   5361       break;
   5362    case VKI_BLKGETSIZE:
   5363       POST_MEM_WRITE(ARG3, sizeof(unsigned long));
   5364       break;
   5365    case VKI_BLKRASET:
   5366       break;
   5367    case VKI_BLKRAGET:
   5368       POST_MEM_WRITE(ARG3, sizeof(long));
   5369       break;
   5370    case VKI_BLKFRASET:
   5371       break;
   5372    case VKI_BLKFRAGET:
   5373       POST_MEM_WRITE(ARG3, sizeof(long));
   5374       break;
   5375    case VKI_BLKSECTGET:
   5376       POST_MEM_WRITE(ARG3, sizeof(unsigned short));
   5377       break;
   5378    case VKI_BLKSSZGET:
   5379       POST_MEM_WRITE(ARG3, sizeof(int));
   5380       break;
   5381    case VKI_BLKBSZGET:
   5382       POST_MEM_WRITE(ARG3, sizeof(int));
   5383       break;
   5384    case VKI_BLKBSZSET:
   5385       break;
   5386    case VKI_BLKGETSIZE64:
   5387       POST_MEM_WRITE(ARG3, sizeof(unsigned long long));
   5388       break;
   5389 
   5390       /* Hard disks */
   5391    case VKI_HDIO_GETGEO: /* 0x0301 */
   5392       POST_MEM_WRITE(ARG3, sizeof(struct vki_hd_geometry));
   5393       break;
   5394    case VKI_HDIO_GET_DMA: /* 0x030b */
   5395       POST_MEM_WRITE(ARG3, sizeof(long));
   5396       break;
   5397    case VKI_HDIO_GET_IDENTITY: /* 0x030d */
   5398       POST_MEM_WRITE(ARG3, VKI_SIZEOF_STRUCT_HD_DRIVEID );
   5399       break;
   5400 
   5401       /* CD ROM stuff (??)  */
   5402    case VKI_CDROMSUBCHNL:
   5403       POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_subchnl));
   5404       break;
   5405    case VKI_CDROMREADTOCHDR:
   5406       POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_tochdr));
   5407       break;
   5408    case VKI_CDROMREADTOCENTRY:
   5409       POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_tocentry));
   5410       break;
   5411    case VKI_CDROMMULTISESSION:
   5412       POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_multisession));
   5413       break;
   5414    case VKI_CDROMVOLREAD:
   5415       POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_volctrl));
   5416       break;
   5417    case VKI_CDROMREADRAW:
   5418       POST_MEM_WRITE(ARG3, VKI_CD_FRAMESIZE_RAW);
   5419       break;
   5420    case VKI_CDROMREADAUDIO:
   5421    {
   5422       struct vki_cdrom_read_audio *cra = (struct vki_cdrom_read_audio *) ARG3;
   5423       POST_MEM_WRITE( (Addr)(cra->buf), cra->nframes * VKI_CD_FRAMESIZE_RAW);
   5424       break;
   5425    }
   5426 
   5427    case VKI_CDROMPLAYMSF:
   5428       break;
   5429       /* The following two are probably bogus (should check args
   5430 	 for readability).  JRS 20021117 */
   5431    case VKI_CDROM_DRIVE_STATUS: /* 0x5326 */
   5432    case VKI_CDROM_CLEAR_OPTIONS: /* 0x5321 */
   5433       break;
   5434 
   5435    case VKI_FIGETBSZ:
   5436       POST_MEM_WRITE(ARG3, sizeof(unsigned long));
   5437       break;
   5438    case VKI_FIBMAP:
   5439       POST_MEM_WRITE(ARG3, sizeof(int));
   5440       break;
   5441 
   5442    case VKI_FBIOGET_VSCREENINFO: //0x4600
   5443       POST_MEM_WRITE(ARG3, sizeof(struct vki_fb_var_screeninfo));
   5444       break;
   5445    case VKI_FBIOGET_FSCREENINFO: //0x4602
   5446       POST_MEM_WRITE(ARG3, sizeof(struct vki_fb_fix_screeninfo));
   5447       break;
   5448 
   5449    case VKI_PPCLAIM:
   5450    case VKI_PPEXCL:
   5451    case VKI_PPYIELD:
   5452    case VKI_PPRELEASE:
   5453    case VKI_PPSETMODE:
   5454    case VKI_PPSETPHASE:
   5455    case VKI_PPSETFLAGS:
   5456    case VKI_PPWDATA:
   5457    case VKI_PPWCONTROL:
   5458    case VKI_PPFCONTROL:
   5459    case VKI_PPDATADIR:
   5460    case VKI_PPNEGOT:
   5461    case VKI_PPWCTLONIRQ:
   5462    case VKI_PPSETTIME:
   5463       break;
   5464    case VKI_PPGETMODE:
   5465       POST_MEM_WRITE( ARG3, sizeof(int) );
   5466       break;
   5467    case VKI_PPGETPHASE:
   5468       POST_MEM_WRITE( ARG3, sizeof(int) );
   5469       break;
   5470    case VKI_PPGETMODES:
   5471       POST_MEM_WRITE( ARG3, sizeof(unsigned int) );
   5472       break;
   5473    case VKI_PPGETFLAGS:
   5474       POST_MEM_WRITE( ARG3, sizeof(int) );
   5475       break;
   5476    case VKI_PPRSTATUS:
   5477       POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
   5478       break;
   5479    case VKI_PPRDATA:
   5480       POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
   5481       break;
   5482    case VKI_PPRCONTROL:
   5483       POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
   5484       break;
   5485    case VKI_PPCLRIRQ:
   5486       POST_MEM_WRITE( ARG3, sizeof(int) );
   5487       break;
   5488    case VKI_PPGETTIME:
   5489       POST_MEM_WRITE( ARG3, sizeof(struct vki_timeval) );
   5490       break;
   5491 
   5492    case VKI_GIO_FONT:
   5493       POST_MEM_WRITE( ARG3, 32 * 256 );
   5494       break;
   5495    case VKI_PIO_FONT:
   5496       break;
   5497 
   5498    case VKI_GIO_FONTX:
   5499       POST_MEM_WRITE( (Addr)((struct vki_consolefontdesc *)ARG3)->chardata,
   5500                       32 * ((struct vki_consolefontdesc *)ARG3)->charcount );
   5501       break;
   5502    case VKI_PIO_FONTX:
   5503       break;
   5504 
   5505    case VKI_PIO_FONTRESET:
   5506       break;
   5507 
   5508    case VKI_GIO_CMAP:
   5509       POST_MEM_WRITE( ARG3, 16 * 3 );
   5510       break;
   5511    case VKI_PIO_CMAP:
   5512       break;
   5513 
   5514    case VKI_KIOCSOUND:
   5515    case VKI_KDMKTONE:
   5516       break;
   5517 
   5518    case VKI_KDGETLED:
   5519       POST_MEM_WRITE( ARG3, sizeof(char) );
   5520       break;
   5521    case VKI_KDSETLED:
   5522       break;
   5523 
   5524    case VKI_KDGKBTYPE:
   5525       POST_MEM_WRITE( ARG3, sizeof(char) );
   5526       break;
   5527 
   5528    case VKI_KDADDIO:
   5529    case VKI_KDDELIO:
   5530    case VKI_KDENABIO:
   5531    case VKI_KDDISABIO:
   5532       break;
   5533 
   5534    case VKI_KDSETMODE:
   5535       break;
   5536    case VKI_KDGETMODE:
   5537       POST_MEM_WRITE( ARG3, sizeof(int) );
   5538       break;
   5539 
   5540    case VKI_KDMAPDISP:
   5541    case VKI_KDUNMAPDISP:
   5542       break;
   5543 
   5544    case VKI_GIO_SCRNMAP:
   5545       POST_MEM_WRITE( ARG3, VKI_E_TABSZ );
   5546       break;
   5547    case VKI_PIO_SCRNMAP:
   5548       break;
   5549    case VKI_GIO_UNISCRNMAP:
   5550       POST_MEM_WRITE( ARG3, VKI_E_TABSZ * sizeof(unsigned short) );
   5551       break;
   5552    case VKI_PIO_UNISCRNMAP:
   5553       break;
   5554 
   5555    case VKI_GIO_UNIMAP:
   5556       if ( ARG3 ) {
   5557          struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
   5558          POST_MEM_WRITE( (Addr)&desc->entry_ct, sizeof(desc->entry_ct));
   5559          POST_MEM_WRITE( (Addr)desc->entries,
   5560       	                 desc->entry_ct * sizeof(struct vki_unipair) );
   5561       }
   5562       break;
   5563    case VKI_PIO_UNIMAP:
   5564       break;
   5565    case VKI_PIO_UNIMAPCLR:
   5566       break;
   5567 
   5568    case VKI_KDGKBMODE:
   5569       POST_MEM_WRITE( ARG3, sizeof(int) );
   5570       break;
   5571    case VKI_KDSKBMODE:
   5572       break;
   5573 
   5574    case VKI_KDGKBMETA:
   5575       POST_MEM_WRITE( ARG3, sizeof(int) );
   5576       break;
   5577    case VKI_KDSKBMETA:
   5578       break;
   5579 
   5580    case VKI_KDGKBLED:
   5581       POST_MEM_WRITE( ARG3, sizeof(char) );
   5582       break;
   5583    case VKI_KDSKBLED:
   5584       break;
   5585 
   5586    case VKI_KDGKBENT:
   5587       POST_MEM_WRITE( (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
   5588                       sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
   5589       break;
   5590    case VKI_KDSKBENT:
   5591       break;
   5592 
   5593    case VKI_KDGKBSENT:
   5594       POST_MEM_WRITE( (Addr)((struct vki_kbsentry *)ARG3)->kb_string,
   5595                       sizeof(((struct vki_kbsentry *)ARG3)->kb_string) );
   5596       break;
   5597    case VKI_KDSKBSENT:
   5598       break;
   5599 
   5600    case VKI_KDGKBDIACR:
   5601       POST_MEM_WRITE( ARG3, sizeof(struct vki_kbdiacrs) );
   5602       break;
   5603    case VKI_KDSKBDIACR:
   5604       break;
   5605 
   5606    case VKI_KDGETKEYCODE:
   5607       POST_MEM_WRITE( (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
   5608                       sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
   5609       break;
   5610    case VKI_KDSETKEYCODE:
   5611       break;
   5612 
   5613    case VKI_KDSIGACCEPT:
   5614       break;
   5615 
   5616    case VKI_KDKBDREP:
   5617       break;
   5618 
   5619    case VKI_KDFONTOP:
   5620       if ( ARG3 ) {
   5621          struct vki_console_font_op *op = (struct vki_console_font_op *) ARG3;
   5622          switch ( op->op ) {
   5623             case VKI_KD_FONT_OP_SET:
   5624                break;
   5625             case VKI_KD_FONT_OP_GET:
   5626                if ( op->data )
   5627                   POST_MEM_WRITE( (Addr) op->data,
   5628                                   (op->width + 7) / 8 * 32 * op->charcount );
   5629                break;
   5630             case VKI_KD_FONT_OP_SET_DEFAULT:
   5631                break;
   5632             case VKI_KD_FONT_OP_COPY:
   5633                break;
   5634          }
   5635          POST_MEM_WRITE( (Addr) op, sizeof(*op));
   5636       }
   5637       break;
   5638 
   5639    case VKI_VT_OPENQRY:
   5640       POST_MEM_WRITE( ARG3, sizeof(int) );
   5641       break;
   5642    case VKI_VT_GETMODE:
   5643       POST_MEM_WRITE( ARG3, sizeof(struct vki_vt_mode) );
   5644       break;
   5645    case VKI_VT_SETMODE:
   5646       break;
   5647    case VKI_VT_GETSTATE:
   5648       POST_MEM_WRITE( (Addr) &(((struct vki_vt_stat*) ARG3)->v_active),
   5649                       sizeof(((struct vki_vt_stat*) ARG3)->v_active) );
   5650       POST_MEM_WRITE( (Addr) &(((struct vki_vt_stat*) ARG3)->v_state),
   5651                       sizeof(((struct vki_vt_stat*) ARG3)->v_state) );
   5652       break;
   5653    case VKI_VT_RELDISP:
   5654    case VKI_VT_ACTIVATE:
   5655    case VKI_VT_WAITACTIVE:
   5656    case VKI_VT_DISALLOCATE:
   5657       break;
   5658    case VKI_VT_RESIZE:
   5659       break;
   5660    case VKI_VT_RESIZEX:
   5661       break;
   5662    case VKI_VT_LOCKSWITCH:
   5663    case VKI_VT_UNLOCKSWITCH:
   5664       break;
   5665 
   5666    case VKI_USBDEVFS_CONTROL:
   5667       if ( ARG3 ) {
   5668          struct vki_usbdevfs_ctrltransfer *vkuc = (struct vki_usbdevfs_ctrltransfer *)ARG3;
   5669          if (vkuc->bRequestType & 0x80)
   5670             POST_MEM_WRITE((Addr)vkuc->data, RES);
   5671          break;
   5672       }
   5673    case VKI_USBDEVFS_BULK:
   5674       if ( ARG3 ) {
   5675          struct vki_usbdevfs_bulktransfer *vkub = (struct vki_usbdevfs_bulktransfer *)ARG3;
   5676          if (vkub->ep & 0x80)
   5677             POST_MEM_WRITE((Addr)vkub->data, RES);
   5678          break;
   5679       }
   5680    case VKI_USBDEVFS_GETDRIVER:
   5681       if ( ARG3 ) {
   5682          struct vki_usbdevfs_getdriver *vkugd = (struct vki_usbdevfs_getdriver *)ARG3;
   5683          POST_MEM_WRITE((Addr)&vkugd->driver, sizeof(vkugd->driver));
   5684          break;
   5685       }
   5686    case VKI_USBDEVFS_REAPURB:
   5687    case VKI_USBDEVFS_REAPURBNDELAY:
   5688       if ( ARG3 ) {
   5689          struct vki_usbdevfs_urb **vkuu = (struct vki_usbdevfs_urb**)ARG3;
   5690          POST_MEM_WRITE((Addr)vkuu, sizeof(*vkuu));
   5691          if (!*vkuu)
   5692             break;
   5693          POST_MEM_WRITE((Addr) &((*vkuu)->status),sizeof((*vkuu)->status));
   5694          if ((*vkuu)->type == VKI_USBDEVFS_URB_TYPE_CONTROL) {
   5695             struct vki_usbdevfs_setuppacket *vkusp = (struct vki_usbdevfs_setuppacket *)(*vkuu)->buffer;
   5696             if (vkusp->bRequestType & 0x80)
   5697                POST_MEM_WRITE((Addr)(vkusp+1), (*vkuu)->buffer_length - sizeof(*vkusp));
   5698             POST_MEM_WRITE((Addr)&(*vkuu)->actual_length, sizeof((*vkuu)->actual_length));
   5699          } else if ((*vkuu)->type == VKI_USBDEVFS_URB_TYPE_ISO) {
   5700             char *bp = (*vkuu)->buffer;
   5701             int i;
   5702             for(i=0; i<(*vkuu)->number_of_packets; i++) {
   5703                POST_MEM_WRITE((Addr)&(*vkuu)->iso_frame_desc[i].actual_length, sizeof((*vkuu)->iso_frame_desc[i].actual_length));
   5704                POST_MEM_WRITE((Addr)&(*vkuu)->iso_frame_desc[i].status, sizeof((*vkuu)->iso_frame_desc[i].status));
   5705                if ((*vkuu)->endpoint & 0x80)
   5706                   POST_MEM_WRITE((Addr)bp, (*vkuu)->iso_frame_desc[i].actual_length);
   5707                bp += (*vkuu)->iso_frame_desc[i].length; // FIXME: or actual_length??
   5708             }
   5709             POST_MEM_WRITE((Addr)&(*vkuu)->error_count, sizeof((*vkuu)->error_count));
   5710          } else {
   5711             if ((*vkuu)->endpoint & 0x80)
   5712                POST_MEM_WRITE((Addr)(*vkuu)->buffer, (*vkuu)->actual_length);
   5713             POST_MEM_WRITE((Addr)&(*vkuu)->actual_length, sizeof((*vkuu)->actual_length));
   5714          }
   5715          break;
   5716       }
   5717    case VKI_USBDEVFS_CONNECTINFO:
   5718       POST_MEM_WRITE(ARG3, sizeof(struct vki_usbdevfs_connectinfo));
   5719       break;
   5720    case VKI_USBDEVFS_IOCTL:
   5721       if ( ARG3 ) {
   5722          struct vki_usbdevfs_ioctl *vkui = (struct vki_usbdevfs_ioctl *)ARG3;
   5723          UInt dir2, size2;
   5724          dir2  = _VKI_IOC_DIR(vkui->ioctl_code);
   5725          size2 = _VKI_IOC_SIZE(vkui->ioctl_code);
   5726          if (size2 > 0) {
   5727             if (dir2 & _VKI_IOC_READ)
   5728                POST_MEM_WRITE((Addr)vkui->data, size2);
   5729          }
   5730       }
   5731       break;
   5732 
   5733       /* I2C (/dev/i2c-*) ioctls */
   5734    case VKI_I2C_SLAVE:
   5735    case VKI_I2C_SLAVE_FORCE:
   5736    case VKI_I2C_TENBIT:
   5737    case VKI_I2C_PEC:
   5738       break;
   5739    case VKI_I2C_FUNCS:
   5740       POST_MEM_WRITE( ARG3, sizeof(unsigned long) );
   5741       break;
   5742 
   5743       /* Wireless extensions ioctls */
   5744    case VKI_SIOCSIWCOMMIT:
   5745    case VKI_SIOCSIWNWID:
   5746    case VKI_SIOCSIWFREQ:
   5747    case VKI_SIOCSIWMODE:
   5748    case VKI_SIOCSIWSENS:
   5749    case VKI_SIOCSIWRANGE:
   5750    case VKI_SIOCSIWPRIV:
   5751    case VKI_SIOCSIWSTATS:
   5752    case VKI_SIOCSIWSPY:
   5753    case VKI_SIOCSIWTHRSPY:
   5754    case VKI_SIOCSIWAP:
   5755    case VKI_SIOCSIWSCAN:
   5756    case VKI_SIOCSIWESSID:
   5757    case VKI_SIOCSIWRATE:
   5758    case VKI_SIOCSIWNICKN:
   5759    case VKI_SIOCSIWRTS:
   5760    case VKI_SIOCSIWFRAG:
   5761    case VKI_SIOCSIWTXPOW:
   5762    case VKI_SIOCSIWRETRY:
   5763    case VKI_SIOCSIWENCODE:
   5764    case VKI_SIOCSIWPOWER:
   5765    case VKI_SIOCSIWGENIE:
   5766    case VKI_SIOCSIWMLME:
   5767    case VKI_SIOCSIWAUTH:
   5768    case VKI_SIOCSIWENCODEEXT:
   5769    case VKI_SIOCSIWPMKSA:
   5770       break;
   5771    case VKI_SIOCGIWNAME:
   5772       if (ARG3) {
   5773          POST_MEM_WRITE((Addr)((struct vki_iwreq *)ARG3)->u.name,
   5774                         sizeof(((struct vki_iwreq *)ARG3)->u.name));
   5775       }
   5776       break;
   5777    case VKI_SIOCGIWNWID:
   5778    case VKI_SIOCGIWSENS:
   5779    case VKI_SIOCGIWRATE:
   5780    case VKI_SIOCGIWRTS:
   5781    case VKI_SIOCGIWFRAG:
   5782    case VKI_SIOCGIWTXPOW:
   5783    case VKI_SIOCGIWRETRY:
   5784    case VKI_SIOCGIWPOWER:
   5785    case VKI_SIOCGIWAUTH:
   5786       if (ARG3) {
   5787          POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.param,
   5788                         sizeof(struct vki_iw_param));
   5789       }
   5790       break;
   5791    case VKI_SIOCGIWFREQ:
   5792       if (ARG3) {
   5793          POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.freq,
   5794                         sizeof(struct vki_iw_freq));
   5795       }
   5796       break;
   5797    case VKI_SIOCGIWMODE:
   5798       if (ARG3) {
   5799          POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.mode,
   5800                        sizeof(__vki_u32));
   5801       }
   5802       break;
   5803    case VKI_SIOCGIWRANGE:
   5804    case VKI_SIOCGIWPRIV:
   5805    case VKI_SIOCGIWSTATS:
   5806    case VKI_SIOCGIWSPY:
   5807    case VKI_SIOCGIWTHRSPY:
   5808    case VKI_SIOCGIWAPLIST:
   5809    case VKI_SIOCGIWSCAN:
   5810    case VKI_SIOCGIWESSID:
   5811    case VKI_SIOCGIWNICKN:
   5812    case VKI_SIOCGIWENCODE:
   5813    case VKI_SIOCGIWGENIE:
   5814    case VKI_SIOCGIWENCODEEXT:
   5815       if (ARG3) {
   5816          struct vki_iw_point* point;
   5817          point = &((struct vki_iwreq *)ARG3)->u.data;
   5818          POST_MEM_WRITE((Addr)point->pointer, point->length);
   5819       }
   5820       break;
   5821    case VKI_SIOCGIWAP:
   5822       if (ARG3) {
   5823          POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.ap_addr,
   5824                         sizeof(struct vki_sockaddr));
   5825       }
   5826       break;
   5827 
   5828 #ifdef ANDROID
   5829       /* ashmem */
   5830    case VKI_ASHMEM_GET_SIZE:
   5831    case VKI_ASHMEM_SET_SIZE:
   5832    case VKI_ASHMEM_GET_PROT_MASK:
   5833    case VKI_ASHMEM_SET_PROT_MASK:
   5834    case VKI_ASHMEM_GET_PIN_STATUS:
   5835    case VKI_ASHMEM_PURGE_ALL_CACHES:
   5836    case VKI_ASHMEM_SET_NAME:
   5837    case VKI_ASHMEM_PIN:
   5838    case VKI_ASHMEM_UNPIN:
   5839        break;
   5840    case VKI_ASHMEM_GET_NAME:
   5841        POST_MEM_WRITE( ARG3, VKI_ASHMEM_NAME_LEN );
   5842        break;
   5843 
   5844      /* binder */
   5845    case VKI_BINDER_WRITE_READ:
   5846        if (ARG3) {
   5847            struct vki_binder_write_read* bwr = ARG3;
   5848            POST_FIELD_WRITE(bwr->write_consumed);
   5849            POST_FIELD_WRITE(bwr->read_consumed);
   5850 
   5851            if (bwr->read_size)
   5852                POST_MEM_WRITE((Addr)bwr->read_buffer, bwr->read_consumed);
   5853        }
   5854        break;
   5855 
   5856    case VKI_BINDER_SET_IDLE_TIMEOUT:
   5857    case VKI_BINDER_SET_MAX_THREADS:
   5858    case VKI_BINDER_SET_IDLE_PRIORITY:
   5859    case VKI_BINDER_SET_CONTEXT_MGR:
   5860    case VKI_BINDER_THREAD_EXIT:
   5861        break;
   5862    case VKI_BINDER_VERSION:
   5863        if (ARG3) {
   5864            struct vki_binder_version* bv = (struct vki_binder_version*)ARG3;
   5865            POST_FIELD_WRITE(bv->protocol_version);
   5866        }
   5867        break;
   5868 #endif
   5869 
   5870    default:
   5871       /* EVIOC* are variable length and return size written on success */
   5872       switch (ARG2 & ~(_VKI_IOC_SIZEMASK << _VKI_IOC_SIZESHIFT)) {
   5873       case VKI_EVIOCGNAME(0):
   5874       case VKI_EVIOCGPHYS(0):
   5875       case VKI_EVIOCGUNIQ(0):
   5876       case VKI_EVIOCGKEY(0):
   5877       case VKI_EVIOCGLED(0):
   5878       case VKI_EVIOCGSND(0):
   5879       case VKI_EVIOCGSW(0):
   5880       case VKI_EVIOCGBIT(VKI_EV_SYN,0):
   5881       case VKI_EVIOCGBIT(VKI_EV_KEY,0):
   5882       case VKI_EVIOCGBIT(VKI_EV_REL,0):
   5883       case VKI_EVIOCGBIT(VKI_EV_ABS,0):
   5884       case VKI_EVIOCGBIT(VKI_EV_MSC,0):
   5885       case VKI_EVIOCGBIT(VKI_EV_SW,0):
   5886       case VKI_EVIOCGBIT(VKI_EV_LED,0):
   5887       case VKI_EVIOCGBIT(VKI_EV_SND,0):
   5888       case VKI_EVIOCGBIT(VKI_EV_REP,0):
   5889       case VKI_EVIOCGBIT(VKI_EV_FF,0):
   5890       case VKI_EVIOCGBIT(VKI_EV_PWR,0):
   5891       case VKI_EVIOCGBIT(VKI_EV_FF_STATUS,0):
   5892          if (RES > 0)
   5893             POST_MEM_WRITE(ARG3, RES);
   5894          break;
   5895       default:
   5896          ML_(POST_unknown_ioctl)(tid, RES, ARG2, ARG3);
   5897          break;
   5898       }
   5899       break;
   5900    }
   5901 }
   5902 
   5903 /* ---------------------------------------------------------------------
   5904    socketcall wrapper helpers
   5905    ------------------------------------------------------------------ */
   5906 
   5907 void
   5908 ML_(linux_PRE_sys_getsockopt) ( ThreadId tid,
   5909                                 UWord arg0, UWord arg1, UWord arg2,
   5910                                 UWord arg3, UWord arg4 )
   5911 {
   5912    /* int getsockopt(int s, int level, int optname,
   5913                      void *optval, socklen_t *optlen); */
   5914    Addr optval_p = arg3;
   5915    Addr optlen_p = arg4;
   5916    /* vg_assert(sizeof(socklen_t) == sizeof(UInt)); */
   5917    if (optval_p != (Addr)NULL) {
   5918       ML_(buf_and_len_pre_check) ( tid, optval_p, optlen_p,
   5919                                    "socketcall.getsockopt(optval)",
   5920                                    "socketcall.getsockopt(optlen)" );
   5921       if (arg1 == VKI_SOL_SCTP &&
   5922           (arg2 == VKI_SCTP_GET_PEER_ADDRS ||
   5923            arg2 == VKI_SCTP_GET_LOCAL_ADDRS))
   5924       {
   5925          struct vki_sctp_getaddrs *ga = (struct vki_sctp_getaddrs*)arg3;
   5926          int address_bytes = sizeof(struct vki_sockaddr_in6) * ga->addr_num;
   5927          PRE_MEM_WRITE( "socketcall.getsockopt(optval.addrs)",
   5928                         (Addr)ga->addrs, address_bytes );
   5929       }
   5930    }
   5931 }
   5932 
   5933 void
   5934 ML_(linux_POST_sys_getsockopt) ( ThreadId tid,
   5935                                  SysRes res,
   5936                                  UWord arg0, UWord arg1, UWord arg2,
   5937                                  UWord arg3, UWord arg4 )
   5938 {
   5939    Addr optval_p = arg3;
   5940    Addr optlen_p = arg4;
   5941    vg_assert(!sr_isError(res)); /* guaranteed by caller */
   5942    if (optval_p != (Addr)NULL) {
   5943       ML_(buf_and_len_post_check) ( tid, res, optval_p, optlen_p,
   5944                                     "socketcall.getsockopt(optlen_out)" );
   5945       if (arg1 == VKI_SOL_SCTP &&
   5946           (arg2 == VKI_SCTP_GET_PEER_ADDRS ||
   5947            arg2 == VKI_SCTP_GET_LOCAL_ADDRS))
   5948       {
   5949          struct vki_sctp_getaddrs *ga = (struct vki_sctp_getaddrs*)arg3;
   5950          struct vki_sockaddr *a = ga->addrs;
   5951          int i;
   5952          for (i = 0; i < ga->addr_num; i++) {
   5953             int sl = 0;
   5954             if (a->sa_family == VKI_AF_INET)
   5955                sl = sizeof(struct vki_sockaddr_in);
   5956             else if (a->sa_family == VKI_AF_INET6)
   5957                sl = sizeof(struct vki_sockaddr_in6);
   5958             else {
   5959                VG_(message)(Vg_UserMsg, "Warning: getsockopt: unhandled "
   5960                                         "address type %d\n", a->sa_family);
   5961             }
   5962             a = (struct vki_sockaddr*)((char*)a + sl);
   5963          }
   5964          POST_MEM_WRITE( (Addr)ga->addrs, (char*)a - (char*)ga->addrs );
   5965       }
   5966    }
   5967 }
   5968 
   5969 #undef PRE
   5970 #undef POST
   5971 
   5972 #endif // defined(VGO_linux)
   5973 
   5974 /*--------------------------------------------------------------------*/
   5975 /*--- end                                                          ---*/
   5976 /*--------------------------------------------------------------------*/
   5977