drd: Add a consistency check
[valgrind.git] / coregrind / m_syswrap / syswrap-linux.c
blobd63010006d4269a3616b6a23bc1b9a029ec51053
2 /*--------------------------------------------------------------------*/
3 /*--- Linux-specific syscalls, etc. syswrap-linux.c ---*/
4 /*--------------------------------------------------------------------*/
6 /*
7 This file is part of Valgrind, a dynamic binary instrumentation
8 framework.
10 Copyright (C) 2000-2013 Nicholas Nethercote
11 njn@valgrind.org
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.
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.
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.
28 The GNU General Public License is contained in the file COPYING.
31 #if defined(VGO_linux)
33 #include "pub_core_basics.h"
34 #include "pub_core_vki.h"
35 #include "pub_core_vkiscnums.h"
36 #include "pub_core_libcsetjmp.h" // to keep _threadstate.h happy
37 #include "pub_core_threadstate.h"
38 #include "pub_core_aspacemgr.h"
39 #include "pub_core_debuginfo.h" // VG_(di_notify_*)
40 #include "pub_core_transtab.h" // VG_(discard_translations)
41 #include "pub_core_xarray.h"
42 #include "pub_core_clientstate.h"
43 #include "pub_core_debuglog.h"
44 #include "pub_core_libcbase.h"
45 #include "pub_core_libcassert.h"
46 #include "pub_core_libcfile.h"
47 #include "pub_core_libcprint.h"
48 #include "pub_core_libcproc.h"
49 #include "pub_core_libcsignal.h"
50 #include "pub_core_machine.h" // VG_(get_SP)
51 #include "pub_core_mallocfree.h"
52 #include "pub_core_tooliface.h"
53 #include "pub_core_options.h"
54 #include "pub_core_scheduler.h"
55 #include "pub_core_signals.h"
56 #include "pub_core_syscall.h"
57 #include "pub_core_syswrap.h"
58 #include "pub_core_inner.h"
59 #if defined(ENABLE_INNER_CLIENT_REQUEST)
60 #include "pub_core_clreq.h"
61 #endif
63 #include "priv_types_n_macros.h"
64 #include "priv_syswrap-generic.h"
65 #include "priv_syswrap-linux.h"
66 #include "priv_syswrap-xen.h"
68 // Run a thread from beginning to end and return the thread's
69 // scheduler-return-code.
70 static VgSchedReturnCode thread_wrapper(Word /*ThreadId*/ tidW)
72 VgSchedReturnCode ret;
73 ThreadId tid = (ThreadId)tidW;
74 ThreadState* tst = VG_(get_ThreadState)(tid);
76 VG_(debugLog)(1, "syswrap-linux",
77 "thread_wrapper(tid=%lld): entry\n",
78 (ULong)tidW);
80 vg_assert(tst->status == VgTs_Init);
82 /* make sure we get the CPU lock before doing anything significant */
83 VG_(acquire_BigLock)(tid, "thread_wrapper(starting new thread)");
85 if (0)
86 VG_(printf)("thread tid %d started: stack = %p\n",
87 tid, &tid);
89 /* Make sure error reporting is enabled in the new thread. */
90 tst->err_disablement_level = 0;
92 VG_TRACK(pre_thread_first_insn, tid);
94 tst->os_state.lwpid = VG_(gettid)();
95 /* Set the threadgroup for real. This overwrites the provisional
96 value set in do_clone() syswrap-*-linux.c. See comments in
97 do_clone for background, also #226116. */
98 tst->os_state.threadgroup = VG_(getpid)();
100 /* Thread created with all signals blocked; scheduler will set the
101 appropriate mask */
103 ret = VG_(scheduler)(tid);
105 vg_assert(VG_(is_exiting)(tid));
107 vg_assert(tst->status == VgTs_Runnable);
108 vg_assert(VG_(is_running_thread)(tid));
110 VG_(debugLog)(1, "syswrap-linux",
111 "thread_wrapper(tid=%lld): exit, schedreturncode %s\n",
112 (ULong)tidW, VG_(name_of_VgSchedReturnCode)(ret));
114 /* Return to caller, still holding the lock. */
115 return ret;
119 /* ---------------------------------------------------------------------
120 clone-related stuff
121 ------------------------------------------------------------------ */
123 /* Run a thread all the way to the end, then do appropriate exit actions
124 (this is the last-one-out-turn-off-the-lights bit). */
125 static void run_a_thread_NORETURN ( Word tidW )
127 ThreadId tid = (ThreadId)tidW;
128 VgSchedReturnCode src;
129 Int c;
130 ThreadState* tst;
131 #ifdef ENABLE_INNER_CLIENT_REQUEST
132 Int registered_vgstack_id;
133 #endif
135 VG_(debugLog)(1, "syswrap-linux",
136 "run_a_thread_NORETURN(tid=%lld): pre-thread_wrapper\n",
137 (ULong)tidW);
139 tst = VG_(get_ThreadState)(tid);
140 vg_assert(tst);
142 /* An thread has two stacks:
143 * the simulated stack (used by the synthetic cpu. Guest process
144 is using this stack).
145 * the valgrind stack (used by the real cpu. Valgrind code is running
146 on this stack).
147 When Valgrind runs as an inner, it must signals that its (real) stack
148 is the stack to use by the outer to e.g. do stacktraces.
150 INNER_REQUEST
151 (registered_vgstack_id
152 = VALGRIND_STACK_REGISTER (tst->os_state.valgrind_stack_base,
153 tst->os_state.valgrind_stack_init_SP));
155 /* Run the thread all the way through. */
156 src = thread_wrapper(tid);
158 VG_(debugLog)(1, "syswrap-linux",
159 "run_a_thread_NORETURN(tid=%lld): post-thread_wrapper\n",
160 (ULong)tidW);
162 c = VG_(count_living_threads)();
163 vg_assert(c >= 1); /* stay sane */
165 // Tell the tool this thread is exiting
166 VG_TRACK( pre_thread_ll_exit, tid );
168 /* If the thread is exiting with errors disabled, complain loudly;
169 doing so is bad (does the user know this has happened?) Also,
170 in all cases, be paranoid and clear the flag anyway so that the
171 thread slot is safe in this respect if later reallocated. This
172 should be unnecessary since the flag should be cleared when the
173 slot is reallocated, in thread_wrapper(). */
174 if (tst->err_disablement_level > 0) {
175 VG_(umsg)(
176 "WARNING: exiting thread has error reporting disabled.\n"
177 "WARNING: possibly as a result of some mistake in the use\n"
178 "WARNING: of the VALGRIND_DISABLE_ERROR_REPORTING macros.\n"
180 VG_(debugLog)(
181 1, "syswrap-linux",
182 "run_a_thread_NORETURN(tid=%lld): "
183 "WARNING: exiting thread has err_disablement_level = %u\n",
184 (ULong)tidW, tst->err_disablement_level
187 tst->err_disablement_level = 0;
189 if (c == 1) {
191 VG_(debugLog)(1, "syswrap-linux",
192 "run_a_thread_NORETURN(tid=%lld): "
193 "last one standing\n",
194 (ULong)tidW);
196 /* We are the last one standing. Keep hold of the lock and
197 carry on to show final tool results, then exit the entire system.
198 Use the continuation pointer set at startup in m_main. */
199 ( * VG_(address_of_m_main_shutdown_actions_NORETURN) ) (tid, src);
200 } else {
202 VG_(debugLog)(1, "syswrap-linux",
203 "run_a_thread_NORETURN(tid=%lld): "
204 "not last one standing\n",
205 (ULong)tidW);
207 /* OK, thread is dead, but others still exist. Just exit. */
209 /* This releases the run lock */
210 VG_(exit_thread)(tid);
211 vg_assert(tst->status == VgTs_Zombie);
212 vg_assert(sizeof(tst->status) == 4);
213 vg_assert(sizeof(tst->os_state.exitcode) == sizeof(Word));
215 INNER_REQUEST (VALGRIND_STACK_DEREGISTER (registered_vgstack_id));
217 /* We have to use this sequence to terminate the thread to
218 prevent a subtle race. If VG_(exit_thread)() had left the
219 ThreadState as Empty, then it could have been reallocated,
220 reusing the stack while we're doing these last cleanups.
221 Instead, VG_(exit_thread) leaves it as Zombie to prevent
222 reallocation. We need to make sure we don't touch the stack
223 between marking it Empty and exiting. Hence the
224 assembler. */
225 #if defined(VGP_x86_linux)
226 asm volatile (
227 "pushl %%ebx\n"
228 "movl %1, %0\n" /* set tst->status = VgTs_Empty */
229 "movl %2, %%eax\n" /* set %eax = __NR_exit */
230 "movl %3, %%ebx\n" /* set %ebx = tst->os_state.exitcode */
231 "int $0x80\n" /* exit(tst->os_state.exitcode) */
232 "popl %%ebx\n"
233 : "=m" (tst->status)
234 : "n" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
235 : "eax"
237 #elif defined(VGP_amd64_linux)
238 asm volatile (
239 "movl %1, %0\n" /* set tst->status = VgTs_Empty */
240 "movq %2, %%rax\n" /* set %rax = __NR_exit */
241 "movq %3, %%rdi\n" /* set %rdi = tst->os_state.exitcode */
242 "syscall\n" /* exit(tst->os_state.exitcode) */
243 : "=m" (tst->status)
244 : "n" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
245 : "rax", "rdi"
247 #elif defined(VGP_ppc32_linux) || defined(VGP_ppc64be_linux) \
248 || defined(VGP_ppc64le_linux)
249 { UInt vgts_empty = (UInt)VgTs_Empty;
250 asm volatile (
251 "stw %1,%0\n\t" /* set tst->status = VgTs_Empty */
252 "li 0,%2\n\t" /* set r0 = __NR_exit */
253 "lwz 3,%3\n\t" /* set r3 = tst->os_state.exitcode */
254 "sc\n\t" /* exit(tst->os_state.exitcode) */
255 : "=m" (tst->status)
256 : "r" (vgts_empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
257 : "r0", "r3"
260 #elif defined(VGP_arm_linux)
261 asm volatile (
262 "str %1, %0\n" /* set tst->status = VgTs_Empty */
263 "mov r7, %2\n" /* set %r7 = __NR_exit */
264 "ldr r0, %3\n" /* set %r0 = tst->os_state.exitcode */
265 "svc 0x00000000\n" /* exit(tst->os_state.exitcode) */
266 : "=m" (tst->status)
267 : "r" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
268 : "r0", "r7"
270 #elif defined(VGP_arm64_linux)
271 asm volatile (
272 "str %w1, %0\n" /* set tst->status = VgTs_Empty (32-bit store) */
273 "mov x8, %2\n" /* set %r7 = __NR_exit */
274 "ldr x0, %3\n" /* set %r0 = tst->os_state.exitcode */
275 "svc 0x00000000\n" /* exit(tst->os_state.exitcode) */
276 : "=m" (tst->status)
277 : "r" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
278 : "r0", "r7"
280 #elif defined(VGP_s390x_linux)
281 asm volatile (
282 "st %1, %0\n" /* set tst->status = VgTs_Empty */
283 "lg 2, %3\n" /* set r2 = tst->os_state.exitcode */
284 "svc %2\n" /* exit(tst->os_state.exitcode) */
285 : "=m" (tst->status)
286 : "d" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
287 : "2"
289 #elif defined(VGP_mips32_linux) || defined(VGP_mips64_linux)
290 asm volatile (
291 "sw %1, %0\n\t" /* set tst->status = VgTs_Empty */
292 "li $2, %2\n\t" /* set v0 = __NR_exit */
293 "lw $4, %3\n\t" /* set a0 = tst->os_state.exitcode */
294 "syscall\n\t" /* exit(tst->os_state.exitcode) */
295 "nop"
296 : "=m" (tst->status)
297 : "r" (VgTs_Empty), "n" (__NR_exit), "m" (tst->os_state.exitcode)
298 : "cc", "memory" , "v0", "a0"
300 #else
301 # error Unknown platform
302 #endif
304 VG_(core_panic)("Thread exit failed?\n");
307 /*NOTREACHED*/
308 vg_assert(0);
311 Word ML_(start_thread_NORETURN) ( void* arg )
313 ThreadState* tst = (ThreadState*)arg;
314 ThreadId tid = tst->tid;
316 run_a_thread_NORETURN ( (Word)tid );
317 /*NOTREACHED*/
318 vg_assert(0);
321 /* Allocate a stack for this thread, if it doesn't already have one.
322 They're allocated lazily, and never freed. Returns the initial stack
323 pointer value to use, or 0 if allocation failed. */
324 Addr ML_(allocstack)(ThreadId tid)
326 ThreadState* tst = VG_(get_ThreadState)(tid);
327 VgStack* stack;
328 Addr initial_SP;
330 /* Either the stack_base and stack_init_SP are both zero (in which
331 case a stack hasn't been allocated) or they are both non-zero,
332 in which case it has. */
334 if (tst->os_state.valgrind_stack_base == 0)
335 vg_assert(tst->os_state.valgrind_stack_init_SP == 0);
337 if (tst->os_state.valgrind_stack_base != 0)
338 vg_assert(tst->os_state.valgrind_stack_init_SP != 0);
340 /* If no stack is present, allocate one. */
342 if (tst->os_state.valgrind_stack_base == 0) {
343 stack = VG_(am_alloc_VgStack)( &initial_SP );
344 if (stack) {
345 tst->os_state.valgrind_stack_base = (Addr)stack;
346 tst->os_state.valgrind_stack_init_SP = initial_SP;
350 if (0)
351 VG_(printf)( "stack for tid %d at %p; init_SP=%p\n",
352 tid,
353 (void*)tst->os_state.valgrind_stack_base,
354 (void*)tst->os_state.valgrind_stack_init_SP );
356 return tst->os_state.valgrind_stack_init_SP;
359 /* Allocate a stack for the main thread, and run it all the way to the
360 end. Although we already have a working VgStack
361 (VG_(interim_stack)) it's better to allocate a new one, so that
362 overflow detection works uniformly for all threads.
364 void VG_(main_thread_wrapper_NORETURN)(ThreadId tid)
366 Addr sp;
367 VG_(debugLog)(1, "syswrap-linux",
368 "entering VG_(main_thread_wrapper_NORETURN)\n");
370 sp = ML_(allocstack)(tid);
371 #if defined(ENABLE_INNER_CLIENT_REQUEST)
373 // we must register the main thread stack before the call
374 // to ML_(call_on_new_stack_0_1), otherwise the outer valgrind
375 // reports 'write error' on the non registered stack.
376 ThreadState* tst = VG_(get_ThreadState)(tid);
377 INNER_REQUEST
378 ((void)
379 VALGRIND_STACK_REGISTER (tst->os_state.valgrind_stack_base,
380 tst->os_state.valgrind_stack_init_SP));
382 #endif
384 #if defined(VGP_ppc32_linux)
385 /* make a stack frame */
386 sp -= 16;
387 sp &= ~0xF;
388 *(UWord *)sp = 0;
389 #elif defined(VGP_ppc64be_linux) || defined(VGP_ppc64le_linux)
390 /* make a stack frame */
391 sp -= 112;
392 sp &= ~((Addr)0xF);
393 *(UWord *)sp = 0;
394 #elif defined(VGP_s390x_linux)
395 /* make a stack frame */
396 sp -= 160;
397 sp &= ~((Addr)0xF);
398 *(UWord *)sp = 0;
399 #endif
401 /* If we can't even allocate the first thread's stack, we're hosed.
402 Give up. */
403 vg_assert2(sp != 0, "Cannot allocate main thread's stack.");
405 /* shouldn't be any other threads around yet */
406 vg_assert( VG_(count_living_threads)() == 1 );
408 ML_(call_on_new_stack_0_1)(
409 (Addr)sp, /* stack */
410 0, /* bogus return address */
411 run_a_thread_NORETURN, /* fn to call */
412 (Word)tid /* arg to give it */
415 /*NOTREACHED*/
416 vg_assert(0);
420 /* Do a clone which is really a fork() */
421 SysRes ML_(do_fork_clone) ( ThreadId tid, UInt flags,
422 Int* parent_tidptr, Int* child_tidptr )
424 vki_sigset_t fork_saved_mask;
425 vki_sigset_t mask;
426 SysRes res;
428 if (flags & (VKI_CLONE_SETTLS | VKI_CLONE_FS | VKI_CLONE_VM
429 | VKI_CLONE_FILES | VKI_CLONE_VFORK))
430 return VG_(mk_SysRes_Error)( VKI_EINVAL );
432 /* Block all signals during fork, so that we can fix things up in
433 the child without being interrupted. */
434 VG_(sigfillset)(&mask);
435 VG_(sigprocmask)(VKI_SIG_SETMASK, &mask, &fork_saved_mask);
437 VG_(do_atfork_pre)(tid);
439 /* Since this is the fork() form of clone, we don't need all that
440 VG_(clone) stuff */
441 #if defined(VGP_x86_linux) \
442 || defined(VGP_ppc32_linux) \
443 || defined(VGP_ppc64be_linux) || defined(VGP_ppc64le_linux) \
444 || defined(VGP_arm_linux) || defined(VGP_mips32_linux) \
445 || defined(VGP_mips64_linux) || defined(VGP_arm64_linux)
446 res = VG_(do_syscall5)( __NR_clone, flags,
447 (UWord)NULL, (UWord)parent_tidptr,
448 (UWord)NULL, (UWord)child_tidptr );
449 #elif defined(VGP_amd64_linux)
450 /* note that the last two arguments are the opposite way round to x86 and
451 ppc32 as the amd64 kernel expects the arguments in a different order */
452 res = VG_(do_syscall5)( __NR_clone, flags,
453 (UWord)NULL, (UWord)parent_tidptr,
454 (UWord)child_tidptr, (UWord)NULL );
455 #elif defined(VGP_s390x_linux)
456 /* Note that s390 has the stack first and then the flags */
457 res = VG_(do_syscall4)( __NR_clone, (UWord) NULL, flags,
458 (UWord)parent_tidptr, (UWord)child_tidptr);
459 #else
460 # error Unknown platform
461 #endif
463 if (!sr_isError(res) && sr_Res(res) == 0) {
464 /* child */
465 VG_(do_atfork_child)(tid);
467 /* restore signal mask */
468 VG_(sigprocmask)(VKI_SIG_SETMASK, &fork_saved_mask, NULL);
470 /* If --child-silent-after-fork=yes was specified, set the
471 output file descriptors to 'impossible' values. This is
472 noticed by send_bytes_to_logging_sink in m_libcprint.c, which
473 duly stops writing any further output. */
474 if (VG_(clo_child_silent_after_fork)) {
475 if (!VG_(log_output_sink).is_socket)
476 VG_(log_output_sink).fd = -1;
477 if (!VG_(xml_output_sink).is_socket)
478 VG_(xml_output_sink).fd = -1;
481 else
482 if (!sr_isError(res) && sr_Res(res) > 0) {
483 /* parent */
484 VG_(do_atfork_parent)(tid);
486 if (VG_(clo_trace_syscalls))
487 VG_(printf)(" clone(fork): process %d created child %ld\n",
488 VG_(getpid)(), sr_Res(res));
490 /* restore signal mask */
491 VG_(sigprocmask)(VKI_SIG_SETMASK, &fork_saved_mask, NULL);
494 return res;
498 /* ---------------------------------------------------------------------
499 PRE/POST wrappers for arch-generic, Linux-specific syscalls
500 ------------------------------------------------------------------ */
502 // Nb: See the comment above the generic PRE/POST wrappers in
503 // m_syswrap/syswrap-generic.c for notes about how they work.
505 #define PRE(name) DEFN_PRE_TEMPLATE(linux, name)
506 #define POST(name) DEFN_POST_TEMPLATE(linux, name)
508 // Macros to support 64-bit syscall args split into two 32 bit values
509 #define LOHI64(lo,hi) ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
510 #if defined(VG_LITTLEENDIAN)
511 #define MERGE64(lo,hi) ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
512 #define MERGE64_FIRST(name) name##_low
513 #define MERGE64_SECOND(name) name##_high
514 #elif defined(VG_BIGENDIAN)
515 #define MERGE64(hi,lo) ( ((ULong)(lo)) | (((ULong)(hi)) << 32) )
516 #define MERGE64_FIRST(name) name##_high
517 #define MERGE64_SECOND(name) name##_low
518 #else
519 #error Unknown endianness
520 #endif
522 /* ---------------------------------------------------------------------
523 *mount wrappers
524 ------------------------------------------------------------------ */
526 PRE(sys_mount)
528 // Nb: depending on 'flags', the 'type' and 'data' args may be ignored.
529 // We are conservative and check everything, except the memory pointed to
530 // by 'data'.
531 *flags |= SfMayBlock;
532 PRINT("sys_mount( %#lx(%s), %#lx(%s), %#lx(%s), %#lx, %#lx )",
533 ARG1,(HChar*)ARG1, ARG2,(HChar*)ARG2, ARG3,(HChar*)ARG3, ARG4, ARG5);
534 PRE_REG_READ5(long, "mount",
535 char *, source, char *, target, char *, type,
536 unsigned long, flags, void *, data);
537 if (ARG1)
538 PRE_MEM_RASCIIZ( "mount(source)", ARG1);
539 PRE_MEM_RASCIIZ( "mount(target)", ARG2);
540 PRE_MEM_RASCIIZ( "mount(type)", ARG3);
543 PRE(sys_oldumount)
545 PRINT("sys_oldumount( %#lx )", ARG1);
546 PRE_REG_READ1(long, "umount", char *, path);
547 PRE_MEM_RASCIIZ( "umount(path)", ARG1);
550 PRE(sys_umount)
552 PRINT("sys_umount( %#lx, %ld )", ARG1, ARG2);
553 PRE_REG_READ2(long, "umount2", char *, path, int, flags);
554 PRE_MEM_RASCIIZ( "umount2(path)", ARG1);
557 /* Not actually wrapped by GLibc but does things with the system
558 * mounts so it is put here.
560 PRE(sys_pivot_root)
562 PRINT("sys_pivot_root ( %s %s )", (HChar*)ARG1, (HChar*)ARG2);
563 PRE_REG_READ2(int, "pivot_root", char *, new_root, char *, old_root);
564 PRE_MEM_RASCIIZ( "pivot_root(new_root)", ARG1);
565 PRE_MEM_RASCIIZ( "pivot_root(old_root)", ARG2);
569 /* ---------------------------------------------------------------------
570 16- and 32-bit uid/gid wrappers
571 ------------------------------------------------------------------ */
573 PRE(sys_setfsuid16)
575 PRINT("sys_setfsuid16 ( %ld )", ARG1);
576 PRE_REG_READ1(long, "setfsuid16", vki_old_uid_t, uid);
579 PRE(sys_setfsuid)
581 PRINT("sys_setfsuid ( %ld )", ARG1);
582 PRE_REG_READ1(long, "setfsuid", vki_uid_t, uid);
585 PRE(sys_setfsgid16)
587 PRINT("sys_setfsgid16 ( %ld )", ARG1);
588 PRE_REG_READ1(long, "setfsgid16", vki_old_gid_t, gid);
591 PRE(sys_setfsgid)
593 PRINT("sys_setfsgid ( %ld )", ARG1);
594 PRE_REG_READ1(long, "setfsgid", vki_gid_t, gid);
597 PRE(sys_setresuid16)
599 PRINT("sys_setresuid16 ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
600 PRE_REG_READ3(long, "setresuid16",
601 vki_old_uid_t, ruid, vki_old_uid_t, euid, vki_old_uid_t, suid);
604 PRE(sys_setresuid)
606 PRINT("sys_setresuid ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
607 PRE_REG_READ3(long, "setresuid",
608 vki_uid_t, ruid, vki_uid_t, euid, vki_uid_t, suid);
611 PRE(sys_getresuid16)
613 PRINT("sys_getresuid16 ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
614 PRE_REG_READ3(long, "getresuid16",
615 vki_old_uid_t *, ruid, vki_old_uid_t *, euid,
616 vki_old_uid_t *, suid);
617 PRE_MEM_WRITE( "getresuid16(ruid)", ARG1, sizeof(vki_old_uid_t) );
618 PRE_MEM_WRITE( "getresuid16(euid)", ARG2, sizeof(vki_old_uid_t) );
619 PRE_MEM_WRITE( "getresuid16(suid)", ARG3, sizeof(vki_old_uid_t) );
621 POST(sys_getresuid16)
623 vg_assert(SUCCESS);
624 if (RES == 0) {
625 POST_MEM_WRITE( ARG1, sizeof(vki_old_uid_t) );
626 POST_MEM_WRITE( ARG2, sizeof(vki_old_uid_t) );
627 POST_MEM_WRITE( ARG3, sizeof(vki_old_uid_t) );
631 PRE(sys_getresuid)
633 PRINT("sys_getresuid ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
634 PRE_REG_READ3(long, "getresuid",
635 vki_uid_t *, ruid, vki_uid_t *, euid, vki_uid_t *, suid);
636 PRE_MEM_WRITE( "getresuid(ruid)", ARG1, sizeof(vki_uid_t) );
637 PRE_MEM_WRITE( "getresuid(euid)", ARG2, sizeof(vki_uid_t) );
638 PRE_MEM_WRITE( "getresuid(suid)", ARG3, sizeof(vki_uid_t) );
640 POST(sys_getresuid)
642 vg_assert(SUCCESS);
643 if (RES == 0) {
644 POST_MEM_WRITE( ARG1, sizeof(vki_uid_t) );
645 POST_MEM_WRITE( ARG2, sizeof(vki_uid_t) );
646 POST_MEM_WRITE( ARG3, sizeof(vki_uid_t) );
650 PRE(sys_setresgid16)
652 PRINT("sys_setresgid16 ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
653 PRE_REG_READ3(long, "setresgid16",
654 vki_old_gid_t, rgid,
655 vki_old_gid_t, egid, vki_old_gid_t, sgid);
658 PRE(sys_setresgid)
660 PRINT("sys_setresgid ( %ld, %ld, %ld )", ARG1, ARG2, ARG3);
661 PRE_REG_READ3(long, "setresgid",
662 vki_gid_t, rgid, vki_gid_t, egid, vki_gid_t, sgid);
665 PRE(sys_getresgid16)
667 PRINT("sys_getresgid16 ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
668 PRE_REG_READ3(long, "getresgid16",
669 vki_old_gid_t *, rgid, vki_old_gid_t *, egid,
670 vki_old_gid_t *, sgid);
671 PRE_MEM_WRITE( "getresgid16(rgid)", ARG1, sizeof(vki_old_gid_t) );
672 PRE_MEM_WRITE( "getresgid16(egid)", ARG2, sizeof(vki_old_gid_t) );
673 PRE_MEM_WRITE( "getresgid16(sgid)", ARG3, sizeof(vki_old_gid_t) );
675 POST(sys_getresgid16)
677 vg_assert(SUCCESS);
678 if (RES == 0) {
679 POST_MEM_WRITE( ARG1, sizeof(vki_old_gid_t) );
680 POST_MEM_WRITE( ARG2, sizeof(vki_old_gid_t) );
681 POST_MEM_WRITE( ARG3, sizeof(vki_old_gid_t) );
685 PRE(sys_getresgid)
687 PRINT("sys_getresgid ( %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3);
688 PRE_REG_READ3(long, "getresgid",
689 vki_gid_t *, rgid, vki_gid_t *, egid, vki_gid_t *, sgid);
690 PRE_MEM_WRITE( "getresgid(rgid)", ARG1, sizeof(vki_gid_t) );
691 PRE_MEM_WRITE( "getresgid(egid)", ARG2, sizeof(vki_gid_t) );
692 PRE_MEM_WRITE( "getresgid(sgid)", ARG3, sizeof(vki_gid_t) );
694 POST(sys_getresgid)
696 vg_assert(SUCCESS);
697 if (RES == 0) {
698 POST_MEM_WRITE( ARG1, sizeof(vki_gid_t) );
699 POST_MEM_WRITE( ARG2, sizeof(vki_gid_t) );
700 POST_MEM_WRITE( ARG3, sizeof(vki_gid_t) );
704 /* ---------------------------------------------------------------------
705 miscellaneous wrappers
706 ------------------------------------------------------------------ */
708 PRE(sys_exit_group)
710 ThreadId t;
711 ThreadState* tst;
713 PRINT("exit_group( %ld )", ARG1);
714 PRE_REG_READ1(void, "exit_group", int, status);
716 tst = VG_(get_ThreadState)(tid);
717 /* A little complex; find all the threads with the same threadgroup
718 as this one (including this one), and mark them to exit */
719 /* It is unclear how one can get a threadgroup in this process which
720 is not the threadgroup of the calling thread:
721 The assignments to threadgroups are:
722 = 0; /// scheduler.c os_state_clear
723 = getpid(); /// scheduler.c in child after fork
724 = getpid(); /// this file, in thread_wrapper
725 = ptst->os_state.threadgroup; /// syswrap-*-linux.c,
726 copying the thread group of the thread doing clone
727 So, the only case where the threadgroup might be different to the getpid
728 value is in the child, just after fork. But then the fork syscall is
729 still going on, the forked thread has had no chance yet to make this
730 syscall. */
731 for (t = 1; t < VG_N_THREADS; t++) {
732 if ( /* not alive */
733 VG_(threads)[t].status == VgTs_Empty
735 /* not our group */
736 VG_(threads)[t].os_state.threadgroup != tst->os_state.threadgroup
738 continue;
739 /* Assign the exit code, VG_(nuke_all_threads_except) will assign
740 the exitreason. */
741 VG_(threads)[t].os_state.exitcode = ARG1;
744 /* Indicate in all other threads that the process is exiting.
745 Then wait using VG_(reap_threads) for these threads to disappear.
747 Can this give a deadlock if another thread is calling exit in parallel
748 and would then wait for this thread to disappear ?
749 The answer is no:
750 Other threads are either blocked in a syscall or have yielded the CPU.
752 A thread that has yielded the CPU is trying to get the big lock in
753 VG_(scheduler). This thread will get the CPU thanks to the call
754 to VG_(reap_threads). The scheduler will then check for signals,
755 kill the process if this is a fatal signal, and otherwise prepare
756 the thread for handling this signal. After this preparation, if
757 the thread status is VG_(is_exiting), the scheduler exits the thread.
758 So, a thread that has yielded the CPU does not have a chance to
759 call exit => no deadlock for this thread.
761 VG_(nuke_all_threads_except) will send the VG_SIGVGKILL signal
762 to all threads blocked in a syscall.
763 The syscall will be interrupted, and the control will go to the
764 scheduler. The scheduler will then return, as the thread is in
765 exiting state. */
767 VG_(nuke_all_threads_except)( tid, VgSrc_ExitProcess );
768 VG_(reap_threads)(tid);
769 VG_(threads)[tid].exitreason = VgSrc_ExitThread;
770 /* we do assign VgSrc_ExitThread and not VgSrc_ExitProcess, as this thread
771 is the thread calling exit_group and so its registers must be considered
772 as not reachable. See pub_tool_machine.h VG_(apply_to_GP_regs). */
774 /* We have to claim the syscall already succeeded. */
775 SET_STATUS_Success(0);
778 PRE(sys_llseek)
780 PRINT("sys_llseek ( %ld, 0x%lx, 0x%lx, %#lx, %ld )", ARG1,ARG2,ARG3,ARG4,ARG5);
781 PRE_REG_READ5(long, "llseek",
782 unsigned int, fd, unsigned long, offset_high,
783 unsigned long, offset_low, vki_loff_t *, result,
784 unsigned int, whence);
785 if (!ML_(fd_allowed)(ARG1, "llseek", tid, False))
786 SET_STATUS_Failure( VKI_EBADF );
787 else
788 PRE_MEM_WRITE( "llseek(result)", ARG4, sizeof(vki_loff_t));
790 POST(sys_llseek)
792 vg_assert(SUCCESS);
793 if (RES == 0)
794 POST_MEM_WRITE( ARG4, sizeof(vki_loff_t) );
797 PRE(sys_adjtimex)
799 struct vki_timex *tx = (struct vki_timex *)ARG1;
800 PRINT("sys_adjtimex ( %#lx )", ARG1);
801 PRE_REG_READ1(long, "adjtimex", struct timex *, buf);
802 PRE_MEM_READ( "adjtimex(timex->modes)", ARG1, sizeof(tx->modes));
804 #define ADJX(bits,field) \
805 if (tx->modes & (bits)) \
806 PRE_MEM_READ( "adjtimex(timex->"#field")", \
807 (Addr)&tx->field, sizeof(tx->field))
809 if (tx->modes & VKI_ADJ_ADJTIME) {
810 if (!(tx->modes & VKI_ADJ_OFFSET_READONLY))
811 PRE_MEM_READ( "adjtimex(timex->offset)", (Addr)&tx->offset, sizeof(tx->offset));
812 } else {
813 ADJX(VKI_ADJ_OFFSET, offset);
814 ADJX(VKI_ADJ_FREQUENCY, freq);
815 ADJX(VKI_ADJ_MAXERROR, maxerror);
816 ADJX(VKI_ADJ_ESTERROR, esterror);
817 ADJX(VKI_ADJ_STATUS, status);
818 ADJX(VKI_ADJ_TIMECONST|VKI_ADJ_TAI, constant);
819 ADJX(VKI_ADJ_TICK, tick);
821 #undef ADJX
823 PRE_MEM_WRITE( "adjtimex(timex)", ARG1, sizeof(struct vki_timex));
826 POST(sys_adjtimex)
828 POST_MEM_WRITE( ARG1, sizeof(struct vki_timex) );
831 PRE(sys_clock_adjtime)
833 struct vki_timex *tx = (struct vki_timex *)ARG2;
834 PRINT("sys_clock_adjtime ( %ld, %#lx )", ARG1,ARG2);
835 PRE_REG_READ2(long, "clock_adjtime", vki_clockid_t, id, struct timex *, buf);
836 PRE_MEM_READ( "clock_adjtime(timex->modes)", ARG2, sizeof(tx->modes));
838 #define ADJX(bits,field) \
839 if (tx->modes & (bits)) \
840 PRE_MEM_READ( "clock_adjtime(timex->"#field")", \
841 (Addr)&tx->field, sizeof(tx->field))
843 if (tx->modes & VKI_ADJ_ADJTIME) {
844 if (!(tx->modes & VKI_ADJ_OFFSET_READONLY))
845 PRE_MEM_READ( "clock_adjtime(timex->offset)", (Addr)&tx->offset, sizeof(tx->offset));
846 } else {
847 ADJX(VKI_ADJ_OFFSET, offset);
848 ADJX(VKI_ADJ_FREQUENCY, freq);
849 ADJX(VKI_ADJ_MAXERROR, maxerror);
850 ADJX(VKI_ADJ_ESTERROR, esterror);
851 ADJX(VKI_ADJ_STATUS, status);
852 ADJX(VKI_ADJ_TIMECONST|VKI_ADJ_TAI, constant);
853 ADJX(VKI_ADJ_TICK, tick);
855 #undef ADJX
857 PRE_MEM_WRITE( "adjtimex(timex)", ARG2, sizeof(struct vki_timex));
860 POST(sys_clock_adjtime)
862 POST_MEM_WRITE( ARG2, sizeof(struct vki_timex) );
865 PRE(sys_ioperm)
867 PRINT("sys_ioperm ( %ld, %ld, %ld )", ARG1, ARG2, ARG3 );
868 PRE_REG_READ3(long, "ioperm",
869 unsigned long, from, unsigned long, num, int, turn_on);
872 PRE(sys_syslog)
874 *flags |= SfMayBlock;
875 PRINT("sys_syslog (%ld, %#lx, %ld)", ARG1,ARG2,ARG3);
876 PRE_REG_READ3(long, "syslog", int, type, char *, bufp, int, len);
877 switch (ARG1) {
878 // The kernel uses magic numbers here, rather than named constants,
879 // therefore so do we.
880 case 2: case 3: case 4:
881 PRE_MEM_WRITE( "syslog(bufp)", ARG2, ARG3);
882 break;
883 default:
884 break;
887 POST(sys_syslog)
889 switch (ARG1) {
890 case 2: case 3: case 4:
891 POST_MEM_WRITE( ARG2, ARG3 );
892 break;
893 default:
894 break;
898 PRE(sys_vhangup)
900 PRINT("sys_vhangup ( )");
901 PRE_REG_READ0(long, "vhangup");
904 PRE(sys_sysinfo)
906 PRINT("sys_sysinfo ( %#lx )",ARG1);
907 PRE_REG_READ1(long, "sysinfo", struct sysinfo *, info);
908 PRE_MEM_WRITE( "sysinfo(info)", ARG1, sizeof(struct vki_sysinfo) );
910 POST(sys_sysinfo)
912 POST_MEM_WRITE( ARG1, sizeof(struct vki_sysinfo) );
915 PRE(sys_personality)
917 PRINT("sys_personality ( %llu )", (ULong)ARG1);
918 PRE_REG_READ1(long, "personality", vki_u_long, persona);
921 PRE(sys_sysctl)
923 struct __vki_sysctl_args *args;
924 PRINT("sys_sysctl ( %#lx )", ARG1 );
925 args = (struct __vki_sysctl_args *)ARG1;
926 PRE_REG_READ1(long, "sysctl", struct __sysctl_args *, args);
927 PRE_MEM_WRITE( "sysctl(args)", ARG1, sizeof(struct __vki_sysctl_args) );
928 if (!VG_(am_is_valid_for_client)(ARG1, sizeof(struct __vki_sysctl_args),
929 VKI_PROT_READ)) {
930 SET_STATUS_Failure( VKI_EFAULT );
931 return;
934 PRE_MEM_READ("sysctl(name)", (Addr)args->name, args->nlen * sizeof(*args->name));
935 if (args->newval != NULL)
936 PRE_MEM_READ("sysctl(newval)", (Addr)args->newval, args->newlen);
937 if (args->oldlenp != NULL) {
938 PRE_MEM_READ("sysctl(oldlenp)", (Addr)args->oldlenp, sizeof(*args->oldlenp));
939 PRE_MEM_WRITE("sysctl(oldval)", (Addr)args->oldval, *args->oldlenp);
942 POST(sys_sysctl)
944 struct __vki_sysctl_args *args;
945 args = (struct __vki_sysctl_args *)ARG1;
946 if (args->oldlenp != NULL) {
947 POST_MEM_WRITE((Addr)args->oldlenp, sizeof(*args->oldlenp));
948 POST_MEM_WRITE((Addr)args->oldval, 1 + *args->oldlenp);
952 PRE(sys_prctl)
954 *flags |= SfMayBlock;
955 PRINT( "sys_prctl ( %ld, %ld, %ld, %ld, %ld )", ARG1, ARG2, ARG3, ARG4, ARG5 );
956 switch (ARG1) {
957 case VKI_PR_SET_PDEATHSIG:
958 PRE_REG_READ2(int, "prctl", int, option, int, signal);
959 break;
960 case VKI_PR_GET_PDEATHSIG:
961 PRE_REG_READ2(int, "prctl", int, option, int *, signal);
962 PRE_MEM_WRITE("prctl(get-death-signal)", ARG2, sizeof(Int));
963 break;
964 case VKI_PR_GET_DUMPABLE:
965 PRE_REG_READ1(int, "prctl", int, option);
966 break;
967 case VKI_PR_SET_DUMPABLE:
968 PRE_REG_READ2(int, "prctl", int, option, int, dump);
969 break;
970 case VKI_PR_GET_UNALIGN:
971 PRE_REG_READ2(int, "prctl", int, option, int *, value);
972 PRE_MEM_WRITE("prctl(get-unalign)", ARG2, sizeof(Int));
973 break;
974 case VKI_PR_SET_UNALIGN:
975 PRE_REG_READ2(int, "prctl", int, option, int, value);
976 break;
977 case VKI_PR_GET_KEEPCAPS:
978 PRE_REG_READ1(int, "prctl", int, option);
979 break;
980 case VKI_PR_SET_KEEPCAPS:
981 PRE_REG_READ2(int, "prctl", int, option, int, keepcaps);
982 break;
983 case VKI_PR_GET_FPEMU:
984 PRE_REG_READ2(int, "prctl", int, option, int *, value);
985 PRE_MEM_WRITE("prctl(get-fpemu)", ARG2, sizeof(Int));
986 break;
987 case VKI_PR_SET_FPEMU:
988 PRE_REG_READ2(int, "prctl", int, option, int, value);
989 break;
990 case VKI_PR_GET_FPEXC:
991 PRE_REG_READ2(int, "prctl", int, option, int *, value);
992 PRE_MEM_WRITE("prctl(get-fpexc)", ARG2, sizeof(Int));
993 break;
994 case VKI_PR_SET_FPEXC:
995 PRE_REG_READ2(int, "prctl", int, option, int, value);
996 break;
997 case VKI_PR_GET_TIMING:
998 PRE_REG_READ1(int, "prctl", int, option);
999 break;
1000 case VKI_PR_SET_TIMING:
1001 PRE_REG_READ2(int, "prctl", int, option, int, timing);
1002 break;
1003 case VKI_PR_SET_NAME:
1004 PRE_REG_READ2(int, "prctl", int, option, char *, name);
1005 PRE_MEM_RASCIIZ("prctl(set-name)", ARG2);
1006 break;
1007 case VKI_PR_GET_NAME:
1008 PRE_REG_READ2(int, "prctl", int, option, char *, name);
1009 PRE_MEM_WRITE("prctl(get-name)", ARG2, VKI_TASK_COMM_LEN);
1010 break;
1011 case VKI_PR_GET_ENDIAN:
1012 PRE_REG_READ2(int, "prctl", int, option, int *, value);
1013 PRE_MEM_WRITE("prctl(get-endian)", ARG2, sizeof(Int));
1014 break;
1015 case VKI_PR_SET_ENDIAN:
1016 PRE_REG_READ2(int, "prctl", int, option, int, value);
1017 break;
1018 default:
1019 PRE_REG_READ5(long, "prctl",
1020 int, option, unsigned long, arg2, unsigned long, arg3,
1021 unsigned long, arg4, unsigned long, arg5);
1022 break;
1025 POST(sys_prctl)
1027 switch (ARG1) {
1028 case VKI_PR_GET_PDEATHSIG:
1029 POST_MEM_WRITE(ARG2, sizeof(Int));
1030 break;
1031 case VKI_PR_GET_UNALIGN:
1032 POST_MEM_WRITE(ARG2, sizeof(Int));
1033 break;
1034 case VKI_PR_GET_FPEMU:
1035 POST_MEM_WRITE(ARG2, sizeof(Int));
1036 break;
1037 case VKI_PR_GET_FPEXC:
1038 POST_MEM_WRITE(ARG2, sizeof(Int));
1039 break;
1040 case VKI_PR_GET_NAME:
1041 POST_MEM_WRITE(ARG2, VKI_TASK_COMM_LEN);
1042 break;
1043 case VKI_PR_GET_ENDIAN:
1044 POST_MEM_WRITE(ARG2, sizeof(Int));
1045 break;
1046 case VKI_PR_SET_NAME:
1048 const HChar* new_name = (const HChar*) ARG2;
1049 if (new_name) { // Paranoia
1050 ThreadState* tst = VG_(get_ThreadState)(tid);
1051 SizeT new_len = VG_(strlen)(new_name);
1053 /* Don't bother reusing the memory. This is a rare event. */
1054 tst->thread_name =
1055 VG_(realloc)("syswrap.prctl", tst->thread_name, new_len + 1);
1056 VG_(strcpy)(tst->thread_name, new_name);
1059 break;
1063 PRE(sys_sendfile)
1065 *flags |= SfMayBlock;
1066 PRINT("sys_sendfile ( %ld, %ld, %#lx, %lu )", ARG1,ARG2,ARG3,ARG4);
1067 PRE_REG_READ4(ssize_t, "sendfile",
1068 int, out_fd, int, in_fd, vki_off_t *, offset,
1069 vki_size_t, count);
1070 if (ARG3 != 0)
1071 PRE_MEM_WRITE( "sendfile(offset)", ARG3, sizeof(vki_off_t) );
1073 POST(sys_sendfile)
1075 if (ARG3 != 0 ) {
1076 POST_MEM_WRITE( ARG3, sizeof( vki_off_t ) );
1080 PRE(sys_sendfile64)
1082 *flags |= SfMayBlock;
1083 PRINT("sendfile64 ( %ld, %ld, %#lx, %lu )",ARG1,ARG2,ARG3,ARG4);
1084 PRE_REG_READ4(ssize_t, "sendfile64",
1085 int, out_fd, int, in_fd, vki_loff_t *, offset,
1086 vki_size_t, count);
1087 if (ARG3 != 0)
1088 PRE_MEM_WRITE( "sendfile64(offset)", ARG3, sizeof(vki_loff_t) );
1090 POST(sys_sendfile64)
1092 if (ARG3 != 0 ) {
1093 POST_MEM_WRITE( ARG3, sizeof(vki_loff_t) );
1097 PRE(sys_futex)
1100 arg param used by ops
1102 ARG1 - u32 *futex all
1103 ARG2 - int op
1104 ARG3 - int val WAIT,WAKE,FD,REQUEUE,CMP_REQUEUE
1105 ARG4 - struct timespec *utime WAIT:time* REQUEUE,CMP_REQUEUE:val2
1106 ARG5 - u32 *uaddr2 REQUEUE,CMP_REQUEUE
1107 ARG6 - int val3 CMP_REQUEUE
1109 PRINT("sys_futex ( %#lx, %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
1110 switch(ARG2 & ~(VKI_FUTEX_PRIVATE_FLAG|VKI_FUTEX_CLOCK_REALTIME)) {
1111 case VKI_FUTEX_CMP_REQUEUE:
1112 case VKI_FUTEX_WAKE_OP:
1113 case VKI_FUTEX_CMP_REQUEUE_PI:
1114 PRE_REG_READ6(long, "futex",
1115 vki_u32 *, futex, int, op, int, val,
1116 struct timespec *, utime, vki_u32 *, uaddr2, int, val3);
1117 break;
1118 case VKI_FUTEX_REQUEUE:
1119 case VKI_FUTEX_WAIT_REQUEUE_PI:
1120 PRE_REG_READ5(long, "futex",
1121 vki_u32 *, futex, int, op, int, val,
1122 struct timespec *, utime, vki_u32 *, uaddr2);
1123 break;
1124 case VKI_FUTEX_WAIT_BITSET:
1125 /* Check that the address at least begins in client-accessible area. */
1126 if (!VG_(am_is_valid_for_client)( ARG1, 1, VKI_PROT_READ )) {
1127 SET_STATUS_Failure( VKI_EFAULT );
1128 return;
1130 if (*(vki_u32 *)ARG1 != ARG3) {
1131 PRE_REG_READ5(long, "futex",
1132 vki_u32 *, futex, int, op, int, val,
1133 struct timespec *, utime, int, dummy);
1134 } else {
1135 PRE_REG_READ6(long, "futex",
1136 vki_u32 *, futex, int, op, int, val,
1137 struct timespec *, utime, int, dummy, int, val3);
1139 break;
1140 case VKI_FUTEX_WAKE_BITSET:
1141 PRE_REG_READ6(long, "futex",
1142 vki_u32 *, futex, int, op, int, val,
1143 int, dummy, int, dummy2, int, val3);
1144 break;
1145 case VKI_FUTEX_WAIT:
1146 case VKI_FUTEX_LOCK_PI:
1147 PRE_REG_READ4(long, "futex",
1148 vki_u32 *, futex, int, op, int, val,
1149 struct timespec *, utime);
1150 break;
1151 case VKI_FUTEX_WAKE:
1152 case VKI_FUTEX_FD:
1153 case VKI_FUTEX_TRYLOCK_PI:
1154 PRE_REG_READ3(long, "futex",
1155 vki_u32 *, futex, int, op, int, val);
1156 break;
1157 case VKI_FUTEX_UNLOCK_PI:
1158 default:
1159 PRE_REG_READ2(long, "futex", vki_u32 *, futex, int, op);
1160 break;
1163 *flags |= SfMayBlock;
1165 switch(ARG2 & ~(VKI_FUTEX_PRIVATE_FLAG|VKI_FUTEX_CLOCK_REALTIME)) {
1166 case VKI_FUTEX_WAIT:
1167 case VKI_FUTEX_LOCK_PI:
1168 case VKI_FUTEX_WAIT_BITSET:
1169 case VKI_FUTEX_WAIT_REQUEUE_PI:
1170 PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
1171 if (ARG4 != 0)
1172 PRE_MEM_READ( "futex(timeout)", ARG4, sizeof(struct vki_timespec) );
1173 break;
1175 case VKI_FUTEX_REQUEUE:
1176 case VKI_FUTEX_CMP_REQUEUE:
1177 case VKI_FUTEX_CMP_REQUEUE_PI:
1178 case VKI_FUTEX_WAKE_OP:
1179 PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
1180 PRE_MEM_READ( "futex(futex2)", ARG5, sizeof(Int) );
1181 break;
1183 case VKI_FUTEX_FD:
1184 case VKI_FUTEX_TRYLOCK_PI:
1185 case VKI_FUTEX_UNLOCK_PI:
1186 PRE_MEM_READ( "futex(futex)", ARG1, sizeof(Int) );
1187 break;
1189 case VKI_FUTEX_WAKE:
1190 case VKI_FUTEX_WAKE_BITSET:
1191 /* no additional pointers */
1192 break;
1194 default:
1195 SET_STATUS_Failure( VKI_ENOSYS ); // some futex function we don't understand
1196 break;
1199 POST(sys_futex)
1201 vg_assert(SUCCESS);
1202 POST_MEM_WRITE( ARG1, sizeof(int) );
1203 if (ARG2 == VKI_FUTEX_FD) {
1204 if (!ML_(fd_allowed)(RES, "futex", tid, True)) {
1205 VG_(close)(RES);
1206 SET_STATUS_Failure( VKI_EMFILE );
1207 } else {
1208 if (VG_(clo_track_fds))
1209 ML_(record_fd_open_nameless)(tid, RES);
1214 PRE(sys_set_robust_list)
1216 PRINT("sys_set_robust_list ( %#lx, %ld )", ARG1,ARG2);
1217 PRE_REG_READ2(long, "set_robust_list",
1218 struct vki_robust_list_head *, head, vki_size_t, len);
1220 /* Just check the robust_list_head structure is readable - don't
1221 try and chase the list as the kernel will only read it when
1222 the thread exits so the current contents is irrelevant. */
1223 if (ARG1 != 0)
1224 PRE_MEM_READ("set_robust_list(head)", ARG1, ARG2);
1227 PRE(sys_get_robust_list)
1229 PRINT("sys_get_robust_list ( %ld, %#lx, %ld )", ARG1,ARG2,ARG3);
1230 PRE_REG_READ3(long, "get_robust_list",
1231 int, pid,
1232 struct vki_robust_list_head **, head_ptr,
1233 vki_size_t *, len_ptr);
1234 PRE_MEM_WRITE("get_robust_list(head_ptr)",
1235 ARG2, sizeof(struct vki_robust_list_head *));
1236 PRE_MEM_WRITE("get_robust_list(len_ptr)",
1237 ARG3, sizeof(struct vki_size_t *));
1239 POST(sys_get_robust_list)
1241 POST_MEM_WRITE(ARG2, sizeof(struct vki_robust_list_head *));
1242 POST_MEM_WRITE(ARG3, sizeof(struct vki_size_t *));
1245 PRE(sys_pselect6)
1247 *flags |= SfMayBlock;
1248 PRINT("sys_pselect6 ( %ld, %#lx, %#lx, %#lx, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
1249 PRE_REG_READ6(long, "pselect6",
1250 int, n, vki_fd_set *, readfds, vki_fd_set *, writefds,
1251 vki_fd_set *, exceptfds, struct vki_timeval *, timeout,
1252 void *, sig);
1253 // XXX: this possibly understates how much memory is read.
1254 if (ARG2 != 0)
1255 PRE_MEM_READ( "pselect6(readfds)",
1256 ARG2, ARG1/8 /* __FD_SETSIZE/8 */ );
1257 if (ARG3 != 0)
1258 PRE_MEM_READ( "pselect6(writefds)",
1259 ARG3, ARG1/8 /* __FD_SETSIZE/8 */ );
1260 if (ARG4 != 0)
1261 PRE_MEM_READ( "pselect6(exceptfds)",
1262 ARG4, ARG1/8 /* __FD_SETSIZE/8 */ );
1263 if (ARG5 != 0)
1264 PRE_MEM_READ( "pselect6(timeout)", ARG5, sizeof(struct vki_timeval) );
1265 if (ARG6 != 0)
1266 PRE_MEM_READ( "pselect6(sig)", ARG6, sizeof(void *)+sizeof(vki_size_t) );
1269 PRE(sys_ppoll)
1271 UInt i;
1272 struct vki_pollfd* ufds = (struct vki_pollfd *)ARG1;
1273 *flags |= SfMayBlock;
1274 PRINT("sys_ppoll ( %#lx, %ld, %#lx, %#lx, %llu )\n", ARG1,ARG2,ARG3,ARG4,(ULong)ARG5);
1275 PRE_REG_READ5(long, "ppoll",
1276 struct vki_pollfd *, ufds, unsigned int, nfds,
1277 struct vki_timespec *, tsp, vki_sigset_t *, sigmask,
1278 vki_size_t, sigsetsize);
1280 for (i = 0; i < ARG2; i++) {
1281 PRE_MEM_READ( "ppoll(ufds.fd)",
1282 (Addr)(&ufds[i].fd), sizeof(ufds[i].fd) );
1283 PRE_MEM_READ( "ppoll(ufds.events)",
1284 (Addr)(&ufds[i].events), sizeof(ufds[i].events) );
1285 PRE_MEM_WRITE( "ppoll(ufds.revents)",
1286 (Addr)(&ufds[i].revents), sizeof(ufds[i].revents) );
1289 if (ARG3)
1290 PRE_MEM_READ( "ppoll(tsp)", ARG3, sizeof(struct vki_timespec) );
1291 if (ARG4)
1292 PRE_MEM_READ( "ppoll(sigmask)", ARG4, sizeof(vki_sigset_t) );
1295 POST(sys_ppoll)
1297 if (RES > 0) {
1298 UInt i;
1299 struct vki_pollfd* ufds = (struct vki_pollfd *)ARG1;
1300 for (i = 0; i < ARG2; i++)
1301 POST_MEM_WRITE( (Addr)(&ufds[i].revents), sizeof(ufds[i].revents) );
1306 /* ---------------------------------------------------------------------
1307 epoll_* wrappers
1308 ------------------------------------------------------------------ */
1310 PRE(sys_epoll_create)
1312 PRINT("sys_epoll_create ( %ld )", ARG1);
1313 PRE_REG_READ1(long, "epoll_create", int, size);
1315 POST(sys_epoll_create)
1317 vg_assert(SUCCESS);
1318 if (!ML_(fd_allowed)(RES, "epoll_create", tid, True)) {
1319 VG_(close)(RES);
1320 SET_STATUS_Failure( VKI_EMFILE );
1321 } else {
1322 if (VG_(clo_track_fds))
1323 ML_(record_fd_open_nameless) (tid, RES);
1327 PRE(sys_epoll_create1)
1329 PRINT("sys_epoll_create1 ( %ld )", ARG1);
1330 PRE_REG_READ1(long, "epoll_create1", int, flags);
1332 POST(sys_epoll_create1)
1334 vg_assert(SUCCESS);
1335 if (!ML_(fd_allowed)(RES, "epoll_create1", tid, True)) {
1336 VG_(close)(RES);
1337 SET_STATUS_Failure( VKI_EMFILE );
1338 } else {
1339 if (VG_(clo_track_fds))
1340 ML_(record_fd_open_nameless) (tid, RES);
1344 PRE(sys_epoll_ctl)
1346 static const HChar* epoll_ctl_s[3] = {
1347 "EPOLL_CTL_ADD",
1348 "EPOLL_CTL_DEL",
1349 "EPOLL_CTL_MOD"
1351 PRINT("sys_epoll_ctl ( %ld, %s, %ld, %#lx )",
1352 ARG1, ( ARG2<3 ? epoll_ctl_s[ARG2] : "?" ), ARG3, ARG4);
1353 PRE_REG_READ4(long, "epoll_ctl",
1354 int, epfd, int, op, int, fd, struct vki_epoll_event *, event);
1355 if (ARG2 != VKI_EPOLL_CTL_DEL)
1356 PRE_MEM_READ( "epoll_ctl(event)", ARG4, sizeof(struct vki_epoll_event) );
1359 PRE(sys_epoll_wait)
1361 *flags |= SfMayBlock;
1362 PRINT("sys_epoll_wait ( %ld, %#lx, %ld, %ld )", ARG1, ARG2, ARG3, ARG4);
1363 PRE_REG_READ4(long, "epoll_wait",
1364 int, epfd, struct vki_epoll_event *, events,
1365 int, maxevents, int, timeout);
1366 PRE_MEM_WRITE( "epoll_wait(events)", ARG2, sizeof(struct vki_epoll_event)*ARG3);
1368 POST(sys_epoll_wait)
1370 vg_assert(SUCCESS);
1371 if (RES > 0)
1372 POST_MEM_WRITE( ARG2, sizeof(struct vki_epoll_event)*RES ) ;
1375 PRE(sys_epoll_pwait)
1377 *flags |= SfMayBlock;
1378 PRINT("sys_epoll_pwait ( %ld, %#lx, %ld, %ld, %#lx, %llu )", ARG1,ARG2,ARG3,ARG4,ARG5,(ULong)ARG6);
1379 PRE_REG_READ6(long, "epoll_pwait",
1380 int, epfd, struct vki_epoll_event *, events,
1381 int, maxevents, int, timeout, vki_sigset_t *, sigmask,
1382 vki_size_t, sigsetsize);
1383 PRE_MEM_WRITE( "epoll_pwait(events)", ARG2, sizeof(struct vki_epoll_event)*ARG3);
1384 if (ARG4)
1385 PRE_MEM_READ( "epoll_pwait(sigmask)", ARG5, sizeof(vki_sigset_t) );
1387 POST(sys_epoll_pwait)
1389 vg_assert(SUCCESS);
1390 if (RES > 0)
1391 POST_MEM_WRITE( ARG2, sizeof(struct vki_epoll_event)*RES ) ;
1394 PRE(sys_eventfd)
1396 PRINT("sys_eventfd ( %lu )", ARG1);
1397 PRE_REG_READ1(long, "sys_eventfd", unsigned int, count);
1399 POST(sys_eventfd)
1401 if (!ML_(fd_allowed)(RES, "eventfd", tid, True)) {
1402 VG_(close)(RES);
1403 SET_STATUS_Failure( VKI_EMFILE );
1404 } else {
1405 if (VG_(clo_track_fds))
1406 ML_(record_fd_open_nameless) (tid, RES);
1410 PRE(sys_eventfd2)
1412 PRINT("sys_eventfd2 ( %lu, %ld )", ARG1,ARG2);
1413 PRE_REG_READ2(long, "sys_eventfd2", unsigned int, count, int, flags);
1415 POST(sys_eventfd2)
1417 if (!ML_(fd_allowed)(RES, "eventfd2", tid, True)) {
1418 VG_(close)(RES);
1419 SET_STATUS_Failure( VKI_EMFILE );
1420 } else {
1421 if (VG_(clo_track_fds))
1422 ML_(record_fd_open_nameless) (tid, RES);
1426 PRE(sys_fallocate)
1428 *flags |= SfMayBlock;
1429 #if VG_WORDSIZE == 4
1430 PRINT("sys_fallocate ( %ld, %ld, %lld, %lld )",
1431 ARG1, ARG2, MERGE64(ARG3,ARG4), MERGE64(ARG5,ARG6));
1432 PRE_REG_READ6(long, "fallocate",
1433 int, fd, int, mode,
1434 unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
1435 unsigned, MERGE64_FIRST(len), unsigned, MERGE64_SECOND(len));
1436 #elif VG_WORDSIZE == 8
1437 PRINT("sys_fallocate ( %ld, %ld, %lld, %lld )",
1438 ARG1, ARG2, (Long)ARG3, (Long)ARG4);
1439 PRE_REG_READ4(long, "fallocate",
1440 int, fd, int, mode, vki_loff_t, offset, vki_loff_t, len);
1441 #else
1442 # error Unexpected word size
1443 #endif
1444 if (!ML_(fd_allowed)(ARG1, "fallocate", tid, False))
1445 SET_STATUS_Failure( VKI_EBADF );
1448 PRE(sys_prlimit64)
1450 PRINT("sys_prlimit64 ( %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4);
1451 PRE_REG_READ4(long, "prlimit64",
1452 vki_pid_t, pid, unsigned int, resource,
1453 const struct rlimit64 *, new_rlim,
1454 struct rlimit64 *, old_rlim);
1455 if (ARG3)
1456 PRE_MEM_READ( "rlimit64(new_rlim)", ARG3, sizeof(struct vki_rlimit64) );
1457 if (ARG4)
1458 PRE_MEM_WRITE( "rlimit64(old_rlim)", ARG4, sizeof(struct vki_rlimit64) );
1460 if (ARG3 &&
1461 ((struct vki_rlimit64 *)ARG3)->rlim_cur > ((struct vki_rlimit64 *)ARG3)->rlim_max) {
1462 SET_STATUS_Failure( VKI_EINVAL );
1464 else if (ARG1 == 0 || ARG1 == VG_(getpid)()) {
1465 switch (ARG2) {
1466 case VKI_RLIMIT_NOFILE:
1467 SET_STATUS_Success( 0 );
1468 if (ARG4) {
1469 ((struct vki_rlimit64 *)ARG4)->rlim_cur = VG_(fd_soft_limit);
1470 ((struct vki_rlimit64 *)ARG4)->rlim_max = VG_(fd_hard_limit);
1472 if (ARG3) {
1473 if (((struct vki_rlimit64 *)ARG3)->rlim_cur > VG_(fd_hard_limit) ||
1474 ((struct vki_rlimit64 *)ARG3)->rlim_max != VG_(fd_hard_limit)) {
1475 SET_STATUS_Failure( VKI_EPERM );
1477 else {
1478 VG_(fd_soft_limit) = ((struct vki_rlimit64 *)ARG3)->rlim_cur;
1481 break;
1483 case VKI_RLIMIT_DATA:
1484 SET_STATUS_Success( 0 );
1485 if (ARG4) {
1486 ((struct vki_rlimit64 *)ARG4)->rlim_cur = VG_(client_rlimit_data).rlim_cur;
1487 ((struct vki_rlimit64 *)ARG4)->rlim_max = VG_(client_rlimit_data).rlim_max;
1489 if (ARG3) {
1490 if (((struct vki_rlimit64 *)ARG3)->rlim_cur > VG_(client_rlimit_data).rlim_max ||
1491 ((struct vki_rlimit64 *)ARG3)->rlim_max > VG_(client_rlimit_data).rlim_max) {
1492 SET_STATUS_Failure( VKI_EPERM );
1494 else {
1495 VG_(client_rlimit_data).rlim_cur = ((struct vki_rlimit64 *)ARG3)->rlim_cur;
1496 VG_(client_rlimit_data).rlim_max = ((struct vki_rlimit64 *)ARG3)->rlim_max;
1499 break;
1501 case VKI_RLIMIT_STACK:
1502 SET_STATUS_Success( 0 );
1503 if (ARG4) {
1504 ((struct vki_rlimit64 *)ARG4)->rlim_cur = VG_(client_rlimit_stack).rlim_cur;
1505 ((struct vki_rlimit64 *)ARG4)->rlim_max = VG_(client_rlimit_stack).rlim_max;
1507 if (ARG3) {
1508 if (((struct vki_rlimit64 *)ARG3)->rlim_cur > VG_(client_rlimit_stack).rlim_max ||
1509 ((struct vki_rlimit64 *)ARG3)->rlim_max > VG_(client_rlimit_stack).rlim_max) {
1510 SET_STATUS_Failure( VKI_EPERM );
1512 else {
1513 VG_(threads)[tid].client_stack_szB = ((struct vki_rlimit64 *)ARG3)->rlim_cur;
1514 VG_(client_rlimit_stack).rlim_cur = ((struct vki_rlimit64 *)ARG3)->rlim_cur;
1515 VG_(client_rlimit_stack).rlim_max = ((struct vki_rlimit64 *)ARG3)->rlim_max;
1518 break;
1523 POST(sys_prlimit64)
1525 if (ARG4)
1526 POST_MEM_WRITE( ARG4, sizeof(struct vki_rlimit64) );
1529 /* ---------------------------------------------------------------------
1530 tid-related wrappers
1531 ------------------------------------------------------------------ */
1533 PRE(sys_gettid)
1535 PRINT("sys_gettid ()");
1536 PRE_REG_READ0(long, "gettid");
1539 PRE(sys_set_tid_address)
1541 PRINT("sys_set_tid_address ( %#lx )", ARG1);
1542 PRE_REG_READ1(long, "set_tid_address", int *, tidptr);
1545 PRE(sys_tkill)
1547 PRINT("sys_tgkill ( %ld, %ld )", ARG1,ARG2);
1548 PRE_REG_READ2(long, "tkill", int, tid, int, sig);
1549 if (!ML_(client_signal_OK)(ARG2)) {
1550 SET_STATUS_Failure( VKI_EINVAL );
1551 return;
1554 /* Check to see if this kill gave us a pending signal */
1555 *flags |= SfPollAfter;
1557 if (VG_(clo_trace_signals))
1558 VG_(message)(Vg_DebugMsg, "tkill: sending signal %ld to pid %ld\n",
1559 ARG2, ARG1);
1561 /* If we're sending SIGKILL, check to see if the target is one of
1562 our threads and handle it specially. */
1563 if (ARG2 == VKI_SIGKILL && ML_(do_sigkill)(ARG1, -1)) {
1564 SET_STATUS_Success(0);
1565 return;
1568 /* Ask to handle this syscall via the slow route, since that's the
1569 only one that sets tst->status to VgTs_WaitSys. If the result
1570 of doing the syscall is an immediate run of
1571 async_signalhandler() in m_signals, then we need the thread to
1572 be properly tidied away. I have the impression the previous
1573 version of this wrapper worked on x86/amd64 only because the
1574 kernel did not immediately deliver the async signal to this
1575 thread (on ppc it did, which broke the assertion re tst->status
1576 at the top of async_signalhandler()). */
1577 *flags |= SfMayBlock;
1579 POST(sys_tkill)
1581 if (VG_(clo_trace_signals))
1582 VG_(message)(Vg_DebugMsg, "tkill: sent signal %ld to pid %ld\n",
1583 ARG2, ARG1);
1586 PRE(sys_tgkill)
1588 PRINT("sys_tgkill ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
1589 PRE_REG_READ3(long, "tgkill", int, tgid, int, tid, int, sig);
1590 if (!ML_(client_signal_OK)(ARG3)) {
1591 SET_STATUS_Failure( VKI_EINVAL );
1592 return;
1595 /* Check to see if this kill gave us a pending signal */
1596 *flags |= SfPollAfter;
1598 if (VG_(clo_trace_signals))
1599 VG_(message)(Vg_DebugMsg,
1600 "tgkill: sending signal %ld to pid %ld/%ld\n",
1601 ARG3, ARG1, ARG2);
1603 /* If we're sending SIGKILL, check to see if the target is one of
1604 our threads and handle it specially. */
1605 if (ARG3 == VKI_SIGKILL && ML_(do_sigkill)(ARG2, ARG1)) {
1606 SET_STATUS_Success(0);
1607 return;
1610 /* Ask to handle this syscall via the slow route, since that's the
1611 only one that sets tst->status to VgTs_WaitSys. If the result
1612 of doing the syscall is an immediate run of
1613 async_signalhandler() in m_signals, then we need the thread to
1614 be properly tidied away. I have the impression the previous
1615 version of this wrapper worked on x86/amd64 only because the
1616 kernel did not immediately deliver the async signal to this
1617 thread (on ppc it did, which broke the assertion re tst->status
1618 at the top of async_signalhandler()). */
1619 *flags |= SfMayBlock;
1621 POST(sys_tgkill)
1623 if (VG_(clo_trace_signals))
1624 VG_(message)(Vg_DebugMsg,
1625 "tgkill: sent signal %ld to pid %ld/%ld\n",
1626 ARG3, ARG1, ARG2);
1629 /* ---------------------------------------------------------------------
1630 fadvise64* wrappers
1631 ------------------------------------------------------------------ */
1633 PRE(sys_fadvise64)
1635 PRINT("sys_fadvise64 ( %ld, %lld, %lu, %ld )",
1636 ARG1, MERGE64(ARG2,ARG3), ARG4, ARG5);
1637 PRE_REG_READ5(long, "fadvise64",
1638 int, fd, vki_u32, MERGE64_FIRST(offset), vki_u32, MERGE64_SECOND(offset),
1639 vki_size_t, len, int, advice);
1642 PRE(sys_fadvise64_64)
1644 PRINT("sys_fadvise64_64 ( %ld, %lld, %lld, %ld )",
1645 ARG1, MERGE64(ARG2,ARG3), MERGE64(ARG4,ARG5), ARG6);
1646 PRE_REG_READ6(long, "fadvise64_64",
1647 int, fd, vki_u32, MERGE64_FIRST(offset), vki_u32, MERGE64_SECOND(offset),
1648 vki_u32, MERGE64_FIRST(len), vki_u32, MERGE64_SECOND(len), int, advice);
1651 /* ---------------------------------------------------------------------
1652 io_* wrappers
1653 ------------------------------------------------------------------ */
1655 // Nb: this wrapper has to pad/unpad memory around the syscall itself,
1656 // and this allows us to control exactly the code that gets run while
1657 // the padding is in place.
1659 PRE(sys_io_setup)
1661 PRINT("sys_io_setup ( %lu, %#lx )", ARG1,ARG2);
1662 PRE_REG_READ2(long, "io_setup",
1663 unsigned, nr_events, vki_aio_context_t *, ctxp);
1664 PRE_MEM_WRITE( "io_setup(ctxp)", ARG2, sizeof(vki_aio_context_t) );
1667 POST(sys_io_setup)
1669 SizeT size;
1670 struct vki_aio_ring *r;
1672 size = VG_PGROUNDUP(sizeof(struct vki_aio_ring) +
1673 ARG1*sizeof(struct vki_io_event));
1674 r = *(struct vki_aio_ring **)ARG2;
1675 vg_assert(ML_(valid_client_addr)((Addr)r, size, tid, "io_setup"));
1677 ML_(notify_core_and_tool_of_mmap)( (Addr)r, size,
1678 VKI_PROT_READ | VKI_PROT_WRITE,
1679 VKI_MAP_ANONYMOUS, -1, 0 );
1681 POST_MEM_WRITE( ARG2, sizeof(vki_aio_context_t) );
1684 // Nb: This wrapper is "Special" because we need 'size' to do the unmap
1685 // after the syscall. We must get 'size' from the aio_ring structure,
1686 // before the syscall, while the aio_ring structure still exists. (And we
1687 // know that we must look at the aio_ring structure because Tom inspected the
1688 // kernel and glibc sources to see what they do, yuk.)
1690 // XXX This segment can be implicitly unmapped when aio
1691 // file-descriptors are closed...
1692 PRE(sys_io_destroy)
1694 SizeT size = 0;
1696 PRINT("sys_io_destroy ( %llu )", (ULong)ARG1);
1697 PRE_REG_READ1(long, "io_destroy", vki_aio_context_t, ctx);
1699 // If we are going to seg fault (due to a bogus ARG1) do it as late as
1700 // possible...
1701 if (ML_(safe_to_deref)( (void*)ARG1, sizeof(struct vki_aio_ring))) {
1702 struct vki_aio_ring *r = (struct vki_aio_ring *)ARG1;
1703 size = VG_PGROUNDUP(sizeof(struct vki_aio_ring) +
1704 r->nr*sizeof(struct vki_io_event));
1707 SET_STATUS_from_SysRes( VG_(do_syscall1)(SYSNO, ARG1) );
1709 if (SUCCESS && RES == 0) {
1710 Bool d = VG_(am_notify_munmap)( ARG1, size );
1711 VG_TRACK( die_mem_munmap, ARG1, size );
1712 if (d)
1713 VG_(discard_translations)( (Addr64)ARG1, (ULong)size,
1714 "PRE(sys_io_destroy)" );
1718 PRE(sys_io_getevents)
1720 *flags |= SfMayBlock;
1721 PRINT("sys_io_getevents ( %llu, %lld, %lld, %#lx, %#lx )",
1722 (ULong)ARG1,(Long)ARG2,(Long)ARG3,ARG4,ARG5);
1723 PRE_REG_READ5(long, "io_getevents",
1724 vki_aio_context_t, ctx_id, long, min_nr, long, nr,
1725 struct io_event *, events,
1726 struct timespec *, timeout);
1727 if (ARG3 > 0)
1728 PRE_MEM_WRITE( "io_getevents(events)",
1729 ARG4, sizeof(struct vki_io_event)*ARG3 );
1730 if (ARG5 != 0)
1731 PRE_MEM_READ( "io_getevents(timeout)",
1732 ARG5, sizeof(struct vki_timespec));
1734 POST(sys_io_getevents)
1736 Int i;
1737 vg_assert(SUCCESS);
1738 if (RES > 0) {
1739 POST_MEM_WRITE( ARG4, sizeof(struct vki_io_event)*RES );
1740 for (i = 0; i < RES; i++) {
1741 const struct vki_io_event *vev = ((struct vki_io_event *)ARG4) + i;
1742 const struct vki_iocb *cb = (struct vki_iocb *)(Addr)vev->obj;
1744 switch (cb->aio_lio_opcode) {
1745 case VKI_IOCB_CMD_PREAD:
1746 if (vev->result > 0)
1747 POST_MEM_WRITE( cb->aio_buf, vev->result );
1748 break;
1750 case VKI_IOCB_CMD_PWRITE:
1751 break;
1753 case VKI_IOCB_CMD_FSYNC:
1754 break;
1756 case VKI_IOCB_CMD_FDSYNC:
1757 break;
1759 case VKI_IOCB_CMD_PREADV:
1760 if (vev->result > 0) {
1761 struct vki_iovec * vec = (struct vki_iovec *)(Addr)cb->aio_buf;
1762 Int remains = vev->result;
1763 Int j;
1765 for (j = 0; j < cb->aio_nbytes; j++) {
1766 Int nReadThisBuf = vec[j].iov_len;
1767 if (nReadThisBuf > remains) nReadThisBuf = remains;
1768 POST_MEM_WRITE( (Addr)vec[j].iov_base, nReadThisBuf );
1769 remains -= nReadThisBuf;
1770 if (remains < 0) VG_(core_panic)("io_getevents(PREADV): remains < 0");
1773 break;
1775 case VKI_IOCB_CMD_PWRITEV:
1776 break;
1778 default:
1779 VG_(message)(Vg_DebugMsg,
1780 "Warning: unhandled io_getevents opcode: %u\n",
1781 cb->aio_lio_opcode);
1782 break;
1788 PRE(sys_io_submit)
1790 Int i, j;
1792 PRINT("sys_io_submit ( %llu, %ld, %#lx )", (ULong)ARG1,ARG2,ARG3);
1793 PRE_REG_READ3(long, "io_submit",
1794 vki_aio_context_t, ctx_id, long, nr,
1795 struct iocb **, iocbpp);
1796 PRE_MEM_READ( "io_submit(iocbpp)", ARG3, ARG2*sizeof(struct vki_iocb *) );
1797 if (ARG3 != 0) {
1798 for (i = 0; i < ARG2; i++) {
1799 struct vki_iocb *cb = ((struct vki_iocb **)ARG3)[i];
1800 struct vki_iovec *iov;
1802 PRE_MEM_READ( "io_submit(iocb)", (Addr)cb, sizeof(struct vki_iocb) );
1803 switch (cb->aio_lio_opcode) {
1804 case VKI_IOCB_CMD_PREAD:
1805 PRE_MEM_WRITE( "io_submit(PREAD)", cb->aio_buf, cb->aio_nbytes );
1806 break;
1808 case VKI_IOCB_CMD_PWRITE:
1809 PRE_MEM_READ( "io_submit(PWRITE)", cb->aio_buf, cb->aio_nbytes );
1810 break;
1812 case VKI_IOCB_CMD_FSYNC:
1813 break;
1815 case VKI_IOCB_CMD_FDSYNC:
1816 break;
1818 case VKI_IOCB_CMD_PREADV:
1819 iov = (struct vki_iovec *)(Addr)cb->aio_buf;
1820 PRE_MEM_READ( "io_submit(PREADV)", cb->aio_buf, cb->aio_nbytes * sizeof(struct vki_iovec) );
1821 for (j = 0; j < cb->aio_nbytes; j++)
1822 PRE_MEM_WRITE( "io_submit(PREADV(iov[i]))", (Addr)iov[j].iov_base, iov[j].iov_len );
1823 break;
1825 case VKI_IOCB_CMD_PWRITEV:
1826 iov = (struct vki_iovec *)(Addr)cb->aio_buf;
1827 PRE_MEM_READ( "io_submit(PWRITEV)", cb->aio_buf, cb->aio_nbytes * sizeof(struct vki_iovec) );
1828 for (j = 0; j < cb->aio_nbytes; j++)
1829 PRE_MEM_READ( "io_submit(PWRITEV(iov[i]))", (Addr)iov[j].iov_base, iov[j].iov_len );
1830 break;
1832 default:
1833 VG_(message)(Vg_DebugMsg,"Warning: unhandled io_submit opcode: %u\n",
1834 cb->aio_lio_opcode);
1835 break;
1841 PRE(sys_io_cancel)
1843 PRINT("sys_io_cancel ( %llu, %#lx, %#lx )", (ULong)ARG1,ARG2,ARG3);
1844 PRE_REG_READ3(long, "io_cancel",
1845 vki_aio_context_t, ctx_id, struct iocb *, iocb,
1846 struct io_event *, result);
1847 PRE_MEM_READ( "io_cancel(iocb)", ARG2, sizeof(struct vki_iocb) );
1848 PRE_MEM_WRITE( "io_cancel(result)", ARG3, sizeof(struct vki_io_event) );
1850 POST(sys_io_cancel)
1852 POST_MEM_WRITE( ARG3, sizeof(struct vki_io_event) );
1855 /* ---------------------------------------------------------------------
1856 *_mempolicy wrappers
1857 ------------------------------------------------------------------ */
1859 PRE(sys_mbind)
1861 PRINT("sys_mbind ( %#lx, %lu, %ld, %#lx, %lu, %lu )", ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
1862 PRE_REG_READ6(long, "mbind",
1863 unsigned long, start, unsigned long, len,
1864 unsigned long, policy, unsigned long *, nodemask,
1865 unsigned long, maxnode, unsigned, flags);
1866 if (ARG1 != 0)
1867 PRE_MEM_READ( "mbind(nodemask)", ARG4,
1868 VG_ROUNDUP( ARG5-1, sizeof(UWord) * 8 ) / 8 );
1871 PRE(sys_set_mempolicy)
1873 PRINT("sys_set_mempolicy ( %ld, %#lx, %ld )", ARG1,ARG2,ARG3);
1874 PRE_REG_READ3(long, "set_mempolicy",
1875 int, policy, unsigned long *, nodemask,
1876 unsigned long, maxnode);
1877 PRE_MEM_READ( "set_mempolicy(nodemask)", ARG2,
1878 VG_ROUNDUP( ARG3-1, sizeof(UWord) * 8 ) / 8 );
1881 PRE(sys_get_mempolicy)
1883 PRINT("sys_get_mempolicy ( %#lx, %#lx, %ld, %#lx, %lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
1884 PRE_REG_READ5(long, "get_mempolicy",
1885 int *, policy, unsigned long *, nodemask,
1886 unsigned long, maxnode, unsigned long, addr,
1887 unsigned long, flags);
1888 if (ARG1 != 0)
1889 PRE_MEM_WRITE( "get_mempolicy(policy)", ARG1, sizeof(Int) );
1890 if (ARG2 != 0)
1891 PRE_MEM_WRITE( "get_mempolicy(nodemask)", ARG2,
1892 VG_ROUNDUP( ARG3-1, sizeof(UWord) * 8 ) / 8 );
1894 POST(sys_get_mempolicy)
1896 if (ARG1 != 0)
1897 POST_MEM_WRITE( ARG1, sizeof(Int) );
1898 if (ARG2 != 0)
1899 POST_MEM_WRITE( ARG2, VG_ROUNDUP( ARG3-1, sizeof(UWord) * 8 ) / 8 );
1902 /* ---------------------------------------------------------------------
1903 fanotify_* wrappers
1904 ------------------------------------------------------------------ */
1906 PRE(sys_fanotify_init)
1908 PRINT("sys_fanotify_init ( %lu, %lu )", ARG1,ARG2);
1909 PRE_REG_READ2(long, "fanotify_init",
1910 unsigned int, flags, unsigned int, event_f_flags);
1913 POST(sys_fanotify_init)
1915 vg_assert(SUCCESS);
1916 if (!ML_(fd_allowed)(RES, "fanotify_init", tid, True)) {
1917 VG_(close)(RES);
1918 SET_STATUS_Failure( VKI_EMFILE );
1919 } else {
1920 if (VG_(clo_track_fds))
1921 ML_(record_fd_open_nameless) (tid, RES);
1925 PRE(sys_fanotify_mark)
1927 #if VG_WORDSIZE == 4
1928 PRINT( "sys_fanotify_mark ( %ld, %lu, %llu, %ld, %#lx(%s))",
1929 ARG1,ARG2,MERGE64(ARG3,ARG4),ARG5,ARG6,(char *)ARG6);
1930 PRE_REG_READ6(long, "sys_fanotify_mark",
1931 int, fanotify_fd, unsigned int, flags,
1932 __vki_u32, mask0, __vki_u32, mask1,
1933 int, dfd, const char *, pathname);
1934 if (ARG6)
1935 PRE_MEM_RASCIIZ( "fanotify_mark(path)", ARG6);
1936 #elif VG_WORDSIZE == 8
1937 PRINT( "sys_fanotify_mark ( %ld, %lu, %llu, %ld, %#lx(%s))",
1938 ARG1,ARG2,(ULong)ARG3,ARG4,ARG5,(char *)ARG5);
1939 PRE_REG_READ5(long, "sys_fanotify_mark",
1940 int, fanotify_fd, unsigned int, flags,
1941 __vki_u64, mask,
1942 int, dfd, const char *, pathname);
1943 if (ARG5)
1944 PRE_MEM_RASCIIZ( "fanotify_mark(path)", ARG5);
1945 #else
1946 # error Unexpected word size
1947 #endif
1950 /* ---------------------------------------------------------------------
1951 inotify_* wrappers
1952 ------------------------------------------------------------------ */
1954 PRE(sys_inotify_init)
1956 PRINT("sys_inotify_init ( )");
1957 PRE_REG_READ0(long, "inotify_init");
1959 POST(sys_inotify_init)
1961 vg_assert(SUCCESS);
1962 if (!ML_(fd_allowed)(RES, "inotify_init", tid, True)) {
1963 VG_(close)(RES);
1964 SET_STATUS_Failure( VKI_EMFILE );
1965 } else {
1966 if (VG_(clo_track_fds))
1967 ML_(record_fd_open_nameless) (tid, RES);
1971 PRE(sys_inotify_init1)
1973 PRINT("sys_inotify_init ( %ld )", ARG1);
1974 PRE_REG_READ1(long, "inotify_init", int, flag);
1977 POST(sys_inotify_init1)
1979 vg_assert(SUCCESS);
1980 if (!ML_(fd_allowed)(RES, "inotify_init", tid, True)) {
1981 VG_(close)(RES);
1982 SET_STATUS_Failure( VKI_EMFILE );
1983 } else {
1984 if (VG_(clo_track_fds))
1985 ML_(record_fd_open_nameless) (tid, RES);
1989 PRE(sys_inotify_add_watch)
1991 PRINT( "sys_inotify_add_watch ( %ld, %#lx, %lx )", ARG1,ARG2,ARG3);
1992 PRE_REG_READ3(long, "inotify_add_watch", int, fd, char *, path, int, mask);
1993 PRE_MEM_RASCIIZ( "inotify_add_watch(path)", ARG2 );
1996 PRE(sys_inotify_rm_watch)
1998 PRINT( "sys_inotify_rm_watch ( %ld, %lx )", ARG1,ARG2);
1999 PRE_REG_READ2(long, "inotify_rm_watch", int, fd, int, wd);
2002 /* ---------------------------------------------------------------------
2003 mq_* wrappers
2004 ------------------------------------------------------------------ */
2006 PRE(sys_mq_open)
2008 PRINT("sys_mq_open( %#lx(%s), %ld, %lld, %#lx )",
2009 ARG1,(char*)ARG1,ARG2,(ULong)ARG3,ARG4);
2010 PRE_REG_READ4(long, "mq_open",
2011 const char *, name, int, oflag, vki_mode_t, mode,
2012 struct mq_attr *, attr);
2013 PRE_MEM_RASCIIZ( "mq_open(name)", ARG1 );
2014 if ((ARG2 & VKI_O_CREAT) != 0 && ARG4 != 0) {
2015 const struct vki_mq_attr *attr = (struct vki_mq_attr *)ARG4;
2016 PRE_MEM_READ( "mq_open(attr->mq_maxmsg)",
2017 (Addr)&attr->mq_maxmsg, sizeof(attr->mq_maxmsg) );
2018 PRE_MEM_READ( "mq_open(attr->mq_msgsize)",
2019 (Addr)&attr->mq_msgsize, sizeof(attr->mq_msgsize) );
2022 POST(sys_mq_open)
2024 vg_assert(SUCCESS);
2025 if (!ML_(fd_allowed)(RES, "mq_open", tid, True)) {
2026 VG_(close)(RES);
2027 SET_STATUS_Failure( VKI_EMFILE );
2028 } else {
2029 if (VG_(clo_track_fds))
2030 ML_(record_fd_open_with_given_name)(tid, RES, (HChar*)ARG1);
2034 PRE(sys_mq_unlink)
2036 PRINT("sys_mq_unlink ( %#lx(%s) )", ARG1,(char*)ARG1);
2037 PRE_REG_READ1(long, "mq_unlink", const char *, name);
2038 PRE_MEM_RASCIIZ( "mq_unlink(name)", ARG1 );
2041 PRE(sys_mq_timedsend)
2043 *flags |= SfMayBlock;
2044 PRINT("sys_mq_timedsend ( %ld, %#lx, %llu, %ld, %#lx )",
2045 ARG1,ARG2,(ULong)ARG3,ARG4,ARG5);
2046 PRE_REG_READ5(long, "mq_timedsend",
2047 vki_mqd_t, mqdes, const char *, msg_ptr, vki_size_t, msg_len,
2048 unsigned int, msg_prio, const struct timespec *, abs_timeout);
2049 if (!ML_(fd_allowed)(ARG1, "mq_timedsend", tid, False)) {
2050 SET_STATUS_Failure( VKI_EBADF );
2051 } else {
2052 PRE_MEM_READ( "mq_timedsend(msg_ptr)", ARG2, ARG3 );
2053 if (ARG5 != 0)
2054 PRE_MEM_READ( "mq_timedsend(abs_timeout)", ARG5,
2055 sizeof(struct vki_timespec) );
2059 PRE(sys_mq_timedreceive)
2061 *flags |= SfMayBlock;
2062 PRINT("sys_mq_timedreceive( %ld, %#lx, %llu, %#lx, %#lx )",
2063 ARG1,ARG2,(ULong)ARG3,ARG4,ARG5);
2064 PRE_REG_READ5(ssize_t, "mq_timedreceive",
2065 vki_mqd_t, mqdes, char *, msg_ptr, vki_size_t, msg_len,
2066 unsigned int *, msg_prio,
2067 const struct timespec *, abs_timeout);
2068 if (!ML_(fd_allowed)(ARG1, "mq_timedreceive", tid, False)) {
2069 SET_STATUS_Failure( VKI_EBADF );
2070 } else {
2071 PRE_MEM_WRITE( "mq_timedreceive(msg_ptr)", ARG2, ARG3 );
2072 if (ARG4 != 0)
2073 PRE_MEM_WRITE( "mq_timedreceive(msg_prio)",
2074 ARG4, sizeof(unsigned int) );
2075 if (ARG5 != 0)
2076 PRE_MEM_READ( "mq_timedreceive(abs_timeout)",
2077 ARG5, sizeof(struct vki_timespec) );
2080 POST(sys_mq_timedreceive)
2082 POST_MEM_WRITE( ARG2, RES );
2083 if (ARG4 != 0)
2084 POST_MEM_WRITE( ARG4, sizeof(unsigned int) );
2087 PRE(sys_mq_notify)
2089 PRINT("sys_mq_notify( %ld, %#lx )", ARG1,ARG2 );
2090 PRE_REG_READ2(long, "mq_notify",
2091 vki_mqd_t, mqdes, const struct sigevent *, notification);
2092 if (!ML_(fd_allowed)(ARG1, "mq_notify", tid, False))
2093 SET_STATUS_Failure( VKI_EBADF );
2094 else if (ARG2 != 0)
2095 PRE_MEM_READ( "mq_notify(notification)",
2096 ARG2, sizeof(struct vki_sigevent) );
2099 PRE(sys_mq_getsetattr)
2101 PRINT("sys_mq_getsetattr( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3 );
2102 PRE_REG_READ3(long, "mq_getsetattr",
2103 vki_mqd_t, mqdes, const struct mq_attr *, mqstat,
2104 struct mq_attr *, omqstat);
2105 if (!ML_(fd_allowed)(ARG1, "mq_getsetattr", tid, False)) {
2106 SET_STATUS_Failure( VKI_EBADF );
2107 } else {
2108 if (ARG2 != 0) {
2109 const struct vki_mq_attr *attr = (struct vki_mq_attr *)ARG2;
2110 PRE_MEM_READ( "mq_getsetattr(mqstat->mq_flags)",
2111 (Addr)&attr->mq_flags, sizeof(attr->mq_flags) );
2113 if (ARG3 != 0)
2114 PRE_MEM_WRITE( "mq_getsetattr(omqstat)", ARG3,
2115 sizeof(struct vki_mq_attr) );
2118 POST(sys_mq_getsetattr)
2120 if (ARG3 != 0)
2121 POST_MEM_WRITE( ARG3, sizeof(struct vki_mq_attr) );
2124 /* ---------------------------------------------------------------------
2125 clock_* wrappers
2126 ------------------------------------------------------------------ */
2128 PRE(sys_clock_settime)
2130 PRINT("sys_clock_settime( %ld, %#lx )", ARG1,ARG2);
2131 PRE_REG_READ2(long, "clock_settime",
2132 vki_clockid_t, clk_id, const struct timespec *, tp);
2133 PRE_MEM_READ( "clock_settime(tp)", ARG2, sizeof(struct vki_timespec) );
2136 PRE(sys_clock_gettime)
2138 PRINT("sys_clock_gettime( %ld, %#lx )" , ARG1,ARG2);
2139 PRE_REG_READ2(long, "clock_gettime",
2140 vki_clockid_t, clk_id, struct timespec *, tp);
2141 PRE_MEM_WRITE( "clock_gettime(tp)", ARG2, sizeof(struct vki_timespec) );
2143 POST(sys_clock_gettime)
2145 POST_MEM_WRITE( ARG2, sizeof(struct vki_timespec) );
2148 PRE(sys_clock_getres)
2150 PRINT("sys_clock_getres( %ld, %#lx )" , ARG1,ARG2);
2151 // Nb: we can't use "RES" as the param name because that's a macro
2152 // defined above!
2153 PRE_REG_READ2(long, "clock_getres",
2154 vki_clockid_t, clk_id, struct timespec *, res);
2155 if (ARG2 != 0)
2156 PRE_MEM_WRITE( "clock_getres(res)", ARG2, sizeof(struct vki_timespec) );
2158 POST(sys_clock_getres)
2160 if (ARG2 != 0)
2161 POST_MEM_WRITE( ARG2, sizeof(struct vki_timespec) );
2164 PRE(sys_clock_nanosleep)
2166 *flags |= SfMayBlock|SfPostOnFail;
2167 PRINT("sys_clock_nanosleep( %ld, %ld, %#lx, %#lx )", ARG1,ARG2,ARG3,ARG4);
2168 PRE_REG_READ4(int32_t, "clock_nanosleep",
2169 vki_clockid_t, clkid, int, flags,
2170 const struct timespec *, rqtp, struct timespec *, rmtp);
2171 PRE_MEM_READ( "clock_nanosleep(rqtp)", ARG3, sizeof(struct vki_timespec) );
2172 if (ARG4 != 0)
2173 PRE_MEM_WRITE( "clock_nanosleep(rmtp)", ARG4, sizeof(struct vki_timespec) );
2175 POST(sys_clock_nanosleep)
2177 if (ARG4 != 0 && FAILURE && ERR == VKI_EINTR)
2178 POST_MEM_WRITE( ARG4, sizeof(struct vki_timespec) );
2181 /* ---------------------------------------------------------------------
2182 timer_* wrappers
2183 ------------------------------------------------------------------ */
2185 PRE(sys_timer_create)
2187 PRINT("sys_timer_create( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3);
2188 PRE_REG_READ3(long, "timer_create",
2189 vki_clockid_t, clockid, struct sigevent *, evp,
2190 vki_timer_t *, timerid);
2191 if (ARG2 != 0) {
2192 struct vki_sigevent *evp = (struct vki_sigevent *) ARG2;
2193 PRE_MEM_READ( "timer_create(evp.sigev_value)", (Addr)&evp->sigev_value,
2194 sizeof(vki_sigval_t) );
2195 PRE_MEM_READ( "timer_create(evp.sigev_signo)", (Addr)&evp->sigev_signo,
2196 sizeof(int) );
2197 PRE_MEM_READ( "timer_create(evp.sigev_notify)", (Addr)&evp->sigev_notify,
2198 sizeof(int) );
2199 if (ML_(safe_to_deref)(&evp->sigev_notify, sizeof(int))
2200 && (evp->sigev_notify & VKI_SIGEV_THREAD_ID) != 0)
2201 PRE_MEM_READ( "timer_create(evp.sigev_notify_thread_id)",
2202 (Addr)&evp->vki_sigev_notify_thread_id, sizeof(int) );
2204 PRE_MEM_WRITE( "timer_create(timerid)", ARG3, sizeof(vki_timer_t) );
2206 POST(sys_timer_create)
2208 POST_MEM_WRITE( ARG3, sizeof(vki_timer_t) );
2211 PRE(sys_timer_settime)
2213 PRINT("sys_timer_settime( %lld, %ld, %#lx, %#lx )", (ULong)ARG1,ARG2,ARG3,ARG4);
2214 PRE_REG_READ4(long, "timer_settime",
2215 vki_timer_t, timerid, int, flags,
2216 const struct itimerspec *, value,
2217 struct itimerspec *, ovalue);
2218 PRE_MEM_READ( "timer_settime(value)", ARG3,
2219 sizeof(struct vki_itimerspec) );
2220 if (ARG4 != 0)
2221 PRE_MEM_WRITE( "timer_settime(ovalue)", ARG4,
2222 sizeof(struct vki_itimerspec) );
2224 POST(sys_timer_settime)
2226 if (ARG4 != 0)
2227 POST_MEM_WRITE( ARG4, sizeof(struct vki_itimerspec) );
2230 PRE(sys_timer_gettime)
2232 PRINT("sys_timer_gettime( %lld, %#lx )", (ULong)ARG1,ARG2);
2233 PRE_REG_READ2(long, "timer_gettime",
2234 vki_timer_t, timerid, struct itimerspec *, value);
2235 PRE_MEM_WRITE( "timer_gettime(value)", ARG2,
2236 sizeof(struct vki_itimerspec));
2238 POST(sys_timer_gettime)
2240 POST_MEM_WRITE( ARG2, sizeof(struct vki_itimerspec) );
2243 PRE(sys_timer_getoverrun)
2245 PRINT("sys_timer_getoverrun( %#lx )", ARG1);
2246 PRE_REG_READ1(long, "timer_getoverrun", vki_timer_t, timerid);
2249 PRE(sys_timer_delete)
2251 PRINT("sys_timer_delete( %#lx )", ARG1);
2252 PRE_REG_READ1(long, "timer_delete", vki_timer_t, timerid);
2255 /* ---------------------------------------------------------------------
2256 timerfd* wrappers
2257 See also http://lwn.net/Articles/260172/ for an overview.
2258 See also /usr/src/linux/fs/timerfd.c for the implementation.
2259 ------------------------------------------------------------------ */
2261 /* Returns True if running on 2.6.22, else False (or False if
2262 cannot be determined). */
2263 static Bool linux_kernel_2_6_22(void)
2265 static Int result = -1;
2266 Int fd, read;
2267 HChar release[64];
2268 SysRes res;
2270 if (result == -1) {
2271 res = VG_(open)("/proc/sys/kernel/osrelease", 0, 0);
2272 if (sr_isError(res))
2273 return False;
2274 fd = sr_Res(res);
2275 read = VG_(read)(fd, release, sizeof(release) - 1);
2276 vg_assert(read >= 0);
2277 release[read] = 0;
2278 VG_(close)(fd);
2279 //VG_(printf)("kernel release = %s\n", release);
2280 result = (VG_(strncmp)(release, "2.6.22", 6) == 0
2281 && (release[6] < '0' || release[6] > '9'));
2283 vg_assert(result == 0 || result == 1);
2284 return result == 1;
2287 PRE(sys_timerfd_create)
2289 if (linux_kernel_2_6_22()) {
2290 /* 2.6.22 kernel: timerfd system call. */
2291 PRINT("sys_timerfd ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
2292 PRE_REG_READ3(long, "sys_timerfd",
2293 int, fd, int, clockid, const struct itimerspec *, tmr);
2294 PRE_MEM_READ("timerfd(tmr)", ARG3,
2295 sizeof(struct vki_itimerspec) );
2296 if ((Word)ARG1 != -1L && !ML_(fd_allowed)(ARG1, "timerfd", tid, False))
2297 SET_STATUS_Failure( VKI_EBADF );
2298 } else {
2299 /* 2.6.24 and later kernels: timerfd_create system call. */
2300 PRINT("sys_timerfd_create (%ld, %ld )", ARG1, ARG2);
2301 PRE_REG_READ2(long, "timerfd_create", int, clockid, int, flags);
2304 POST(sys_timerfd_create)
2306 if (linux_kernel_2_6_22())
2308 /* 2.6.22 kernel: timerfd system call. */
2309 if (!ML_(fd_allowed)(RES, "timerfd", tid, True)) {
2310 VG_(close)(RES);
2311 SET_STATUS_Failure( VKI_EMFILE );
2312 } else {
2313 if (VG_(clo_track_fds))
2314 ML_(record_fd_open_nameless) (tid, RES);
2317 else
2319 /* 2.6.24 and later kernels: timerfd_create system call. */
2320 if (!ML_(fd_allowed)(RES, "timerfd_create", tid, True)) {
2321 VG_(close)(RES);
2322 SET_STATUS_Failure( VKI_EMFILE );
2323 } else {
2324 if (VG_(clo_track_fds))
2325 ML_(record_fd_open_nameless) (tid, RES);
2330 PRE(sys_timerfd_gettime)
2332 PRINT("sys_timerfd_gettime ( %ld, %#lx )", ARG1, ARG2);
2333 PRE_REG_READ2(long, "timerfd_gettime",
2334 int, ufd,
2335 struct vki_itimerspec*, otmr);
2336 if (!ML_(fd_allowed)(ARG1, "timerfd_gettime", tid, False))
2337 SET_STATUS_Failure(VKI_EBADF);
2338 else
2339 PRE_MEM_WRITE("timerfd_gettime(result)",
2340 ARG2, sizeof(struct vki_itimerspec));
2342 POST(sys_timerfd_gettime)
2344 if (RES == 0)
2345 POST_MEM_WRITE(ARG2, sizeof(struct vki_itimerspec));
2348 PRE(sys_timerfd_settime)
2350 PRINT("sys_timerfd_settime ( %ld, %ld, %#lx, %#lx )", ARG1, ARG2, ARG3, ARG4);
2351 PRE_REG_READ4(long, "timerfd_settime",
2352 int, ufd,
2353 int, flags,
2354 const struct vki_itimerspec*, utmr,
2355 struct vki_itimerspec*, otmr);
2356 if (!ML_(fd_allowed)(ARG1, "timerfd_settime", tid, False))
2357 SET_STATUS_Failure(VKI_EBADF);
2358 else
2360 PRE_MEM_READ("timerfd_settime(result)",
2361 ARG3, sizeof(struct vki_itimerspec));
2362 if (ARG4)
2364 PRE_MEM_WRITE("timerfd_settime(result)",
2365 ARG4, sizeof(struct vki_itimerspec));
2369 POST(sys_timerfd_settime)
2371 if (RES == 0 && ARG4 != 0)
2372 POST_MEM_WRITE(ARG4, sizeof(struct vki_itimerspec));
2375 /* ---------------------------------------------------------------------
2376 capabilities wrappers
2377 ------------------------------------------------------------------ */
2379 PRE(sys_capget)
2381 PRINT("sys_capget ( %#lx, %#lx )", ARG1, ARG2 );
2382 PRE_REG_READ2(long, "capget",
2383 vki_cap_user_header_t, header, vki_cap_user_data_t, data);
2384 PRE_MEM_READ( "capget(header)", ARG1,
2385 sizeof(struct __vki_user_cap_header_struct) );
2386 if (ARG2 != (Addr)NULL)
2387 PRE_MEM_WRITE( "capget(data)", ARG2,
2388 sizeof(struct __vki_user_cap_data_struct) );
2390 POST(sys_capget)
2392 if (ARG2 != (Addr)NULL)
2393 POST_MEM_WRITE( ARG2, sizeof(struct __vki_user_cap_data_struct) );
2396 PRE(sys_capset)
2398 PRINT("sys_capset ( %#lx, %#lx )", ARG1, ARG2 );
2399 PRE_REG_READ2(long, "capset",
2400 vki_cap_user_header_t, header,
2401 const vki_cap_user_data_t, data);
2402 PRE_MEM_READ( "capset(header)",
2403 ARG1, sizeof(struct __vki_user_cap_header_struct) );
2404 PRE_MEM_READ( "capset(data)",
2405 ARG2, sizeof(struct __vki_user_cap_data_struct) );
2408 /* ---------------------------------------------------------------------
2409 16-bit uid/gid/groups wrappers
2410 ------------------------------------------------------------------ */
2412 PRE(sys_getuid16)
2414 PRINT("sys_getuid16 ( )");
2415 PRE_REG_READ0(long, "getuid16");
2418 PRE(sys_setuid16)
2420 PRINT("sys_setuid16 ( %ld )", ARG1);
2421 PRE_REG_READ1(long, "setuid16", vki_old_uid_t, uid);
2424 PRE(sys_getgid16)
2426 PRINT("sys_getgid16 ( )");
2427 PRE_REG_READ0(long, "getgid16");
2430 PRE(sys_setgid16)
2432 PRINT("sys_setgid16 ( %ld )", ARG1);
2433 PRE_REG_READ1(long, "setgid16", vki_old_gid_t, gid);
2436 PRE(sys_geteuid16)
2438 PRINT("sys_geteuid16 ( )");
2439 PRE_REG_READ0(long, "geteuid16");
2442 PRE(sys_getegid16)
2444 PRINT("sys_getegid16 ( )");
2445 PRE_REG_READ0(long, "getegid16");
2448 PRE(sys_setreuid16)
2450 PRINT("setreuid16 ( 0x%lx, 0x%lx )", ARG1, ARG2);
2451 PRE_REG_READ2(long, "setreuid16", vki_old_uid_t, ruid, vki_old_uid_t, euid);
2454 PRE(sys_setregid16)
2456 PRINT("sys_setregid16 ( %ld, %ld )", ARG1, ARG2);
2457 PRE_REG_READ2(long, "setregid16", vki_old_gid_t, rgid, vki_old_gid_t, egid);
2460 PRE(sys_getgroups16)
2462 PRINT("sys_getgroups16 ( %ld, %#lx )", ARG1, ARG2);
2463 PRE_REG_READ2(long, "getgroups16", int, size, vki_old_gid_t *, list);
2464 if (ARG1 > 0)
2465 PRE_MEM_WRITE( "getgroups16(list)", ARG2, ARG1 * sizeof(vki_old_gid_t) );
2467 POST(sys_getgroups16)
2469 vg_assert(SUCCESS);
2470 if (ARG1 > 0 && RES > 0)
2471 POST_MEM_WRITE( ARG2, RES * sizeof(vki_old_gid_t) );
2474 PRE(sys_setgroups16)
2476 PRINT("sys_setgroups16 ( %llu, %#lx )", (ULong)ARG1, ARG2);
2477 PRE_REG_READ2(long, "setgroups16", int, size, vki_old_gid_t *, list);
2478 if (ARG1 > 0)
2479 PRE_MEM_READ( "setgroups16(list)", ARG2, ARG1 * sizeof(vki_old_gid_t) );
2482 /* ---------------------------------------------------------------------
2483 *chown16 wrappers
2484 ------------------------------------------------------------------ */
2486 PRE(sys_chown16)
2488 PRINT("sys_chown16 ( %#lx, 0x%lx, 0x%lx )", ARG1,ARG2,ARG3);
2489 PRE_REG_READ3(long, "chown16",
2490 const char *, path,
2491 vki_old_uid_t, owner, vki_old_gid_t, group);
2492 PRE_MEM_RASCIIZ( "chown16(path)", ARG1 );
2495 PRE(sys_fchown16)
2497 PRINT("sys_fchown16 ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
2498 PRE_REG_READ3(long, "fchown16",
2499 unsigned int, fd, vki_old_uid_t, owner, vki_old_gid_t, group);
2502 /* ---------------------------------------------------------------------
2503 *xattr wrappers
2504 ------------------------------------------------------------------ */
2506 PRE(sys_setxattr)
2508 *flags |= SfMayBlock;
2509 PRINT("sys_setxattr ( %#lx, %#lx, %#lx, %llu, %ld )",
2510 ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
2511 PRE_REG_READ5(long, "setxattr",
2512 char *, path, char *, name,
2513 void *, value, vki_size_t, size, int, flags);
2514 PRE_MEM_RASCIIZ( "setxattr(path)", ARG1 );
2515 PRE_MEM_RASCIIZ( "setxattr(name)", ARG2 );
2516 PRE_MEM_READ( "setxattr(value)", ARG3, ARG4 );
2519 PRE(sys_lsetxattr)
2521 *flags |= SfMayBlock;
2522 PRINT("sys_lsetxattr ( %#lx, %#lx, %#lx, %llu, %ld )",
2523 ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
2524 PRE_REG_READ5(long, "lsetxattr",
2525 char *, path, char *, name,
2526 void *, value, vki_size_t, size, int, flags);
2527 PRE_MEM_RASCIIZ( "lsetxattr(path)", ARG1 );
2528 PRE_MEM_RASCIIZ( "lsetxattr(name)", ARG2 );
2529 PRE_MEM_READ( "lsetxattr(value)", ARG3, ARG4 );
2532 PRE(sys_fsetxattr)
2534 *flags |= SfMayBlock;
2535 PRINT("sys_fsetxattr ( %ld, %#lx, %#lx, %llu, %ld )",
2536 ARG1, ARG2, ARG3, (ULong)ARG4, ARG5);
2537 PRE_REG_READ5(long, "fsetxattr",
2538 int, fd, char *, name, void *, value,
2539 vki_size_t, size, int, flags);
2540 PRE_MEM_RASCIIZ( "fsetxattr(name)", ARG2 );
2541 PRE_MEM_READ( "fsetxattr(value)", ARG3, ARG4 );
2544 PRE(sys_getxattr)
2546 *flags |= SfMayBlock;
2547 PRINT("sys_getxattr ( %#lx, %#lx, %#lx, %llu )", ARG1,ARG2,ARG3, (ULong)ARG4);
2548 PRE_REG_READ4(ssize_t, "getxattr",
2549 char *, path, char *, name, void *, value, vki_size_t, size);
2550 PRE_MEM_RASCIIZ( "getxattr(path)", ARG1 );
2551 PRE_MEM_RASCIIZ( "getxattr(name)", ARG2 );
2552 PRE_MEM_WRITE( "getxattr(value)", ARG3, ARG4 );
2554 POST(sys_getxattr)
2556 vg_assert(SUCCESS);
2557 if (RES > 0 && ARG3 != (Addr)NULL) {
2558 POST_MEM_WRITE( ARG3, RES );
2562 PRE(sys_lgetxattr)
2564 *flags |= SfMayBlock;
2565 PRINT("sys_lgetxattr ( %#lx, %#lx, %#lx, %llu )", ARG1,ARG2,ARG3, (ULong)ARG4);
2566 PRE_REG_READ4(ssize_t, "lgetxattr",
2567 char *, path, char *, name, void *, value, vki_size_t, size);
2568 PRE_MEM_RASCIIZ( "lgetxattr(path)", ARG1 );
2569 PRE_MEM_RASCIIZ( "lgetxattr(name)", ARG2 );
2570 PRE_MEM_WRITE( "lgetxattr(value)", ARG3, ARG4 );
2572 POST(sys_lgetxattr)
2574 vg_assert(SUCCESS);
2575 if (RES > 0 && ARG3 != (Addr)NULL) {
2576 POST_MEM_WRITE( ARG3, RES );
2580 PRE(sys_fgetxattr)
2582 *flags |= SfMayBlock;
2583 PRINT("sys_fgetxattr ( %ld, %#lx, %#lx, %llu )", ARG1, ARG2, ARG3, (ULong)ARG4);
2584 PRE_REG_READ4(ssize_t, "fgetxattr",
2585 int, fd, char *, name, void *, value, vki_size_t, size);
2586 PRE_MEM_RASCIIZ( "fgetxattr(name)", ARG2 );
2587 PRE_MEM_WRITE( "fgetxattr(value)", ARG3, ARG4 );
2589 POST(sys_fgetxattr)
2591 if (RES > 0 && ARG3 != (Addr)NULL)
2592 POST_MEM_WRITE( ARG3, RES );
2595 PRE(sys_listxattr)
2597 *flags |= SfMayBlock;
2598 PRINT("sys_listxattr ( %#lx, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
2599 PRE_REG_READ3(ssize_t, "listxattr",
2600 char *, path, char *, list, vki_size_t, size);
2601 PRE_MEM_RASCIIZ( "listxattr(path)", ARG1 );
2602 PRE_MEM_WRITE( "listxattr(list)", ARG2, ARG3 );
2604 POST(sys_listxattr)
2606 if (RES > 0 && ARG2 != (Addr)NULL)
2607 POST_MEM_WRITE( ARG2, RES );
2610 PRE(sys_llistxattr)
2612 *flags |= SfMayBlock;
2613 PRINT("sys_llistxattr ( %#lx, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
2614 PRE_REG_READ3(ssize_t, "llistxattr",
2615 char *, path, char *, list, vki_size_t, size);
2616 PRE_MEM_RASCIIZ( "llistxattr(path)", ARG1 );
2617 PRE_MEM_WRITE( "llistxattr(list)", ARG2, ARG3 );
2619 POST(sys_llistxattr)
2621 if (RES > 0 && ARG2 != (Addr)NULL)
2622 POST_MEM_WRITE( ARG2, RES );
2625 PRE(sys_flistxattr)
2627 *flags |= SfMayBlock;
2628 PRINT("sys_flistxattr ( %ld, %#lx, %llu )", ARG1, ARG2, (ULong)ARG3);
2629 PRE_REG_READ3(ssize_t, "flistxattr",
2630 int, fd, char *, list, vki_size_t, size);
2631 PRE_MEM_WRITE( "flistxattr(list)", ARG2, ARG3 );
2633 POST(sys_flistxattr)
2635 if (RES > 0 && ARG2 != (Addr)NULL)
2636 POST_MEM_WRITE( ARG2, RES );
2639 PRE(sys_removexattr)
2641 *flags |= SfMayBlock;
2642 PRINT("sys_removexattr ( %#lx, %#lx )", ARG1, ARG2);
2643 PRE_REG_READ2(long, "removexattr", char *, path, char *, name);
2644 PRE_MEM_RASCIIZ( "removexattr(path)", ARG1 );
2645 PRE_MEM_RASCIIZ( "removexattr(name)", ARG2 );
2648 PRE(sys_lremovexattr)
2650 *flags |= SfMayBlock;
2651 PRINT("sys_lremovexattr ( %#lx, %#lx )", ARG1, ARG2);
2652 PRE_REG_READ2(long, "lremovexattr", char *, path, char *, name);
2653 PRE_MEM_RASCIIZ( "lremovexattr(path)", ARG1 );
2654 PRE_MEM_RASCIIZ( "lremovexattr(name)", ARG2 );
2657 PRE(sys_fremovexattr)
2659 *flags |= SfMayBlock;
2660 PRINT("sys_fremovexattr ( %ld, %#lx )", ARG1, ARG2);
2661 PRE_REG_READ2(long, "fremovexattr", int, fd, char *, name);
2662 PRE_MEM_RASCIIZ( "fremovexattr(name)", ARG2 );
2665 /* ---------------------------------------------------------------------
2666 sched_* wrappers
2667 ------------------------------------------------------------------ */
2669 PRE(sys_sched_setparam)
2671 PRINT("sched_setparam ( %ld, %#lx )", ARG1, ARG2 );
2672 PRE_REG_READ2(long, "sched_setparam",
2673 vki_pid_t, pid, struct sched_param *, p);
2674 PRE_MEM_READ( "sched_setparam(p)", ARG2, sizeof(struct vki_sched_param) );
2676 POST(sys_sched_setparam)
2678 POST_MEM_WRITE( ARG2, sizeof(struct vki_sched_param) );
2681 PRE(sys_sched_getparam)
2683 PRINT("sched_getparam ( %ld, %#lx )", ARG1, ARG2 );
2684 PRE_REG_READ2(long, "sched_getparam",
2685 vki_pid_t, pid, struct sched_param *, p);
2686 PRE_MEM_WRITE( "sched_getparam(p)", ARG2, sizeof(struct vki_sched_param) );
2688 POST(sys_sched_getparam)
2690 POST_MEM_WRITE( ARG2, sizeof(struct vki_sched_param) );
2693 PRE(sys_sched_getscheduler)
2695 PRINT("sys_sched_getscheduler ( %ld )", ARG1);
2696 PRE_REG_READ1(long, "sched_getscheduler", vki_pid_t, pid);
2699 PRE(sys_sched_setscheduler)
2701 PRINT("sys_sched_setscheduler ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
2702 PRE_REG_READ3(long, "sched_setscheduler",
2703 vki_pid_t, pid, int, policy, struct sched_param *, p);
2704 if (ARG3 != 0)
2705 PRE_MEM_READ( "sched_setscheduler(p)",
2706 ARG3, sizeof(struct vki_sched_param));
2709 PRE(sys_sched_yield)
2711 *flags |= SfMayBlock;
2712 PRINT("sched_yield()");
2713 PRE_REG_READ0(long, "sys_sched_yield");
2716 PRE(sys_sched_get_priority_max)
2718 PRINT("sched_get_priority_max ( %ld )", ARG1);
2719 PRE_REG_READ1(long, "sched_get_priority_max", int, policy);
2722 PRE(sys_sched_get_priority_min)
2724 PRINT("sched_get_priority_min ( %ld )", ARG1);
2725 PRE_REG_READ1(long, "sched_get_priority_min", int, policy);
2728 PRE(sys_sched_rr_get_interval)
2730 PRINT("sys_sched_rr_get_interval ( %ld, %#lx )", ARG1, ARG2);
2731 PRE_REG_READ2(int, "sched_rr_get_interval",
2732 vki_pid_t, pid,
2733 struct vki_timespec *, tp);
2734 PRE_MEM_WRITE("sched_rr_get_interval(timespec)",
2735 ARG2, sizeof(struct vki_timespec));
2738 POST(sys_sched_rr_get_interval)
2740 POST_MEM_WRITE(ARG2, sizeof(struct vki_timespec));
2743 PRE(sys_sched_setaffinity)
2745 PRINT("sched_setaffinity ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
2746 PRE_REG_READ3(long, "sched_setaffinity",
2747 vki_pid_t, pid, unsigned int, len, unsigned long *, mask);
2748 PRE_MEM_READ( "sched_setaffinity(mask)", ARG3, ARG2);
2751 PRE(sys_sched_getaffinity)
2753 PRINT("sched_getaffinity ( %ld, %ld, %#lx )", ARG1, ARG2, ARG3);
2754 PRE_REG_READ3(long, "sched_getaffinity",
2755 vki_pid_t, pid, unsigned int, len, unsigned long *, mask);
2756 PRE_MEM_WRITE( "sched_getaffinity(mask)", ARG3, ARG2);
2758 POST(sys_sched_getaffinity)
2760 POST_MEM_WRITE(ARG3, ARG2);
2763 PRE(sys_unshare)
2765 PRINT("sys_unshare ( %ld )", ARG1);
2766 PRE_REG_READ1(int, "unshare", int, flags);
2769 /* ---------------------------------------------------------------------
2770 miscellaneous wrappers
2771 ------------------------------------------------------------------ */
2773 PRE(sys_munlockall)
2775 *flags |= SfMayBlock;
2776 PRINT("sys_munlockall ( )");
2777 PRE_REG_READ0(long, "munlockall");
2780 // This has different signatures for different platforms.
2782 // x86: int sys_pipe(unsigned long __user *fildes);
2783 // AMD64: long sys_pipe(int *fildes);
2784 // ppc32: int sys_pipe(int __user *fildes);
2785 // ppc64: int sys_pipe(int __user *fildes);
2787 // The type of the argument is most important, and it is an array of 32 bit
2788 // values in all cases. (The return type differs across platforms, but it
2789 // is not used.) So we use 'int' as its type. This fixed bug #113230 which
2790 // was caused by using an array of 'unsigned long's, which didn't work on
2791 // AMD64.
2792 PRE(sys_pipe)
2794 PRINT("sys_pipe ( %#lx )", ARG1);
2795 PRE_REG_READ1(int, "pipe", int *, filedes);
2796 PRE_MEM_WRITE( "pipe(filedes)", ARG1, 2*sizeof(int) );
2798 POST(sys_pipe)
2800 Int *p = (Int *)ARG1;
2801 if (!ML_(fd_allowed)(p[0], "pipe", tid, True) ||
2802 !ML_(fd_allowed)(p[1], "pipe", tid, True)) {
2803 VG_(close)(p[0]);
2804 VG_(close)(p[1]);
2805 SET_STATUS_Failure( VKI_EMFILE );
2806 } else {
2807 POST_MEM_WRITE( ARG1, 2*sizeof(int) );
2808 if (VG_(clo_track_fds)) {
2809 ML_(record_fd_open_nameless)(tid, p[0]);
2810 ML_(record_fd_open_nameless)(tid, p[1]);
2815 /* pipe2 (a kernel 2.6.twentysomething invention) is like pipe, except
2816 there's a second arg containing flags to be applied to the new file
2817 descriptors. It hardly seems worth the effort to factor out the
2818 duplicated code, hence: */
2819 PRE(sys_pipe2)
2821 PRINT("sys_pipe2 ( %#lx, %#lx )", ARG1, ARG2);
2822 PRE_REG_READ2(int, "pipe", int *, filedes, long, flags);
2823 PRE_MEM_WRITE( "pipe2(filedes)", ARG1, 2*sizeof(int) );
2825 POST(sys_pipe2)
2827 Int *p = (Int *)ARG1;
2828 if (!ML_(fd_allowed)(p[0], "pipe2", tid, True) ||
2829 !ML_(fd_allowed)(p[1], "pipe2", tid, True)) {
2830 VG_(close)(p[0]);
2831 VG_(close)(p[1]);
2832 SET_STATUS_Failure( VKI_EMFILE );
2833 } else {
2834 POST_MEM_WRITE( ARG1, 2*sizeof(int) );
2835 if (VG_(clo_track_fds)) {
2836 ML_(record_fd_open_nameless)(tid, p[0]);
2837 ML_(record_fd_open_nameless)(tid, p[1]);
2842 PRE(sys_dup3)
2844 PRINT("sys_dup3 ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
2845 PRE_REG_READ3(long, "dup3", unsigned int, oldfd, unsigned int, newfd, int, flags);
2846 if (!ML_(fd_allowed)(ARG2, "dup3", tid, True))
2847 SET_STATUS_Failure( VKI_EBADF );
2850 POST(sys_dup3)
2852 vg_assert(SUCCESS);
2853 if (VG_(clo_track_fds))
2854 ML_(record_fd_open_named)(tid, RES);
2857 PRE(sys_quotactl)
2859 PRINT("sys_quotactl (0x%lx, %#lx, 0x%lx, 0x%lx )", ARG1,ARG2,ARG3, ARG4);
2860 PRE_REG_READ4(long, "quotactl",
2861 unsigned int, cmd, const char *, special, vki_qid_t, id,
2862 void *, addr);
2863 PRE_MEM_RASCIIZ( "quotactl(special)", ARG2 );
2866 PRE(sys_waitid)
2868 *flags |= SfMayBlock;
2869 PRINT("sys_waitid( %ld, %ld, %#lx, %ld, %#lx )", ARG1,ARG2,ARG3,ARG4,ARG5);
2870 PRE_REG_READ5(int32_t, "sys_waitid",
2871 int, which, vki_pid_t, pid, struct vki_siginfo *, infop,
2872 int, options, struct vki_rusage *, ru);
2873 PRE_MEM_WRITE( "waitid(infop)", ARG3, sizeof(struct vki_siginfo) );
2874 if (ARG5 != 0)
2875 PRE_MEM_WRITE( "waitid(ru)", ARG5, sizeof(struct vki_rusage) );
2877 POST(sys_waitid)
2879 POST_MEM_WRITE( ARG3, sizeof(struct vki_siginfo) );
2880 if (ARG5 != 0)
2881 POST_MEM_WRITE( ARG5, sizeof(struct vki_rusage) );
2884 PRE(sys_sync_file_range)
2886 *flags |= SfMayBlock;
2887 #if VG_WORDSIZE == 4
2888 PRINT("sys_sync_file_range ( %ld, %lld, %lld, %ld )",
2889 ARG1,MERGE64(ARG2,ARG3),MERGE64(ARG4,ARG5),ARG6);
2890 PRE_REG_READ6(long, "sync_file_range",
2891 int, fd,
2892 unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
2893 unsigned, MERGE64_FIRST(nbytes), unsigned, MERGE64_SECOND(nbytes),
2894 unsigned int, flags);
2895 #elif VG_WORDSIZE == 8
2896 PRINT("sys_sync_file_range ( %ld, %lld, %lld, %ld )",
2897 ARG1,(Long)ARG2,(Long)ARG3,ARG4);
2898 PRE_REG_READ4(long, "sync_file_range",
2899 int, fd, vki_loff_t, offset, vki_loff_t, nbytes,
2900 unsigned int, flags);
2901 #else
2902 # error Unexpected word size
2903 #endif
2904 if (!ML_(fd_allowed)(ARG1, "sync_file_range", tid, False))
2905 SET_STATUS_Failure( VKI_EBADF );
2908 PRE(sys_sync_file_range2)
2910 *flags |= SfMayBlock;
2911 #if VG_WORDSIZE == 4
2912 PRINT("sys_sync_file_range2 ( %ld, %ld, %lld, %lld )",
2913 ARG1,ARG2,MERGE64(ARG3,ARG4),MERGE64(ARG5,ARG6));
2914 PRE_REG_READ6(long, "sync_file_range2",
2915 int, fd, unsigned int, flags,
2916 unsigned, MERGE64_FIRST(offset), unsigned, MERGE64_SECOND(offset),
2917 unsigned, MERGE64_FIRST(nbytes), unsigned, MERGE64_SECOND(nbytes));
2918 #elif VG_WORDSIZE == 8
2919 PRINT("sys_sync_file_range2 ( %ld, %ld, %lld, %lld )",
2920 ARG1,ARG2,(Long)ARG3,(Long)ARG4);
2921 PRE_REG_READ4(long, "sync_file_range2",
2922 int, fd, unsigned int, flags,
2923 vki_loff_t, offset, vki_loff_t, nbytes);
2924 #else
2925 # error Unexpected word size
2926 #endif
2927 if (!ML_(fd_allowed)(ARG1, "sync_file_range2", tid, False))
2928 SET_STATUS_Failure( VKI_EBADF );
2931 PRE(sys_stime)
2933 PRINT("sys_stime ( %#lx )", ARG1);
2934 PRE_REG_READ1(int, "stime", vki_time_t*, t);
2935 PRE_MEM_READ( "stime(t)", ARG1, sizeof(vki_time_t) );
2938 PRE(sys_perf_event_open)
2940 struct vki_perf_event_attr *attr;
2941 PRINT("sys_perf_event_open ( %#lx, %ld, %ld, %ld, %ld )",
2942 ARG1,ARG2,ARG3,ARG4,ARG5);
2943 PRE_REG_READ5(long, "perf_event_open",
2944 struct vki_perf_event_attr *, attr,
2945 vki_pid_t, pid, int, cpu, int, group_fd,
2946 unsigned long, flags);
2947 attr = (struct vki_perf_event_attr *)ARG1;
2948 PRE_MEM_READ( "perf_event_open(attr->size)",
2949 (Addr)&attr->size, sizeof(attr->size) );
2950 PRE_MEM_READ( "perf_event_open(attr)",
2951 (Addr)attr, attr->size );
2954 POST(sys_perf_event_open)
2956 vg_assert(SUCCESS);
2957 if (!ML_(fd_allowed)(RES, "perf_event_open", tid, True)) {
2958 VG_(close)(RES);
2959 SET_STATUS_Failure( VKI_EMFILE );
2960 } else {
2961 if (VG_(clo_track_fds))
2962 ML_(record_fd_open_nameless)(tid, RES);
2966 PRE(sys_getcpu)
2968 PRINT("sys_getcpu ( %#lx, %#lx, %#lx )" , ARG1,ARG2,ARG3);
2969 PRE_REG_READ3(int, "getcpu",
2970 unsigned *, cpu, unsigned *, node, struct vki_getcpu_cache *, tcache);
2971 if (ARG1 != 0)
2972 PRE_MEM_WRITE( "getcpu(cpu)", ARG1, sizeof(unsigned) );
2973 if (ARG2 != 0)
2974 PRE_MEM_WRITE( "getcpu(node)", ARG2, sizeof(unsigned) );
2975 if (ARG3 != 0)
2976 PRE_MEM_WRITE( "getcpu(tcache)", ARG3, sizeof(struct vki_getcpu_cache) );
2979 POST(sys_getcpu)
2981 if (ARG1 != 0)
2982 POST_MEM_WRITE( ARG1, sizeof(unsigned) );
2983 if (ARG2 != 0)
2984 POST_MEM_WRITE( ARG2, sizeof(unsigned) );
2985 if (ARG3 != 0)
2986 POST_MEM_WRITE( ARG3, sizeof(struct vki_getcpu_cache) );
2989 PRE(sys_move_pages)
2991 PRINT("sys_move_pages ( %ld, %ld, %#lx, %#lx, %#lx, %lx )",
2992 ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
2993 PRE_REG_READ6(int, "move_pages",
2994 vki_pid_t, pid, unsigned long, nr_pages, const void **, pages,
2995 const int *, nodes, int *, status, int, flags);
2996 PRE_MEM_READ("move_pages(pages)", ARG3, ARG2 * sizeof(void *));
2997 if (ARG4)
2998 PRE_MEM_READ("move_pages(nodes)", ARG4, ARG2 * sizeof(int));
2999 PRE_MEM_WRITE("move_pages(status)", ARG5, ARG2 * sizeof(int));
3002 POST(sys_move_pages)
3004 POST_MEM_WRITE(ARG5, ARG2 * sizeof(int));
3007 PRE(sys_getrandom)
3009 PRINT("sys_getrandom ( %#lx, %ld, %ld )" , ARG1,ARG2,ARG3);
3010 PRE_REG_READ3(int, "getrandom",
3011 char *, buf, vki_size_t, count, unsigned int, flags);
3012 PRE_MEM_WRITE( "getrandom(cpu)", ARG1, ARG2 );
3015 POST(sys_getrandom)
3017 POST_MEM_WRITE( ARG1, ARG2 );
3020 /* ---------------------------------------------------------------------
3021 utime wrapper
3022 ------------------------------------------------------------------ */
3024 PRE(sys_utime)
3026 *flags |= SfMayBlock;
3027 PRINT("sys_utime ( %#lx, %#lx )", ARG1,ARG2);
3028 PRE_REG_READ2(long, "utime", char *, filename, struct utimbuf *, buf);
3029 PRE_MEM_RASCIIZ( "utime(filename)", ARG1 );
3030 if (ARG2 != 0)
3031 PRE_MEM_READ( "utime(buf)", ARG2, sizeof(struct vki_utimbuf) );
3034 /* ---------------------------------------------------------------------
3035 lseek wrapper
3036 ------------------------------------------------------------------ */
3038 PRE(sys_lseek)
3040 PRINT("sys_lseek ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
3041 PRE_REG_READ3(vki_off_t, "lseek",
3042 unsigned int, fd, vki_off_t, offset, unsigned int, whence);
3045 /* ---------------------------------------------------------------------
3046 readahead wrapper
3047 ------------------------------------------------------------------ */
3049 PRE(sys_readahead)
3051 *flags |= SfMayBlock;
3052 #if VG_WORDSIZE == 4
3053 PRINT("sys_readahead ( %ld, %lld, %ld )", ARG1, MERGE64(ARG2,ARG3), ARG4);
3054 PRE_REG_READ4(vki_off_t, "readahead",
3055 int, fd, unsigned, MERGE64_FIRST(offset),
3056 unsigned, MERGE64_SECOND(offset), vki_size_t, count);
3057 #elif VG_WORDSIZE == 8
3058 PRINT("sys_readahead ( %ld, %lld, %ld )", ARG1, (Long)ARG2, ARG3);
3059 PRE_REG_READ3(vki_off_t, "readahead",
3060 int, fd, vki_loff_t, offset, vki_size_t, count);
3061 #else
3062 # error Unexpected word size
3063 #endif
3064 if (!ML_(fd_allowed)(ARG1, "readahead", tid, False))
3065 SET_STATUS_Failure( VKI_EBADF );
3068 /* ---------------------------------------------------------------------
3069 sig* wrappers
3070 ------------------------------------------------------------------ */
3072 PRE(sys_sigpending)
3074 PRINT( "sys_sigpending ( %#lx )", ARG1 );
3075 PRE_REG_READ1(long, "sigpending", vki_old_sigset_t *, set);
3076 PRE_MEM_WRITE( "sigpending(set)", ARG1, sizeof(vki_old_sigset_t));
3078 POST(sys_sigpending)
3080 POST_MEM_WRITE( ARG1, sizeof(vki_old_sigset_t) ) ;
3083 // This syscall is not used on amd64/Linux -- it only provides
3084 // sys_rt_sigprocmask, which uses sigset_t rather than old_sigset_t.
3085 // This wrapper is only suitable for 32-bit architectures.
3086 // (XXX: so how is it that PRE(sys_sigpending) above doesn't need
3087 // conditional compilation like this?)
3088 #if defined(VGP_x86_linux) || defined(VGP_ppc32_linux) \
3089 || defined(VGP_arm_linux) || defined(VGP_mips32_linux)
3090 PRE(sys_sigprocmask)
3092 vki_old_sigset_t* set;
3093 vki_old_sigset_t* oldset;
3094 vki_sigset_t bigger_set;
3095 vki_sigset_t bigger_oldset;
3097 PRINT("sys_sigprocmask ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
3098 PRE_REG_READ3(long, "sigprocmask",
3099 int, how, vki_old_sigset_t *, set, vki_old_sigset_t *, oldset);
3100 if (ARG2 != 0)
3101 PRE_MEM_READ( "sigprocmask(set)", ARG2, sizeof(vki_old_sigset_t));
3102 if (ARG3 != 0)
3103 PRE_MEM_WRITE( "sigprocmask(oldset)", ARG3, sizeof(vki_old_sigset_t));
3105 // Nb: We must convert the smaller vki_old_sigset_t params into bigger
3106 // vki_sigset_t params.
3107 set = (vki_old_sigset_t*)ARG2;
3108 oldset = (vki_old_sigset_t*)ARG3;
3110 VG_(memset)(&bigger_set, 0, sizeof(vki_sigset_t));
3111 VG_(memset)(&bigger_oldset, 0, sizeof(vki_sigset_t));
3112 if (set)
3113 bigger_set.sig[0] = *(vki_old_sigset_t*)set;
3115 SET_STATUS_from_SysRes(
3116 VG_(do_sys_sigprocmask) ( tid, ARG1 /*how*/,
3117 set ? &bigger_set : NULL,
3118 oldset ? &bigger_oldset : NULL)
3121 if (oldset)
3122 *oldset = bigger_oldset.sig[0];
3124 if (SUCCESS)
3125 *flags |= SfPollAfter;
3127 POST(sys_sigprocmask)
3129 vg_assert(SUCCESS);
3130 if (RES == 0 && ARG3 != 0)
3131 POST_MEM_WRITE( ARG3, sizeof(vki_old_sigset_t));
3134 /* Convert from non-RT to RT sigset_t's */
3135 static
3136 void convert_sigset_to_rt(const vki_old_sigset_t *oldset, vki_sigset_t *set)
3138 VG_(sigemptyset)(set);
3139 set->sig[0] = *oldset;
3141 PRE(sys_sigaction)
3143 vki_sigaction_toK_t new, *newp;
3144 vki_sigaction_fromK_t old, *oldp;
3146 PRINT("sys_sigaction ( %ld, %#lx, %#lx )", ARG1,ARG2,ARG3);
3147 PRE_REG_READ3(int, "sigaction",
3148 int, signum, const struct old_sigaction *, act,
3149 struct old_sigaction *, oldact);
3151 newp = oldp = NULL;
3153 if (ARG2 != 0) {
3154 struct vki_old_sigaction *sa = (struct vki_old_sigaction *)ARG2;
3155 PRE_MEM_READ( "sigaction(act->sa_handler)", (Addr)&sa->ksa_handler, sizeof(sa->ksa_handler));
3156 PRE_MEM_READ( "sigaction(act->sa_mask)", (Addr)&sa->sa_mask, sizeof(sa->sa_mask));
3157 PRE_MEM_READ( "sigaction(act->sa_flags)", (Addr)&sa->sa_flags, sizeof(sa->sa_flags));
3158 if (ML_(safe_to_deref)(sa,sizeof(sa))
3159 && (sa->sa_flags & VKI_SA_RESTORER))
3160 PRE_MEM_READ( "sigaction(act->sa_restorer)", (Addr)&sa->sa_restorer, sizeof(sa->sa_restorer));
3163 if (ARG3 != 0) {
3164 PRE_MEM_WRITE( "sigaction(oldact)", ARG3, sizeof(struct vki_old_sigaction));
3165 oldp = &old;
3168 if (ARG2 != 0) {
3169 struct vki_old_sigaction *oldnew = (struct vki_old_sigaction *)ARG2;
3171 new.ksa_handler = oldnew->ksa_handler;
3172 new.sa_flags = oldnew->sa_flags;
3173 new.sa_restorer = oldnew->sa_restorer;
3174 convert_sigset_to_rt(&oldnew->sa_mask, &new.sa_mask);
3175 newp = &new;
3178 SET_STATUS_from_SysRes( VG_(do_sys_sigaction)(ARG1, newp, oldp) );
3180 if (ARG3 != 0 && SUCCESS && RES == 0) {
3181 struct vki_old_sigaction *oldold = (struct vki_old_sigaction *)ARG3;
3183 oldold->ksa_handler = oldp->ksa_handler;
3184 oldold->sa_flags = oldp->sa_flags;
3185 oldold->sa_restorer = oldp->sa_restorer;
3186 oldold->sa_mask = oldp->sa_mask.sig[0];
3189 POST(sys_sigaction)
3191 vg_assert(SUCCESS);
3192 if (RES == 0 && ARG3 != 0)
3193 POST_MEM_WRITE( ARG3, sizeof(struct vki_old_sigaction));
3195 #endif
3197 PRE(sys_signalfd)
3199 PRINT("sys_signalfd ( %d, %#lx, %llu )", (Int)ARG1,ARG2,(ULong)ARG3);
3200 PRE_REG_READ3(long, "sys_signalfd",
3201 int, fd, vki_sigset_t *, sigmask, vki_size_t, sigsetsize);
3202 PRE_MEM_READ( "signalfd(sigmask)", ARG2, sizeof(vki_sigset_t) );
3203 if ((int)ARG1 != -1 && !ML_(fd_allowed)(ARG1, "signalfd", tid, False))
3204 SET_STATUS_Failure( VKI_EBADF );
3206 POST(sys_signalfd)
3208 if (!ML_(fd_allowed)(RES, "signalfd", tid, True)) {
3209 VG_(close)(RES);
3210 SET_STATUS_Failure( VKI_EMFILE );
3211 } else {
3212 if (VG_(clo_track_fds))
3213 ML_(record_fd_open_nameless) (tid, RES);
3217 PRE(sys_signalfd4)
3219 PRINT("sys_signalfd4 ( %d, %#lx, %llu, %ld )", (Int)ARG1,ARG2,(ULong)ARG3,ARG4);
3220 PRE_REG_READ4(long, "sys_signalfd4",
3221 int, fd, vki_sigset_t *, sigmask, vki_size_t, sigsetsize, int, flags);
3222 PRE_MEM_READ( "signalfd(sigmask)", ARG2, sizeof(vki_sigset_t) );
3223 if ((int)ARG1 != -1 && !ML_(fd_allowed)(ARG1, "signalfd", tid, False))
3224 SET_STATUS_Failure( VKI_EBADF );
3226 POST(sys_signalfd4)
3228 if (!ML_(fd_allowed)(RES, "signalfd4", tid, True)) {
3229 VG_(close)(RES);
3230 SET_STATUS_Failure( VKI_EMFILE );
3231 } else {
3232 if (VG_(clo_track_fds))
3233 ML_(record_fd_open_nameless) (tid, RES);
3238 /* ---------------------------------------------------------------------
3239 rt_sig* wrappers
3240 ------------------------------------------------------------------ */
3242 PRE(sys_rt_sigaction)
3244 PRINT("sys_rt_sigaction ( %ld, %#lx, %#lx, %ld )", ARG1,ARG2,ARG3,ARG4);
3245 PRE_REG_READ4(long, "rt_sigaction",
3246 int, signum, const struct sigaction *, act,
3247 struct sigaction *, oldact, vki_size_t, sigsetsize);
3249 if (ARG2 != 0) {
3250 vki_sigaction_toK_t *sa = (vki_sigaction_toK_t *)ARG2;
3251 PRE_MEM_READ( "rt_sigaction(act->sa_handler)", (Addr)&sa->ksa_handler, sizeof(sa->ksa_handler));
3252 PRE_MEM_READ( "rt_sigaction(act->sa_mask)", (Addr)&sa->sa_mask, sizeof(sa->sa_mask));
3253 PRE_MEM_READ( "rt_sigaction(act->sa_flags)", (Addr)&sa->sa_flags, sizeof(sa->sa_flags));
3254 if (sa->sa_flags & VKI_SA_RESTORER)
3255 PRE_MEM_READ( "rt_sigaction(act->sa_restorer)", (Addr)&sa->sa_restorer, sizeof(sa->sa_restorer));
3257 if (ARG3 != 0)
3258 PRE_MEM_WRITE( "rt_sigaction(oldact)", ARG3, sizeof(vki_sigaction_fromK_t));
3260 // XXX: doesn't seem right to be calling do_sys_sigaction for
3261 // sys_rt_sigaction... perhaps this function should be renamed
3262 // VG_(do_sys_rt_sigaction)() --njn
3264 SET_STATUS_from_SysRes(
3265 VG_(do_sys_sigaction)(ARG1, (const vki_sigaction_toK_t *)ARG2,
3266 (vki_sigaction_fromK_t *)ARG3)
3269 POST(sys_rt_sigaction)
3271 vg_assert(SUCCESS);
3272 if (RES == 0 && ARG3 != 0)
3273 POST_MEM_WRITE( ARG3, sizeof(vki_sigaction_fromK_t));
3276 PRE(sys_rt_sigprocmask)
3278 PRINT("sys_rt_sigprocmask ( %ld, %#lx, %#lx, %llu )",ARG1,ARG2,ARG3,(ULong)ARG4);
3279 PRE_REG_READ4(long, "rt_sigprocmask",
3280 int, how, vki_sigset_t *, set, vki_sigset_t *, oldset,
3281 vki_size_t, sigsetsize);
3282 if (ARG2 != 0)
3283 PRE_MEM_READ( "rt_sigprocmask(set)", ARG2, sizeof(vki_sigset_t));
3284 if (ARG3 != 0)
3285 PRE_MEM_WRITE( "rt_sigprocmask(oldset)", ARG3, sizeof(vki_sigset_t));
3287 // Like the kernel, we fail if the sigsetsize is not exactly what we expect.
3288 if (sizeof(vki_sigset_t) != ARG4)
3289 SET_STATUS_Failure( VKI_EMFILE );
3290 else {
3291 SET_STATUS_from_SysRes(
3292 VG_(do_sys_sigprocmask) ( tid, ARG1 /*how*/,
3293 (vki_sigset_t*) ARG2,
3294 (vki_sigset_t*) ARG3 )
3298 if (SUCCESS)
3299 *flags |= SfPollAfter;
3301 POST(sys_rt_sigprocmask)
3303 vg_assert(SUCCESS);
3304 if (RES == 0 && ARG3 != 0)
3305 POST_MEM_WRITE( ARG3, sizeof(vki_sigset_t));
3308 PRE(sys_rt_sigpending)
3310 PRINT( "sys_rt_sigpending ( %#lx )", ARG1 );
3311 PRE_REG_READ2(long, "rt_sigpending",
3312 vki_sigset_t *, set, vki_size_t, sigsetsize);
3313 PRE_MEM_WRITE( "rt_sigpending(set)", ARG1, sizeof(vki_sigset_t));
3315 POST(sys_rt_sigpending)
3317 POST_MEM_WRITE( ARG1, sizeof(vki_sigset_t) ) ;
3320 PRE(sys_rt_sigtimedwait)
3322 *flags |= SfMayBlock;
3323 PRINT("sys_rt_sigtimedwait ( %#lx, %#lx, %#lx, %lld )",
3324 ARG1,ARG2,ARG3,(ULong)ARG4);
3325 PRE_REG_READ4(long, "rt_sigtimedwait",
3326 const vki_sigset_t *, set, vki_siginfo_t *, info,
3327 const struct timespec *, timeout, vki_size_t, sigsetsize);
3328 if (ARG1 != 0)
3329 PRE_MEM_READ( "rt_sigtimedwait(set)", ARG1, sizeof(vki_sigset_t));
3330 if (ARG2 != 0)
3331 PRE_MEM_WRITE( "rt_sigtimedwait(info)", ARG2, sizeof(vki_siginfo_t) );
3332 if (ARG3 != 0)
3333 PRE_MEM_READ( "rt_sigtimedwait(timeout)",
3334 ARG3, sizeof(struct vki_timespec) );
3336 POST(sys_rt_sigtimedwait)
3338 if (ARG2 != 0)
3339 POST_MEM_WRITE( ARG2, sizeof(vki_siginfo_t) );
3342 PRE(sys_rt_sigqueueinfo)
3344 PRINT("sys_rt_sigqueueinfo(%ld, %ld, %#lx)", ARG1, ARG2, ARG3);
3345 PRE_REG_READ3(long, "rt_sigqueueinfo",
3346 int, pid, int, sig, vki_siginfo_t *, uinfo);
3347 if (ARG2 != 0)
3348 PRE_MEM_READ( "rt_sigqueueinfo(uinfo)", ARG3, VKI_SI_MAX_SIZE );
3350 POST(sys_rt_sigqueueinfo)
3352 if (!ML_(client_signal_OK)(ARG2))
3353 SET_STATUS_Failure( VKI_EINVAL );
3356 PRE(sys_rt_tgsigqueueinfo)
3358 PRINT("sys_rt_tgsigqueueinfo(%ld, %ld, %ld, %#lx)", ARG1, ARG2, ARG3, ARG4);
3359 PRE_REG_READ4(long, "rt_tgsigqueueinfo",
3360 int, tgid, int, pid, int, sig, vki_siginfo_t *, uinfo);
3361 if (ARG3 != 0)
3362 PRE_MEM_READ( "rt_tgsigqueueinfo(uinfo)", ARG4, VKI_SI_MAX_SIZE );
3365 POST(sys_rt_tgsigqueueinfo)
3367 if (!ML_(client_signal_OK)(ARG3))
3368 SET_STATUS_Failure( VKI_EINVAL );
3371 // XXX: x86-specific? The kernel prototypes for the different archs are
3372 // hard to decipher.
3373 PRE(sys_rt_sigsuspend)
3375 /* The C library interface to sigsuspend just takes a pointer to
3376 a signal mask but this system call has two arguments - a pointer
3377 to the mask and the number of bytes used by it. The kernel insists
3378 on the size being equal to sizeof(sigset_t) however and will just
3379 return EINVAL if it isn't.
3381 *flags |= SfMayBlock;
3382 PRINT("sys_rt_sigsuspend ( %#lx, %ld )", ARG1,ARG2 );
3383 PRE_REG_READ2(int, "rt_sigsuspend", vki_sigset_t *, mask, vki_size_t, size)
3384 if (ARG1 != (Addr)NULL) {
3385 PRE_MEM_READ( "rt_sigsuspend(mask)", ARG1, sizeof(vki_sigset_t) );
3389 /* ---------------------------------------------------------------------
3390 linux msg* wrapper helpers
3391 ------------------------------------------------------------------ */
3393 void
3394 ML_(linux_PRE_sys_msgsnd) ( ThreadId tid,
3395 UWord arg0, UWord arg1, UWord arg2, UWord arg3 )
3397 /* int msgsnd(int msqid, struct msgbuf *msgp, size_t msgsz, int msgflg); */
3398 struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
3399 PRE_MEM_READ( "msgsnd(msgp->mtype)", (Addr)&msgp->mtype, sizeof(msgp->mtype) );
3400 PRE_MEM_READ( "msgsnd(msgp->mtext)", (Addr)&msgp->mtext, arg2 );
3403 void
3404 ML_(linux_PRE_sys_msgrcv) ( ThreadId tid,
3405 UWord arg0, UWord arg1, UWord arg2,
3406 UWord arg3, UWord arg4 )
3408 /* ssize_t msgrcv(int msqid, struct msgbuf *msgp, size_t msgsz,
3409 long msgtyp, int msgflg); */
3410 struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
3411 PRE_MEM_WRITE( "msgrcv(msgp->mtype)", (Addr)&msgp->mtype, sizeof(msgp->mtype) );
3412 PRE_MEM_WRITE( "msgrcv(msgp->mtext)", (Addr)&msgp->mtext, arg2 );
3414 void
3415 ML_(linux_POST_sys_msgrcv) ( ThreadId tid,
3416 UWord res,
3417 UWord arg0, UWord arg1, UWord arg2,
3418 UWord arg3, UWord arg4 )
3420 struct vki_msgbuf *msgp = (struct vki_msgbuf *)arg1;
3421 POST_MEM_WRITE( (Addr)&msgp->mtype, sizeof(msgp->mtype) );
3422 POST_MEM_WRITE( (Addr)&msgp->mtext, res );
3425 void
3426 ML_(linux_PRE_sys_msgctl) ( ThreadId tid,
3427 UWord arg0, UWord arg1, UWord arg2 )
3429 /* int msgctl(int msqid, int cmd, struct msqid_ds *buf); */
3430 switch (arg1 /* cmd */) {
3431 case VKI_IPC_INFO:
3432 case VKI_MSG_INFO:
3433 case VKI_IPC_INFO|VKI_IPC_64:
3434 case VKI_MSG_INFO|VKI_IPC_64:
3435 PRE_MEM_WRITE( "msgctl(IPC_INFO, buf)",
3436 arg2, sizeof(struct vki_msginfo) );
3437 break;
3438 case VKI_IPC_STAT:
3439 case VKI_MSG_STAT:
3440 PRE_MEM_WRITE( "msgctl(IPC_STAT, buf)",
3441 arg2, sizeof(struct vki_msqid_ds) );
3442 break;
3443 case VKI_IPC_STAT|VKI_IPC_64:
3444 case VKI_MSG_STAT|VKI_IPC_64:
3445 PRE_MEM_WRITE( "msgctl(IPC_STAT, arg.buf)",
3446 arg2, sizeof(struct vki_msqid64_ds) );
3447 break;
3448 case VKI_IPC_SET:
3449 PRE_MEM_READ( "msgctl(IPC_SET, arg.buf)",
3450 arg2, sizeof(struct vki_msqid_ds) );
3451 break;
3452 case VKI_IPC_SET|VKI_IPC_64:
3453 PRE_MEM_READ( "msgctl(IPC_SET, arg.buf)",
3454 arg2, sizeof(struct vki_msqid64_ds) );
3455 break;
3458 void
3459 ML_(linux_POST_sys_msgctl) ( ThreadId tid,
3460 UWord res,
3461 UWord arg0, UWord arg1, UWord arg2 )
3463 switch (arg1 /* cmd */) {
3464 case VKI_IPC_INFO:
3465 case VKI_MSG_INFO:
3466 case VKI_IPC_INFO|VKI_IPC_64:
3467 case VKI_MSG_INFO|VKI_IPC_64:
3468 POST_MEM_WRITE( arg2, sizeof(struct vki_msginfo) );
3469 break;
3470 case VKI_IPC_STAT:
3471 case VKI_MSG_STAT:
3472 POST_MEM_WRITE( arg2, sizeof(struct vki_msqid_ds) );
3473 break;
3474 case VKI_IPC_STAT|VKI_IPC_64:
3475 case VKI_MSG_STAT|VKI_IPC_64:
3476 POST_MEM_WRITE( arg2, sizeof(struct vki_msqid64_ds) );
3477 break;
3481 /* ---------------------------------------------------------------------
3482 Generic handler for sys_ipc
3483 Depending on the platform, some syscalls (e.g. semctl, semop, ...)
3484 are either direct system calls, or are all implemented via sys_ipc.
3485 ------------------------------------------------------------------ */
3486 #ifdef __NR_ipc
3487 static Addr deref_Addr ( ThreadId tid, Addr a, const HChar* s )
3489 Addr* a_p = (Addr*)a;
3490 PRE_MEM_READ( s, (Addr)a_p, sizeof(Addr) );
3491 return *a_p;
3494 static Bool semctl_cmd_has_4args (UWord cmd)
3496 switch (cmd & ~VKI_IPC_64)
3498 case VKI_IPC_INFO:
3499 case VKI_SEM_INFO:
3500 case VKI_IPC_STAT:
3501 case VKI_SEM_STAT:
3502 case VKI_IPC_SET:
3503 case VKI_GETALL:
3504 case VKI_SETALL:
3505 return True;
3506 default:
3507 return False;
3511 PRE(sys_ipc)
3513 PRINT("sys_ipc ( %ld, %ld, %ld, %ld, %#lx, %ld )",
3514 ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
3516 switch (ARG1 /* call */) {
3517 case VKI_SEMOP:
3518 PRE_REG_READ5(int, "ipc",
3519 vki_uint, call, int, first, int, second, int, third,
3520 void *, ptr);
3521 ML_(generic_PRE_sys_semop)( tid, ARG2, ARG5, ARG3 );
3522 *flags |= SfMayBlock;
3523 break;
3524 case VKI_SEMGET:
3525 PRE_REG_READ4(int, "ipc",
3526 vki_uint, call, int, first, int, second, int, third);
3527 break;
3528 case VKI_SEMCTL:
3530 PRE_REG_READ5(int, "ipc",
3531 vki_uint, call, int, first, int, second, int, third,
3532 void *, ptr);
3533 UWord arg;
3534 if (semctl_cmd_has_4args(ARG4))
3535 arg = deref_Addr( tid, ARG5, "semctl(arg)" );
3536 else
3537 arg = 0;
3538 ML_(generic_PRE_sys_semctl)( tid, ARG2, ARG3, ARG4, arg );
3539 break;
3541 case VKI_SEMTIMEDOP:
3542 PRE_REG_READ6(int, "ipc",
3543 vki_uint, call, int, first, int, second, int, third,
3544 void *, ptr, long, fifth);
3545 ML_(generic_PRE_sys_semtimedop)( tid, ARG2, ARG5, ARG3, ARG6 );
3546 *flags |= SfMayBlock;
3547 break;
3548 case VKI_MSGSND:
3549 PRE_REG_READ5(int, "ipc",
3550 vki_uint, call, int, first, int, second, int, third,
3551 void *, ptr);
3552 ML_(linux_PRE_sys_msgsnd)( tid, ARG2, ARG5, ARG3, ARG4 );
3553 if ((ARG4 & VKI_IPC_NOWAIT) == 0)
3554 *flags |= SfMayBlock;
3555 break;
3556 case VKI_MSGRCV:
3558 PRE_REG_READ5(int, "ipc",
3559 vki_uint, call, int, first, int, second, int, third,
3560 void *, ptr);
3561 Addr msgp;
3562 Word msgtyp;
3564 msgp = deref_Addr( tid, (Addr) (&((struct vki_ipc_kludge *)ARG5)->msgp),
3565 "msgrcv(msgp)" );
3566 msgtyp = deref_Addr( tid,
3567 (Addr) (&((struct vki_ipc_kludge *)ARG5)->msgtyp),
3568 "msgrcv(msgp)" );
3570 ML_(linux_PRE_sys_msgrcv)( tid, ARG2, msgp, ARG3, msgtyp, ARG4 );
3572 if ((ARG4 & VKI_IPC_NOWAIT) == 0)
3573 *flags |= SfMayBlock;
3574 break;
3576 case VKI_MSGGET:
3577 PRE_REG_READ3(int, "ipc", vki_uint, call, int, first, int, second);
3578 break;
3579 case VKI_MSGCTL:
3580 PRE_REG_READ5(int, "ipc",
3581 vki_uint, call, int, first, int, second, int, third,
3582 void *, ptr);
3583 ML_(linux_PRE_sys_msgctl)( tid, ARG2, ARG3, ARG5 );
3584 break;
3585 case VKI_SHMAT:
3587 PRE_REG_READ5(int, "ipc",
3588 vki_uint, call, int, first, int, second, int, third,
3589 void *, ptr);
3590 UWord w;
3591 PRE_MEM_WRITE( "shmat(raddr)", ARG4, sizeof(Addr) );
3592 w = ML_(generic_PRE_sys_shmat)( tid, ARG2, ARG5, ARG3 );
3593 if (w == 0)
3594 SET_STATUS_Failure( VKI_EINVAL );
3595 else
3596 ARG5 = w;
3597 break;
3599 case VKI_SHMDT:
3600 PRE_REG_READ5(int, "ipc",
3601 vki_uint, call, int, first, int, second, int, third,
3602 void *, ptr);
3603 if (!ML_(generic_PRE_sys_shmdt)(tid, ARG5))
3604 SET_STATUS_Failure( VKI_EINVAL );
3605 break;
3606 case VKI_SHMGET:
3607 PRE_REG_READ4(int, "ipc",
3608 vki_uint, call, int, first, int, second, int, third);
3609 if (ARG4 & VKI_SHM_HUGETLB) {
3610 static Bool warning_given = False;
3611 ARG4 &= ~VKI_SHM_HUGETLB;
3612 if (!warning_given) {
3613 warning_given = True;
3614 VG_(umsg)(
3615 "WARNING: valgrind ignores shmget(shmflg) SHM_HUGETLB\n");
3618 break;
3619 case VKI_SHMCTL: /* IPCOP_shmctl */
3620 PRE_REG_READ5(int, "ipc",
3621 vki_uint, call, int, first, int, second, int, third,
3622 void *, ptr);
3623 ML_(generic_PRE_sys_shmctl)( tid, ARG2, ARG3, ARG5 );
3624 break;
3625 default:
3626 VG_(message)(Vg_DebugMsg, "FATAL: unhandled syscall(ipc) %ld\n", ARG1 );
3627 VG_(core_panic)("... bye!\n");
3628 break; /*NOTREACHED*/
3632 POST(sys_ipc)
3634 vg_assert(SUCCESS);
3635 switch (ARG1 /* call */) {
3636 case VKI_SEMOP:
3637 case VKI_SEMGET:
3638 break;
3639 case VKI_SEMCTL:
3641 UWord arg;
3642 if (semctl_cmd_has_4args(ARG4))
3643 arg = deref_Addr( tid, ARG5, "semctl(arg)" );
3644 else
3645 arg = 0;
3646 ML_(generic_POST_sys_semctl)( tid, RES, ARG2, ARG3, ARG4, arg );
3647 break;
3649 case VKI_SEMTIMEDOP:
3650 case VKI_MSGSND:
3651 break;
3652 case VKI_MSGRCV:
3654 Addr msgp;
3655 Word msgtyp;
3657 msgp = deref_Addr( tid,
3658 (Addr) (&((struct vki_ipc_kludge *)ARG5)->msgp),
3659 "msgrcv(msgp)" );
3660 msgtyp = deref_Addr( tid,
3661 (Addr) (&((struct vki_ipc_kludge *)ARG5)->msgtyp),
3662 "msgrcv(msgp)" );
3664 ML_(linux_POST_sys_msgrcv)( tid, RES, ARG2, msgp, ARG3, msgtyp, ARG4 );
3665 break;
3667 case VKI_MSGGET:
3668 break;
3669 case VKI_MSGCTL:
3670 ML_(linux_POST_sys_msgctl)( tid, RES, ARG2, ARG3, ARG5 );
3671 break;
3672 case VKI_SHMAT:
3674 Addr addr;
3676 /* force readability. before the syscall it is
3677 * indeed uninitialized, as can be seen in
3678 * glibc/sysdeps/unix/sysv/linux/shmat.c */
3679 POST_MEM_WRITE( ARG4, sizeof( Addr ) );
3681 addr = deref_Addr ( tid, ARG4, "shmat(addr)" );
3682 ML_(generic_POST_sys_shmat)( tid, addr, ARG2, ARG5, ARG3 );
3683 break;
3685 case VKI_SHMDT:
3686 ML_(generic_POST_sys_shmdt)( tid, RES, ARG5 );
3687 break;
3688 case VKI_SHMGET:
3689 break;
3690 case VKI_SHMCTL:
3691 ML_(generic_POST_sys_shmctl)( tid, RES, ARG2, ARG3, ARG5 );
3692 break;
3693 default:
3694 VG_(message)(Vg_DebugMsg,
3695 "FATAL: unhandled syscall(ipc) %ld\n",
3696 ARG1 );
3697 VG_(core_panic)("... bye!\n");
3698 break; /*NOTREACHED*/
3701 #endif
3703 PRE(sys_semget)
3705 PRINT("sys_semget ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
3706 PRE_REG_READ3(long, "semget", vki_key_t, key, int, nsems, int, semflg);
3709 PRE(sys_semop)
3711 *flags |= SfMayBlock;
3712 PRINT("sys_semop ( %ld, %#lx, %lu )",ARG1,ARG2,ARG3);
3713 PRE_REG_READ3(long, "semop",
3714 int, semid, struct sembuf *, sops, unsigned, nsoops);
3715 ML_(generic_PRE_sys_semop)(tid, ARG1,ARG2,ARG3);
3718 PRE(sys_semctl)
3720 switch (ARG3 & ~VKI_IPC_64) {
3721 case VKI_IPC_INFO:
3722 case VKI_SEM_INFO:
3723 PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
3724 PRE_REG_READ4(long, "semctl",
3725 int, semid, int, semnum, int, cmd, struct seminfo *, arg);
3726 break;
3727 case VKI_IPC_STAT:
3728 case VKI_SEM_STAT:
3729 case VKI_IPC_SET:
3730 PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
3731 PRE_REG_READ4(long, "semctl",
3732 int, semid, int, semnum, int, cmd, struct semid_ds *, arg);
3733 break;
3734 case VKI_GETALL:
3735 case VKI_SETALL:
3736 PRINT("sys_semctl ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
3737 PRE_REG_READ4(long, "semctl",
3738 int, semid, int, semnum, int, cmd, unsigned short *, arg);
3739 break;
3740 default:
3741 PRINT("sys_semctl ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
3742 PRE_REG_READ3(long, "semctl",
3743 int, semid, int, semnum, int, cmd);
3744 break;
3746 #ifdef VGP_amd64_linux
3747 ML_(generic_PRE_sys_semctl)(tid, ARG1,ARG2,ARG3|VKI_IPC_64,ARG4);
3748 #else
3749 ML_(generic_PRE_sys_semctl)(tid, ARG1,ARG2,ARG3,ARG4);
3750 #endif
3753 POST(sys_semctl)
3755 #ifdef VGP_amd64_linux
3756 ML_(generic_POST_sys_semctl)(tid, RES,ARG1,ARG2,ARG3|VKI_IPC_64,ARG4);
3757 #else
3758 ML_(generic_POST_sys_semctl)(tid, RES,ARG1,ARG2,ARG3,ARG4);
3759 #endif
3762 PRE(sys_semtimedop)
3764 *flags |= SfMayBlock;
3765 PRINT("sys_semtimedop ( %ld, %#lx, %lu, %#lx )",ARG1,ARG2,ARG3,ARG4);
3766 PRE_REG_READ4(long, "semtimedop",
3767 int, semid, struct sembuf *, sops, unsigned, nsoops,
3768 struct timespec *, timeout);
3769 ML_(generic_PRE_sys_semtimedop)(tid, ARG1,ARG2,ARG3,ARG4);
3772 PRE(sys_msgget)
3774 PRINT("sys_msgget ( %ld, %ld )",ARG1,ARG2);
3775 PRE_REG_READ2(long, "msgget", vki_key_t, key, int, msgflg);
3778 PRE(sys_msgsnd)
3780 PRINT("sys_msgsnd ( %ld, %#lx, %ld, %ld )",ARG1,ARG2,ARG3,ARG4);
3781 PRE_REG_READ4(long, "msgsnd",
3782 int, msqid, struct msgbuf *, msgp, vki_size_t, msgsz, int, msgflg);
3783 ML_(linux_PRE_sys_msgsnd)(tid, ARG1,ARG2,ARG3,ARG4);
3784 if ((ARG4 & VKI_IPC_NOWAIT) == 0)
3785 *flags |= SfMayBlock;
3788 PRE(sys_msgrcv)
3790 PRINT("sys_msgrcv ( %ld, %#lx, %ld, %ld, %ld )",ARG1,ARG2,ARG3,ARG4,ARG5);
3791 PRE_REG_READ5(long, "msgrcv",
3792 int, msqid, struct msgbuf *, msgp, vki_size_t, msgsz,
3793 long, msgytp, int, msgflg);
3794 ML_(linux_PRE_sys_msgrcv)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
3795 if ((ARG5 & VKI_IPC_NOWAIT) == 0)
3796 *flags |= SfMayBlock;
3798 POST(sys_msgrcv)
3800 ML_(linux_POST_sys_msgrcv)(tid, RES,ARG1,ARG2,ARG3,ARG4,ARG5);
3803 PRE(sys_msgctl)
3805 PRINT("sys_msgctl ( %ld, %ld, %#lx )",ARG1,ARG2,ARG3);
3806 PRE_REG_READ3(long, "msgctl",
3807 int, msqid, int, cmd, struct msqid_ds *, buf);
3808 ML_(linux_PRE_sys_msgctl)(tid, ARG1,ARG2,ARG3);
3811 POST(sys_msgctl)
3813 ML_(linux_POST_sys_msgctl)(tid, RES,ARG1,ARG2,ARG3);
3816 PRE(sys_shmget)
3818 PRINT("sys_shmget ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
3819 PRE_REG_READ3(long, "shmget", vki_key_t, key, vki_size_t, size, int, shmflg);
3820 if (ARG3 & VKI_SHM_HUGETLB) {
3821 static Bool warning_given = False;
3822 ARG3 &= ~VKI_SHM_HUGETLB;
3823 if (!warning_given) {
3824 warning_given = True;
3825 VG_(umsg)(
3826 "WARNING: valgrind ignores shmget(shmflg) SHM_HUGETLB\n");
3831 PRE(wrap_sys_shmat)
3833 UWord arg2tmp;
3834 PRINT("wrap_sys_shmat ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
3835 PRE_REG_READ3(long, "shmat",
3836 int, shmid, const void *, shmaddr, int, shmflg);
3837 #if defined(VGP_arm_linux)
3838 /* Round the attach address down to an VKI_SHMLBA boundary if the
3839 client requested rounding. See #222545. This is necessary only
3840 on arm-linux because VKI_SHMLBA is 4 * VKI_PAGE size; on all
3841 other linux targets it is the same as the page size. */
3842 if (ARG3 & VKI_SHM_RND)
3843 ARG2 = VG_ROUNDDN(ARG2, VKI_SHMLBA);
3844 #endif
3845 arg2tmp = ML_(generic_PRE_sys_shmat)(tid, ARG1,ARG2,ARG3);
3846 if (arg2tmp == 0)
3847 SET_STATUS_Failure( VKI_EINVAL );
3848 else
3849 ARG2 = arg2tmp; // used in POST
3852 POST(wrap_sys_shmat)
3854 ML_(generic_POST_sys_shmat)(tid, RES,ARG1,ARG2,ARG3);
3857 PRE(sys_shmdt)
3859 PRINT("sys_shmdt ( %#lx )",ARG1);
3860 PRE_REG_READ1(long, "shmdt", const void *, shmaddr);
3861 if (!ML_(generic_PRE_sys_shmdt)(tid, ARG1))
3862 SET_STATUS_Failure( VKI_EINVAL );
3865 POST(sys_shmdt)
3867 ML_(generic_POST_sys_shmdt)(tid, RES,ARG1);
3870 PRE(sys_shmctl)
3872 PRINT("sys_shmctl ( %ld, %ld, %#lx )",ARG1,ARG2,ARG3);
3873 PRE_REG_READ3(long, "shmctl",
3874 int, shmid, int, cmd, struct shmid_ds *, buf);
3875 #ifdef VGP_amd64_linux
3876 ML_(generic_PRE_sys_shmctl)(tid, ARG1,ARG2|VKI_IPC_64,ARG3);
3877 #else
3878 ML_(generic_PRE_sys_shmctl)(tid, ARG1,ARG2,ARG3);
3879 #endif
3882 POST(sys_shmctl)
3884 #ifdef VGP_amd64_linux
3885 ML_(generic_POST_sys_shmctl)(tid, RES,ARG1,ARG2|VKI_IPC_64,ARG3);
3886 #else
3887 ML_(generic_POST_sys_shmctl)(tid, RES,ARG1,ARG2,ARG3);
3888 #endif
3892 /* ---------------------------------------------------------------------
3893 Generic handler for sys_socketcall
3894 Depending on the platform, some socket related syscalls (e.g. socketpair,
3895 socket, bind, ...)
3896 are either direct system calls, or are all implemented via sys_socketcall.
3897 ------------------------------------------------------------------ */
3898 #ifdef __NR_socketcall
3899 PRE(sys_socketcall)
3901 # define ARG2_0 (((UWord*)ARG2)[0])
3902 # define ARG2_1 (((UWord*)ARG2)[1])
3903 # define ARG2_2 (((UWord*)ARG2)[2])
3904 # define ARG2_3 (((UWord*)ARG2)[3])
3905 # define ARG2_4 (((UWord*)ARG2)[4])
3906 # define ARG2_5 (((UWord*)ARG2)[5])
3908 // call PRE_MEM_READ and check for EFAULT result.
3909 #define PRE_MEM_READ_ef(msg, arg, size) \
3911 PRE_MEM_READ( msg, arg, size); \
3912 if (!ML_(valid_client_addr)(arg, size, tid, NULL)) { \
3913 SET_STATUS_Failure( VKI_EFAULT ); \
3914 break; \
3918 *flags |= SfMayBlock;
3919 PRINT("sys_socketcall ( %ld, %#lx )",ARG1,ARG2);
3920 PRE_REG_READ2(long, "socketcall", int, call, unsigned long *, args);
3922 switch (ARG1 /* request */) {
3924 case VKI_SYS_SOCKETPAIR:
3925 /* int socketpair(int d, int type, int protocol, int sv[2]); */
3926 PRE_MEM_READ_ef( "socketcall.socketpair(args)", ARG2, 4*sizeof(Addr) );
3927 ML_(generic_PRE_sys_socketpair)( tid, ARG2_0, ARG2_1, ARG2_2, ARG2_3 );
3928 break;
3930 case VKI_SYS_SOCKET:
3931 /* int socket(int domain, int type, int protocol); */
3932 PRE_MEM_READ_ef( "socketcall.socket(args)", ARG2, 3*sizeof(Addr) );
3933 break;
3935 case VKI_SYS_BIND:
3936 /* int bind(int sockfd, struct sockaddr *my_addr,
3937 int addrlen); */
3938 PRE_MEM_READ_ef( "socketcall.bind(args)", ARG2, 3*sizeof(Addr) );
3939 ML_(generic_PRE_sys_bind)( tid, ARG2_0, ARG2_1, ARG2_2 );
3940 break;
3942 case VKI_SYS_LISTEN:
3943 /* int listen(int s, int backlog); */
3944 PRE_MEM_READ_ef( "socketcall.listen(args)", ARG2, 2*sizeof(Addr) );
3945 break;
3947 case VKI_SYS_ACCEPT:
3948 /* int accept(int s, struct sockaddr *addr, int *addrlen); */
3949 PRE_MEM_READ_ef( "socketcall.accept(args)", ARG2, 3*sizeof(Addr) );
3950 ML_(generic_PRE_sys_accept)( tid, ARG2_0, ARG2_1, ARG2_2 );
3951 break;
3953 case VKI_SYS_ACCEPT4:
3954 /* int accept4(int s, struct sockaddr *addr, int *addrlen, int flags); */
3955 PRE_MEM_READ_ef( "socketcall.accept4(args)", ARG2, 4*sizeof(Addr) );
3956 ML_(generic_PRE_sys_accept)( tid, ARG2_0, ARG2_1, ARG2_2 );
3957 break;
3959 case VKI_SYS_SENDTO:
3960 /* int sendto(int s, const void *msg, int len,
3961 unsigned int flags,
3962 const struct sockaddr *to, int tolen); */
3963 PRE_MEM_READ_ef( "socketcall.sendto(args)", ARG2, 6*sizeof(Addr) );
3964 ML_(generic_PRE_sys_sendto)( tid, ARG2_0, ARG2_1, ARG2_2,
3965 ARG2_3, ARG2_4, ARG2_5 );
3966 break;
3968 case VKI_SYS_SEND:
3969 /* int send(int s, const void *msg, size_t len, int flags); */
3970 PRE_MEM_READ_ef( "socketcall.send(args)", ARG2, 4*sizeof(Addr) );
3971 ML_(generic_PRE_sys_send)( tid, ARG2_0, ARG2_1, ARG2_2 );
3972 break;
3974 case VKI_SYS_RECVFROM:
3975 /* int recvfrom(int s, void *buf, int len, unsigned int flags,
3976 struct sockaddr *from, int *fromlen); */
3977 PRE_MEM_READ_ef( "socketcall.recvfrom(args)", ARG2, 6*sizeof(Addr) );
3978 ML_(generic_PRE_sys_recvfrom)( tid, ARG2_0, ARG2_1, ARG2_2,
3979 ARG2_3, ARG2_4, ARG2_5 );
3980 break;
3982 case VKI_SYS_RECV:
3983 /* int recv(int s, void *buf, int len, unsigned int flags); */
3984 /* man 2 recv says:
3985 The recv call is normally used only on a connected socket
3986 (see connect(2)) and is identical to recvfrom with a NULL
3987 from parameter.
3989 PRE_MEM_READ_ef( "socketcall.recv(args)", ARG2, 4*sizeof(Addr) );
3990 ML_(generic_PRE_sys_recv)( tid, ARG2_0, ARG2_1, ARG2_2 );
3991 break;
3993 case VKI_SYS_CONNECT:
3994 /* int connect(int sockfd,
3995 struct sockaddr *serv_addr, int addrlen ); */
3996 PRE_MEM_READ_ef( "socketcall.connect(args)", ARG2, 3*sizeof(Addr) );
3997 ML_(generic_PRE_sys_connect)( tid, ARG2_0, ARG2_1, ARG2_2 );
3998 break;
4000 case VKI_SYS_SETSOCKOPT:
4001 /* int setsockopt(int s, int level, int optname,
4002 const void *optval, int optlen); */
4003 PRE_MEM_READ_ef( "socketcall.setsockopt(args)", ARG2, 5*sizeof(Addr) );
4004 ML_(linux_PRE_sys_setsockopt)( tid, ARG2_0, ARG2_1, ARG2_2,
4005 ARG2_3, ARG2_4 );
4006 break;
4008 case VKI_SYS_GETSOCKOPT:
4009 /* int getsockopt(int s, int level, int optname,
4010 void *optval, socklen_t *optlen); */
4011 PRE_MEM_READ_ef( "socketcall.getsockopt(args)", ARG2, 5*sizeof(Addr) );
4012 ML_(linux_PRE_sys_getsockopt)( tid, ARG2_0, ARG2_1, ARG2_2,
4013 ARG2_3, ARG2_4 );
4014 break;
4016 case VKI_SYS_GETSOCKNAME:
4017 /* int getsockname(int s, struct sockaddr* name, int* namelen) */
4018 PRE_MEM_READ_ef( "socketcall.getsockname(args)", ARG2, 3*sizeof(Addr) );
4019 ML_(generic_PRE_sys_getsockname)( tid, ARG2_0, ARG2_1, ARG2_2 );
4020 break;
4022 case VKI_SYS_GETPEERNAME:
4023 /* int getpeername(int s, struct sockaddr* name, int* namelen) */
4024 PRE_MEM_READ_ef( "socketcall.getpeername(args)", ARG2, 3*sizeof(Addr) );
4025 ML_(generic_PRE_sys_getpeername)( tid, ARG2_0, ARG2_1, ARG2_2 );
4026 break;
4028 case VKI_SYS_SHUTDOWN:
4029 /* int shutdown(int s, int how); */
4030 PRE_MEM_READ_ef( "socketcall.shutdown(args)", ARG2, 2*sizeof(Addr) );
4031 break;
4033 case VKI_SYS_SENDMSG:
4034 /* int sendmsg(int s, const struct msghdr *msg, int flags); */
4035 PRE_MEM_READ_ef( "socketcall.sendmsg(args)", ARG2, 3*sizeof(Addr) );
4036 ML_(generic_PRE_sys_sendmsg)( tid, "msg", (struct vki_msghdr *)ARG2_1 );
4037 break;
4039 case VKI_SYS_RECVMSG:
4040 /* int recvmsg(int s, struct msghdr *msg, int flags); */
4041 PRE_MEM_READ_ef("socketcall.recvmsg(args)", ARG2, 3*sizeof(Addr) );
4042 ML_(generic_PRE_sys_recvmsg)( tid, "msg", (struct vki_msghdr *)ARG2_1 );
4043 break;
4045 default:
4046 VG_(message)(Vg_DebugMsg,"Warning: unhandled socketcall 0x%lx\n",ARG1);
4047 SET_STATUS_Failure( VKI_EINVAL );
4048 break;
4050 # undef ARG2_0
4051 # undef ARG2_1
4052 # undef ARG2_2
4053 # undef ARG2_3
4054 # undef ARG2_4
4055 # undef ARG2_5
4058 POST(sys_socketcall)
4060 # define ARG2_0 (((UWord*)ARG2)[0])
4061 # define ARG2_1 (((UWord*)ARG2)[1])
4062 # define ARG2_2 (((UWord*)ARG2)[2])
4063 # define ARG2_3 (((UWord*)ARG2)[3])
4064 # define ARG2_4 (((UWord*)ARG2)[4])
4065 # define ARG2_5 (((UWord*)ARG2)[5])
4067 SysRes r;
4068 vg_assert(SUCCESS);
4069 switch (ARG1 /* request */) {
4071 case VKI_SYS_SOCKETPAIR:
4072 r = ML_(generic_POST_sys_socketpair)(
4073 tid, VG_(mk_SysRes_Success)(RES),
4074 ARG2_0, ARG2_1, ARG2_2, ARG2_3
4076 SET_STATUS_from_SysRes(r);
4077 break;
4079 case VKI_SYS_SOCKET:
4080 r = ML_(generic_POST_sys_socket)( tid, VG_(mk_SysRes_Success)(RES) );
4081 SET_STATUS_from_SysRes(r);
4082 break;
4084 case VKI_SYS_BIND:
4085 /* int bind(int sockfd, struct sockaddr *my_addr,
4086 int addrlen); */
4087 break;
4089 case VKI_SYS_LISTEN:
4090 /* int listen(int s, int backlog); */
4091 break;
4093 case VKI_SYS_ACCEPT:
4094 case VKI_SYS_ACCEPT4:
4095 /* int accept(int s, struct sockaddr *addr, int *addrlen); */
4096 /* int accept4(int s, struct sockaddr *addr, int *addrlen, int flags); */
4097 r = ML_(generic_POST_sys_accept)( tid, VG_(mk_SysRes_Success)(RES),
4098 ARG2_0, ARG2_1, ARG2_2 );
4099 SET_STATUS_from_SysRes(r);
4100 break;
4102 case VKI_SYS_SENDTO:
4103 break;
4105 case VKI_SYS_SEND:
4106 break;
4108 case VKI_SYS_RECVFROM:
4109 ML_(generic_POST_sys_recvfrom)( tid, VG_(mk_SysRes_Success)(RES),
4110 ARG2_0, ARG2_1, ARG2_2,
4111 ARG2_3, ARG2_4, ARG2_5 );
4112 break;
4114 case VKI_SYS_RECV:
4115 ML_(generic_POST_sys_recv)( tid, RES, ARG2_0, ARG2_1, ARG2_2 );
4116 break;
4118 case VKI_SYS_CONNECT:
4119 break;
4121 case VKI_SYS_SETSOCKOPT:
4122 break;
4124 case VKI_SYS_GETSOCKOPT:
4125 ML_(linux_POST_sys_getsockopt)( tid, VG_(mk_SysRes_Success)(RES),
4126 ARG2_0, ARG2_1,
4127 ARG2_2, ARG2_3, ARG2_4 );
4128 break;
4130 case VKI_SYS_GETSOCKNAME:
4131 ML_(generic_POST_sys_getsockname)( tid, VG_(mk_SysRes_Success)(RES),
4132 ARG2_0, ARG2_1, ARG2_2 );
4133 break;
4135 case VKI_SYS_GETPEERNAME:
4136 ML_(generic_POST_sys_getpeername)( tid, VG_(mk_SysRes_Success)(RES),
4137 ARG2_0, ARG2_1, ARG2_2 );
4138 break;
4140 case VKI_SYS_SHUTDOWN:
4141 break;
4143 case VKI_SYS_SENDMSG:
4144 break;
4146 case VKI_SYS_RECVMSG:
4147 ML_(generic_POST_sys_recvmsg)( tid, "msg", (struct vki_msghdr *)ARG2_1, RES );
4148 break;
4150 default:
4151 VG_(message)(Vg_DebugMsg,"FATAL: unhandled socketcall 0x%lx\n",ARG1);
4152 VG_(core_panic)("... bye!\n");
4153 break; /*NOTREACHED*/
4155 # undef ARG2_0
4156 # undef ARG2_1
4157 # undef ARG2_2
4158 # undef ARG2_3
4159 # undef ARG2_4
4160 # undef ARG2_5
4162 #endif
4164 PRE(sys_socket)
4166 PRINT("sys_socket ( %ld, %ld, %ld )",ARG1,ARG2,ARG3);
4167 PRE_REG_READ3(long, "socket", int, domain, int, type, int, protocol);
4169 POST(sys_socket)
4171 SysRes r;
4172 vg_assert(SUCCESS);
4173 r = ML_(generic_POST_sys_socket)(tid, VG_(mk_SysRes_Success)(RES));
4174 SET_STATUS_from_SysRes(r);
4177 PRE(sys_setsockopt)
4179 PRINT("sys_setsockopt ( %ld, %ld, %ld, %#lx, %ld )",ARG1,ARG2,ARG3,ARG4,ARG5);
4180 PRE_REG_READ5(long, "setsockopt",
4181 int, s, int, level, int, optname,
4182 const void *, optval, int, optlen);
4183 ML_(linux_PRE_sys_setsockopt)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
4186 PRE(sys_getsockopt)
4188 PRINT("sys_getsockopt ( %ld, %ld, %ld, %#lx, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5);
4189 PRE_REG_READ5(long, "getsockopt",
4190 int, s, int, level, int, optname,
4191 void *, optval, int, *optlen);
4192 ML_(linux_PRE_sys_getsockopt)(tid, ARG1,ARG2,ARG3,ARG4,ARG5);
4194 POST(sys_getsockopt)
4196 vg_assert(SUCCESS);
4197 ML_(linux_POST_sys_getsockopt)(tid, VG_(mk_SysRes_Success)(RES),
4198 ARG1,ARG2,ARG3,ARG4,ARG5);
4201 PRE(sys_connect)
4203 *flags |= SfMayBlock;
4204 PRINT("sys_connect ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
4205 PRE_REG_READ3(long, "connect",
4206 int, sockfd, struct sockaddr *, serv_addr, int, addrlen);
4207 ML_(generic_PRE_sys_connect)(tid, ARG1,ARG2,ARG3);
4210 PRE(sys_accept)
4212 *flags |= SfMayBlock;
4213 PRINT("sys_accept ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
4214 PRE_REG_READ3(long, "accept",
4215 int, s, struct sockaddr *, addr, int, *addrlen);
4216 ML_(generic_PRE_sys_accept)(tid, ARG1,ARG2,ARG3);
4218 POST(sys_accept)
4220 SysRes r;
4221 vg_assert(SUCCESS);
4222 r = ML_(generic_POST_sys_accept)(tid, VG_(mk_SysRes_Success)(RES),
4223 ARG1,ARG2,ARG3);
4224 SET_STATUS_from_SysRes(r);
4227 PRE(sys_accept4)
4229 *flags |= SfMayBlock;
4230 PRINT("sys_accept4 ( %ld, %#lx, %ld, %ld )",ARG1,ARG2,ARG3,ARG4);
4231 PRE_REG_READ4(long, "accept4",
4232 int, s, struct sockaddr *, addr, int, *addrlen, int, flags);
4233 ML_(generic_PRE_sys_accept)(tid, ARG1,ARG2,ARG3);
4235 POST(sys_accept4)
4237 SysRes r;
4238 vg_assert(SUCCESS);
4239 r = ML_(generic_POST_sys_accept)(tid, VG_(mk_SysRes_Success)(RES),
4240 ARG1,ARG2,ARG3);
4241 SET_STATUS_from_SysRes(r);
4244 PRE(sys_send)
4246 *flags |= SfMayBlock;
4247 PRINT("sys_send ( %ld, %#lx, %ld, %lu )",ARG1,ARG2,ARG3,ARG4);
4248 PRE_REG_READ4(long, "send",
4249 int, s, const void *, msg, int, len,
4250 unsigned int, flags);
4252 ML_(generic_PRE_sys_send)( tid, ARG1, ARG2, ARG3 );
4255 PRE(sys_sendto)
4257 *flags |= SfMayBlock;
4258 PRINT("sys_sendto ( %ld, %#lx, %ld, %lu, %#lx, %ld )",ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
4259 PRE_REG_READ6(long, "sendto",
4260 int, s, const void *, msg, int, len,
4261 unsigned int, flags,
4262 const struct sockaddr *, to, int, tolen);
4263 ML_(generic_PRE_sys_sendto)(tid, ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
4266 PRE (sys_recv)
4268 *flags |= SfMayBlock;
4269 PRINT ("sys_recv ( %ld, %#lx, %ld, %lu )", ARG1, ARG2, ARG3, ARG4);
4270 PRE_REG_READ4 (long, "recv", int, s, void *, buf, int, len,
4271 unsigned int, flags);
4272 ML_ (generic_PRE_sys_recv) (tid, ARG1, ARG2, ARG3);
4275 POST (sys_recv)
4277 ML_ (generic_POST_sys_recv) (tid, RES, ARG1, ARG2, ARG3);
4280 PRE(sys_recvfrom)
4282 *flags |= SfMayBlock;
4283 PRINT("sys_recvfrom ( %ld, %#lx, %ld, %lu, %#lx, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
4284 PRE_REG_READ6(long, "recvfrom",
4285 int, s, void *, buf, int, len, unsigned int, flags,
4286 struct sockaddr *, from, int *, fromlen);
4287 ML_(generic_PRE_sys_recvfrom)(tid, ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
4289 POST(sys_recvfrom)
4291 vg_assert(SUCCESS);
4292 ML_(generic_POST_sys_recvfrom)(tid, VG_(mk_SysRes_Success)(RES),
4293 ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
4296 PRE(sys_sendmsg)
4298 *flags |= SfMayBlock;
4299 PRINT("sys_sendmsg ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
4300 PRE_REG_READ3(long, "sendmsg",
4301 int, s, const struct msghdr *, msg, int, flags);
4302 ML_(generic_PRE_sys_sendmsg)(tid, "msg", (struct vki_msghdr *)ARG2);
4305 PRE(sys_recvmsg)
4307 *flags |= SfMayBlock;
4308 PRINT("sys_recvmsg ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
4309 PRE_REG_READ3(long, "recvmsg", int, s, struct msghdr *, msg, int, flags);
4310 ML_(generic_PRE_sys_recvmsg)(tid, "msg", (struct vki_msghdr *)ARG2);
4312 POST(sys_recvmsg)
4314 ML_(generic_POST_sys_recvmsg)(tid, "msg", (struct vki_msghdr *)ARG2, RES);
4317 PRE(sys_shutdown)
4319 *flags |= SfMayBlock;
4320 PRINT("sys_shutdown ( %ld, %ld )",ARG1,ARG2);
4321 PRE_REG_READ2(int, "shutdown", int, s, int, how);
4324 PRE(sys_bind)
4326 PRINT("sys_bind ( %ld, %#lx, %ld )",ARG1,ARG2,ARG3);
4327 PRE_REG_READ3(long, "bind",
4328 int, sockfd, struct sockaddr *, my_addr, int, addrlen);
4329 ML_(generic_PRE_sys_bind)(tid, ARG1,ARG2,ARG3);
4332 PRE(sys_listen)
4334 PRINT("sys_listen ( %ld, %ld )",ARG1,ARG2);
4335 PRE_REG_READ2(long, "listen", int, s, int, backlog);
4338 PRE(sys_getsockname)
4340 PRINT("sys_getsockname ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
4341 PRE_REG_READ3(long, "getsockname",
4342 int, s, struct sockaddr *, name, int *, namelen);
4343 ML_(generic_PRE_sys_getsockname)(tid, ARG1,ARG2,ARG3);
4345 POST(sys_getsockname)
4347 vg_assert(SUCCESS);
4348 ML_(generic_POST_sys_getsockname)(tid, VG_(mk_SysRes_Success)(RES),
4349 ARG1,ARG2,ARG3);
4352 PRE(sys_getpeername)
4354 PRINT("sys_getpeername ( %ld, %#lx, %#lx )",ARG1,ARG2,ARG3);
4355 PRE_REG_READ3(long, "getpeername",
4356 int, s, struct sockaddr *, name, int *, namelen);
4357 ML_(generic_PRE_sys_getpeername)(tid, ARG1,ARG2,ARG3);
4359 POST(sys_getpeername)
4361 vg_assert(SUCCESS);
4362 ML_(generic_POST_sys_getpeername)(tid, VG_(mk_SysRes_Success)(RES),
4363 ARG1,ARG2,ARG3);
4366 PRE(sys_socketpair)
4368 PRINT("sys_socketpair ( %ld, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4);
4369 PRE_REG_READ4(long, "socketpair",
4370 int, d, int, type, int, protocol, int*, sv);
4371 ML_(generic_PRE_sys_socketpair)(tid, ARG1,ARG2,ARG3,ARG4);
4373 POST(sys_socketpair)
4375 vg_assert(SUCCESS);
4376 ML_(generic_POST_sys_socketpair)(tid, VG_(mk_SysRes_Success)(RES),
4377 ARG1,ARG2,ARG3,ARG4);
4381 /* ---------------------------------------------------------------------
4382 *at wrappers
4383 ------------------------------------------------------------------ */
4385 PRE(sys_openat)
4387 HChar name[30];
4388 SysRes sres;
4390 if (ARG3 & VKI_O_CREAT) {
4391 // 4-arg version
4392 PRINT("sys_openat ( %ld, %#lx(%s), %ld, %ld )",ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
4393 PRE_REG_READ4(long, "openat",
4394 int, dfd, const char *, filename, int, flags, int, mode);
4395 } else {
4396 // 3-arg version
4397 PRINT("sys_openat ( %ld, %#lx(%s), %ld )",ARG1,ARG2,(char*)ARG2,ARG3);
4398 PRE_REG_READ3(long, "openat",
4399 int, dfd, const char *, filename, int, flags);
4402 PRE_MEM_RASCIIZ( "openat(filename)", ARG2 );
4404 /* For absolute filenames, dfd is ignored. If dfd is AT_FDCWD,
4405 filename is relative to cwd. When comparing dfd against AT_FDCWD,
4406 be sure only to compare the bottom 32 bits. */
4407 if (ML_(safe_to_deref)( (void*)ARG2, 1 )
4408 && *(Char *)ARG2 != '/'
4409 && ((Int)ARG1) != ((Int)VKI_AT_FDCWD)
4410 && !ML_(fd_allowed)(ARG1, "openat", tid, False))
4411 SET_STATUS_Failure( VKI_EBADF );
4413 /* Handle the case where the open is of /proc/self/cmdline or
4414 /proc/<pid>/cmdline, and just give it a copy of the fd for the
4415 fake file we cooked up at startup (in m_main). Also, seek the
4416 cloned fd back to the start. */
4418 VG_(sprintf)(name, "/proc/%d/cmdline", VG_(getpid)());
4419 if (ML_(safe_to_deref)( (void*)ARG2, 1 )
4420 && (VG_(strcmp)((HChar *)ARG2, name) == 0
4421 || VG_(strcmp)((HChar *)ARG2, "/proc/self/cmdline") == 0)) {
4422 sres = VG_(dup)( VG_(cl_cmdline_fd) );
4423 SET_STATUS_from_SysRes( sres );
4424 if (!sr_isError(sres)) {
4425 OffT off = VG_(lseek)( sr_Res(sres), 0, VKI_SEEK_SET );
4426 if (off < 0)
4427 SET_STATUS_Failure( VKI_EMFILE );
4429 return;
4432 /* Do the same for /proc/self/auxv or /proc/<pid>/auxv case. */
4434 VG_(sprintf)(name, "/proc/%d/auxv", VG_(getpid)());
4435 if (ML_(safe_to_deref)( (void*)ARG2, 1 )
4436 && (VG_(strcmp)((HChar *)ARG2, name) == 0
4437 || VG_(strcmp)((HChar *)ARG2, "/proc/self/auxv") == 0)) {
4438 sres = VG_(dup)( VG_(cl_auxv_fd) );
4439 SET_STATUS_from_SysRes( sres );
4440 if (!sr_isError(sres)) {
4441 OffT off = VG_(lseek)( sr_Res(sres), 0, VKI_SEEK_SET );
4442 if (off < 0)
4443 SET_STATUS_Failure( VKI_EMFILE );
4445 return;
4448 /* Otherwise handle normally */
4449 *flags |= SfMayBlock;
4452 POST(sys_openat)
4454 vg_assert(SUCCESS);
4455 if (!ML_(fd_allowed)(RES, "openat", tid, True)) {
4456 VG_(close)(RES);
4457 SET_STATUS_Failure( VKI_EMFILE );
4458 } else {
4459 if (VG_(clo_track_fds))
4460 ML_(record_fd_open_with_given_name)(tid, RES, (HChar*)ARG2);
4464 PRE(sys_mkdirat)
4466 *flags |= SfMayBlock;
4467 PRINT("sys_mkdirat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
4468 PRE_REG_READ3(long, "mkdirat",
4469 int, dfd, const char *, pathname, int, mode);
4470 PRE_MEM_RASCIIZ( "mkdirat(pathname)", ARG2 );
4473 PRE(sys_mknodat)
4475 PRINT("sys_mknodat ( %ld, %#lx(%s), 0x%lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4 );
4476 PRE_REG_READ4(long, "mknodat",
4477 int, dfd, const char *, pathname, int, mode, unsigned, dev);
4478 PRE_MEM_RASCIIZ( "mknodat(pathname)", ARG2 );
4481 PRE(sys_fchownat)
4483 PRINT("sys_fchownat ( %ld, %#lx(%s), 0x%lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
4484 PRE_REG_READ4(long, "fchownat",
4485 int, dfd, const char *, path,
4486 vki_uid_t, owner, vki_gid_t, group);
4487 PRE_MEM_RASCIIZ( "fchownat(path)", ARG2 );
4490 PRE(sys_futimesat)
4492 PRINT("sys_futimesat ( %ld, %#lx(%s), %#lx )", ARG1,ARG2,(char*)ARG2,ARG3);
4493 PRE_REG_READ3(long, "futimesat",
4494 int, dfd, char *, filename, struct timeval *, tvp);
4495 if (ARG2 != 0)
4496 PRE_MEM_RASCIIZ( "futimesat(filename)", ARG2 );
4497 if (ARG3 != 0)
4498 PRE_MEM_READ( "futimesat(tvp)", ARG3, 2 * sizeof(struct vki_timeval) );
4501 PRE(sys_utimensat)
4503 PRINT("sys_utimensat ( %ld, %#lx(%s), %#lx, 0x%lx )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4);
4504 PRE_REG_READ4(long, "utimensat",
4505 int, dfd, char *, filename, struct timespec *, utimes, int, flags);
4506 if (ARG2 != 0)
4507 PRE_MEM_RASCIIZ( "utimensat(filename)", ARG2 );
4508 if (ARG3 != 0)
4509 PRE_MEM_READ( "utimensat(tvp)", ARG3, 2 * sizeof(struct vki_timespec) );
4512 PRE(sys_newfstatat)
4514 FUSE_COMPATIBLE_MAY_BLOCK();
4515 PRINT("sys_newfstatat ( %ld, %#lx(%s), %#lx )", ARG1,ARG2,(char*)ARG2,ARG3);
4516 PRE_REG_READ3(long, "fstatat",
4517 int, dfd, char *, file_name, struct stat *, buf);
4518 PRE_MEM_RASCIIZ( "fstatat(file_name)", ARG2 );
4519 PRE_MEM_WRITE( "fstatat(buf)", ARG3, sizeof(struct vki_stat) );
4522 POST(sys_newfstatat)
4524 POST_MEM_WRITE( ARG3, sizeof(struct vki_stat) );
4527 PRE(sys_unlinkat)
4529 *flags |= SfMayBlock;
4530 PRINT("sys_unlinkat ( %ld, %#lx(%s) )", ARG1,ARG2,(char*)ARG2);
4531 PRE_REG_READ2(long, "unlinkat", int, dfd, const char *, pathname);
4532 PRE_MEM_RASCIIZ( "unlinkat(pathname)", ARG2 );
4535 PRE(sys_renameat)
4537 PRINT("sys_renameat ( %ld, %#lx(%s), %ld, %#lx(%s) )", ARG1,ARG2,(char*)ARG2,ARG3,ARG4,(char*)ARG4);
4538 PRE_REG_READ4(long, "renameat",
4539 int, olddfd, const char *, oldpath,
4540 int, newdfd, const char *, newpath);
4541 PRE_MEM_RASCIIZ( "renameat(oldpath)", ARG2 );
4542 PRE_MEM_RASCIIZ( "renameat(newpath)", ARG4 );
4545 PRE(sys_linkat)
4547 *flags |= SfMayBlock;
4548 PRINT("sys_linkat ( %ld, %#lx(%s), %ld, %#lx(%s), %ld )",ARG1,ARG2,(char*)ARG2,ARG3,ARG4,(char*)ARG4,ARG5);
4549 PRE_REG_READ5(long, "linkat",
4550 int, olddfd, const char *, oldpath,
4551 int, newdfd, const char *, newpath,
4552 int, flags);
4553 PRE_MEM_RASCIIZ( "linkat(oldpath)", ARG2);
4554 PRE_MEM_RASCIIZ( "linkat(newpath)", ARG4);
4557 PRE(sys_symlinkat)
4559 *flags |= SfMayBlock;
4560 PRINT("sys_symlinkat ( %#lx(%s), %ld, %#lx(%s) )",ARG1,(char*)ARG1,ARG2,ARG3,(char*)ARG3);
4561 PRE_REG_READ3(long, "symlinkat",
4562 const char *, oldpath, int, newdfd, const char *, newpath);
4563 PRE_MEM_RASCIIZ( "symlinkat(oldpath)", ARG1 );
4564 PRE_MEM_RASCIIZ( "symlinkat(newpath)", ARG3 );
4567 PRE(sys_readlinkat)
4569 HChar name[25];
4570 Word saved = SYSNO;
4572 PRINT("sys_readlinkat ( %ld, %#lx(%s), %#lx, %llu )", ARG1,ARG2,(char*)ARG2,ARG3,(ULong)ARG4);
4573 PRE_REG_READ4(long, "readlinkat",
4574 int, dfd, const char *, path, char *, buf, int, bufsiz);
4575 PRE_MEM_RASCIIZ( "readlinkat(path)", ARG2 );
4576 PRE_MEM_WRITE( "readlinkat(buf)", ARG3,ARG4 );
4579 * Handle the case where readlinkat is looking at /proc/self/exe or
4580 * /proc/<pid>/exe.
4582 VG_(sprintf)(name, "/proc/%d/exe", VG_(getpid)());
4583 if (ML_(safe_to_deref)((void*)ARG2, 1)
4584 && (VG_(strcmp)((HChar *)ARG2, name) == 0
4585 || VG_(strcmp)((HChar *)ARG2, "/proc/self/exe") == 0)) {
4586 VG_(sprintf)(name, "/proc/self/fd/%d", VG_(cl_exec_fd));
4587 SET_STATUS_from_SysRes( VG_(do_syscall4)(saved, ARG1, (UWord)name,
4588 ARG3, ARG4));
4589 } else {
4590 /* Normal case */
4591 SET_STATUS_from_SysRes( VG_(do_syscall4)(saved, ARG1, ARG2, ARG3, ARG4));
4594 if (SUCCESS && RES > 0)
4595 POST_MEM_WRITE( ARG3, RES );
4598 PRE(sys_fchmodat)
4600 PRINT("sys_fchmodat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
4601 PRE_REG_READ3(long, "fchmodat",
4602 int, dfd, const char *, path, vki_mode_t, mode);
4603 PRE_MEM_RASCIIZ( "fchmodat(path)", ARG2 );
4606 PRE(sys_faccessat)
4608 PRINT("sys_faccessat ( %ld, %#lx(%s), %ld )", ARG1,ARG2,(char*)ARG2,ARG3);
4609 PRE_REG_READ3(long, "faccessat",
4610 int, dfd, const char *, pathname, int, mode);
4611 PRE_MEM_RASCIIZ( "faccessat(pathname)", ARG2 );
4614 PRE(sys_name_to_handle_at)
4616 PRINT("sys_name_to_handle_at ( %ld, %#lx(%s), %#lx, %#lx, %ld )", ARG1, ARG2, (char*)ARG2, ARG3, ARG4, ARG5);
4617 PRE_REG_READ5(int, "name_to_handle_at",
4618 int, dfd, const char *, name,
4619 struct vki_file_handle *, handle,
4620 int *, mnt_id, int, flag);
4621 PRE_MEM_RASCIIZ( "name_to_handle_at(name)", ARG2 );
4622 if (ML_(safe_to_deref)( (void*)ARG3, sizeof(struct vki_file_handle))) {
4623 struct vki_file_handle *fh = (struct vki_file_handle *)ARG3;
4624 PRE_MEM_READ( "name_to_handle_at(handle)", (Addr)&fh->handle_bytes, sizeof(fh->handle_bytes) );
4625 PRE_MEM_WRITE( "name_to_handle_at(handle)", (Addr)fh, sizeof(struct vki_file_handle) + fh->handle_bytes );
4627 PRE_MEM_WRITE( "name_to_handle_at(mnt_id)", ARG4, sizeof(int) );
4630 POST(sys_name_to_handle_at)
4632 struct vki_file_handle *fh = (struct vki_file_handle *)ARG3;
4633 POST_MEM_WRITE( ARG3, sizeof(struct vki_file_handle) + fh->handle_bytes );
4634 POST_MEM_WRITE( ARG4, sizeof(int) );
4637 PRE(sys_open_by_handle_at)
4639 *flags |= SfMayBlock;
4640 PRINT("sys_open_by_handle_at ( %ld, %#lx, %ld )", ARG1, ARG2, ARG3);
4641 PRE_REG_READ3(int, "open_by_handle_at",
4642 int, mountdirfd,
4643 struct vki_file_handle *, handle,
4644 int, flags);
4645 PRE_MEM_READ( "open_by_handle_at(handle)", ARG2, sizeof(struct vki_file_handle) + ((struct vki_file_handle*)ARG2)->handle_bytes );
4648 POST(sys_open_by_handle_at)
4650 vg_assert(SUCCESS);
4651 if (!ML_(fd_allowed)(RES, "open_by_handle_at", tid, True)) {
4652 VG_(close)(RES);
4653 SET_STATUS_Failure( VKI_EMFILE );
4654 } else {
4655 if (VG_(clo_track_fds))
4656 ML_(record_fd_open_with_given_name)(tid, RES, (HChar*)ARG2);
4660 /* ---------------------------------------------------------------------
4661 p{read,write}v wrappers
4662 ------------------------------------------------------------------ */
4664 PRE(sys_preadv)
4666 Int i;
4667 struct vki_iovec * vec;
4668 *flags |= SfMayBlock;
4669 #if VG_WORDSIZE == 4
4670 /* Note that the offset argument here is in lo+hi order on both
4671 big and little endian platforms... */
4672 PRINT("sys_preadv ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,LOHI64(ARG4,ARG5));
4673 PRE_REG_READ5(ssize_t, "preadv",
4674 unsigned long, fd, const struct iovec *, vector,
4675 unsigned long, count, vki_u32, offset_low,
4676 vki_u32, offset_high);
4677 #elif VG_WORDSIZE == 8
4678 PRINT("sys_preadv ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,(Long)ARG4);
4679 PRE_REG_READ4(ssize_t, "preadv",
4680 unsigned long, fd, const struct iovec *, vector,
4681 unsigned long, count, Word, offset);
4682 #else
4683 # error Unexpected word size
4684 #endif
4685 if (!ML_(fd_allowed)(ARG1, "preadv", tid, False)) {
4686 SET_STATUS_Failure( VKI_EBADF );
4687 } else {
4688 PRE_MEM_READ( "preadv(vector)", ARG2, ARG3 * sizeof(struct vki_iovec) );
4690 if (ARG2 != 0) {
4691 /* ToDo: don't do any of the following if the vector is invalid */
4692 vec = (struct vki_iovec *)ARG2;
4693 for (i = 0; i < (Int)ARG3; i++)
4694 PRE_MEM_WRITE( "preadv(vector[...])",
4695 (Addr)vec[i].iov_base, vec[i].iov_len );
4700 POST(sys_preadv)
4702 vg_assert(SUCCESS);
4703 if (RES > 0) {
4704 Int i;
4705 struct vki_iovec * vec = (struct vki_iovec *)ARG2;
4706 Int remains = RES;
4708 /* RES holds the number of bytes read. */
4709 for (i = 0; i < (Int)ARG3; i++) {
4710 Int nReadThisBuf = vec[i].iov_len;
4711 if (nReadThisBuf > remains) nReadThisBuf = remains;
4712 POST_MEM_WRITE( (Addr)vec[i].iov_base, nReadThisBuf );
4713 remains -= nReadThisBuf;
4714 if (remains < 0) VG_(core_panic)("preadv: remains < 0");
4719 PRE(sys_pwritev)
4721 Int i;
4722 struct vki_iovec * vec;
4723 *flags |= SfMayBlock;
4724 #if VG_WORDSIZE == 4
4725 /* Note that the offset argument here is in lo+hi order on both
4726 big and little endian platforms... */
4727 PRINT("sys_pwritev ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,LOHI64(ARG4,ARG5));
4728 PRE_REG_READ5(ssize_t, "pwritev",
4729 unsigned long, fd, const struct iovec *, vector,
4730 unsigned long, count, vki_u32, offset_low,
4731 vki_u32, offset_high);
4732 #elif VG_WORDSIZE == 8
4733 PRINT("sys_pwritev ( %ld, %#lx, %llu, %lld )",ARG1,ARG2,(ULong)ARG3,(Long)ARG4);
4734 PRE_REG_READ4(ssize_t, "pwritev",
4735 unsigned long, fd, const struct iovec *, vector,
4736 unsigned long, count, Word, offset);
4737 #else
4738 # error Unexpected word size
4739 #endif
4740 if (!ML_(fd_allowed)(ARG1, "pwritev", tid, False)) {
4741 SET_STATUS_Failure( VKI_EBADF );
4742 } else {
4743 PRE_MEM_READ( "pwritev(vector)",
4744 ARG2, ARG3 * sizeof(struct vki_iovec) );
4745 if (ARG2 != 0) {
4746 /* ToDo: don't do any of the following if the vector is invalid */
4747 vec = (struct vki_iovec *)ARG2;
4748 for (i = 0; i < (Int)ARG3; i++)
4749 PRE_MEM_READ( "pwritev(vector[...])",
4750 (Addr)vec[i].iov_base, vec[i].iov_len );
4755 /* ---------------------------------------------------------------------
4756 process_vm_{read,write}v wrappers
4757 ------------------------------------------------------------------ */
4759 PRE(sys_process_vm_readv)
4761 PRINT("sys_process_vm_readv ( %lu, %#lx, %lu, %#lx, %lu, %lu )",
4762 ARG1, ARG2, ARG3, ARG4, ARG5, ARG6);
4763 PRE_REG_READ6(ssize_t, "process_vm_readv",
4764 vki_pid_t, pid,
4765 const struct iovec *, lvec,
4766 unsigned long, liovcnt,
4767 const struct iovec *, rvec,
4768 unsigned long, riovcnt,
4769 unsigned long, flags);
4770 PRE_MEM_READ( "process_vm_readv(lvec)",
4771 ARG2, ARG3 * sizeof(struct vki_iovec) );
4772 PRE_MEM_READ( "process_vm_readv(rvec)",
4773 ARG4, ARG5 * sizeof(struct vki_iovec) );
4774 if (ARG2 != 0) {
4775 /* TODO: Don't do any of the following if lvec is invalid */
4776 const struct vki_iovec *vec = (const struct vki_iovec *)ARG2;
4777 UInt i;
4778 for (i = 0; i < ARG3; i++)
4779 PRE_MEM_WRITE( "process_vm_readv(lvec[...])",
4780 (Addr)vec[i].iov_base, vec[i].iov_len );
4784 POST(sys_process_vm_readv)
4786 const struct vki_iovec *vec = (const struct vki_iovec *)ARG2;
4787 UInt remains = RES;
4788 UInt i;
4789 for (i = 0; i < ARG3; i++) {
4790 UInt nReadThisBuf = vec[i].iov_len <= remains ?
4791 vec[i].iov_len : remains;
4792 POST_MEM_WRITE( (Addr)vec[i].iov_base, nReadThisBuf );
4793 remains -= nReadThisBuf;
4797 PRE(sys_process_vm_writev)
4799 PRINT("sys_process_vm_writev ( %lu, %#lx, %lu, %#lx, %lu, %lu )",
4800 ARG1, ARG2, ARG3, ARG4, ARG5, ARG6);
4801 PRE_REG_READ6(ssize_t, "process_vm_writev",
4802 vki_pid_t, pid,
4803 const struct iovec *, lvec,
4804 unsigned long, liovcnt,
4805 const struct iovec *, rvec,
4806 unsigned long, riovcnt,
4807 unsigned long, flags);
4808 PRE_MEM_READ( "process_vm_writev(lvec)",
4809 ARG2, ARG3 * sizeof(struct vki_iovec) );
4810 PRE_MEM_READ( "process_vm_writev(rvec)",
4811 ARG4, ARG5 * sizeof(struct vki_iovec) );
4812 if (ARG2 != 0) {
4813 /* TODO: Don't do any of the following if lvec is invalid */
4814 const struct vki_iovec *vec = (const struct vki_iovec *)ARG2;
4815 UInt i;
4816 for (i = 0; i < ARG3; i++)
4817 PRE_MEM_READ( "process_vm_writev(lvec[...])",
4818 (Addr)vec[i].iov_base, vec[i].iov_len );
4822 /* ---------------------------------------------------------------------
4823 {send,recv}mmsg wrappers
4824 ------------------------------------------------------------------ */
4826 PRE(sys_sendmmsg)
4828 struct vki_mmsghdr *mmsg = (struct vki_mmsghdr *)ARG2;
4829 HChar name[32];
4830 UInt i;
4831 *flags |= SfMayBlock;
4832 PRINT("sys_sendmmsg ( %ld, %#lx, %ld, %ld )",ARG1,ARG2,ARG3,ARG4);
4833 PRE_REG_READ4(long, "sendmmsg",
4834 int, s, const struct mmsghdr *, mmsg, int, vlen, int, flags);
4835 for (i = 0; i < ARG3; i++) {
4836 VG_(sprintf)(name, "mmsg[%u].msg_hdr", i);
4837 ML_(generic_PRE_sys_sendmsg)(tid, name, &mmsg[i].msg_hdr);
4838 VG_(sprintf)(name, "sendmmsg(mmsg[%u].msg_len)", i);
4839 PRE_MEM_WRITE( name, (Addr)&mmsg[i].msg_len, sizeof(mmsg[i].msg_len) );
4843 POST(sys_sendmmsg)
4845 if (RES > 0) {
4846 struct vki_mmsghdr *mmsg = (struct vki_mmsghdr *)ARG2;
4847 UInt i;
4848 for (i = 0; i < RES; i++) {
4849 POST_MEM_WRITE( (Addr)&mmsg[i].msg_len, sizeof(mmsg[i].msg_len) );
4854 PRE(sys_recvmmsg)
4856 struct vki_mmsghdr *mmsg = (struct vki_mmsghdr *)ARG2;
4857 HChar name[32];
4858 UInt i;
4859 *flags |= SfMayBlock;
4860 PRINT("sys_recvmmsg ( %ld, %#lx, %ld, %ld, %#lx )",ARG1,ARG2,ARG3,ARG4,ARG5);
4861 PRE_REG_READ5(long, "recvmmsg",
4862 int, s, struct mmsghdr *, mmsg, int, vlen,
4863 int, flags, struct timespec *, timeout);
4864 for (i = 0; i < ARG3; i++) {
4865 VG_(sprintf)(name, "mmsg[%u].msg_hdr", i);
4866 ML_(generic_PRE_sys_recvmsg)(tid, name, &mmsg[i].msg_hdr);
4867 VG_(sprintf)(name, "recvmmsg(mmsg[%u].msg_len)", i);
4868 PRE_MEM_WRITE( name, (Addr)&mmsg[i].msg_len, sizeof(mmsg[i].msg_len) );
4870 if (ARG5)
4871 PRE_MEM_READ( "recvmmsg(timeout)", ARG5, sizeof(struct vki_timespec) );
4874 POST(sys_recvmmsg)
4876 if (RES > 0) {
4877 struct vki_mmsghdr *mmsg = (struct vki_mmsghdr *)ARG2;
4878 HChar name[32];
4879 UInt i;
4880 for (i = 0; i < RES; i++) {
4881 VG_(sprintf)(name, "mmsg[%u].msg_hdr", i);
4882 ML_(generic_POST_sys_recvmsg)(tid, name, &mmsg[i].msg_hdr, mmsg[i].msg_len);
4883 POST_MEM_WRITE( (Addr)&mmsg[i].msg_len, sizeof(mmsg[i].msg_len) );
4888 /* ---------------------------------------------------------------------
4889 key retention service wrappers
4890 ------------------------------------------------------------------ */
4892 PRE(sys_request_key)
4894 PRINT("sys_request_key ( %#lx(%s), %#lx(%s), %#lx(%s), %ld )",
4895 ARG1,(char*)ARG1,ARG2,(char*)ARG2,ARG3,(char*)ARG3,ARG4);
4896 PRE_REG_READ4(long, "request_key",
4897 const char *, type, const char *, description,
4898 const char *, callout_info, vki_key_serial_t, keyring);
4899 PRE_MEM_RASCIIZ( "request_key(type)", ARG1);
4900 PRE_MEM_RASCIIZ( "request_key(description)", ARG2);
4901 if (ARG3 != (UWord)NULL)
4902 PRE_MEM_RASCIIZ( "request_key(callout_info)", ARG3);
4905 PRE(sys_add_key)
4907 PRINT("sys_add_key ( %#lx(%s), %#lx(%s), %#lx, %ld, %ld )",
4908 ARG1,(char*)ARG1,ARG2,(char*)ARG2,ARG3,ARG4,ARG5);
4909 PRE_REG_READ5(long, "add_key",
4910 const char *, type, const char *, description,
4911 const void *, payload, vki_size_t, plen,
4912 vki_key_serial_t, keyring);
4913 PRE_MEM_RASCIIZ( "add_key(type)", ARG1);
4914 PRE_MEM_RASCIIZ( "add_key(description)", ARG2);
4915 if (ARG3 != (UWord)NULL)
4916 PRE_MEM_READ( "request_key(payload)", ARG3, ARG4);
4919 PRE(sys_keyctl)
4921 switch (ARG1 /* option */) {
4922 case VKI_KEYCTL_GET_KEYRING_ID:
4923 PRINT("sys_keyctl ( KEYCTL_GET_KEYRING_ID, %ld, %ld )", ARG2,ARG3);
4924 PRE_REG_READ3(long, "keyctl(KEYCTL_GET_KEYRING_ID)",
4925 int, option, vki_key_serial_t, id, int, create);
4926 break;
4927 case VKI_KEYCTL_JOIN_SESSION_KEYRING:
4928 PRINT("sys_keyctl ( KEYCTL_JOIN_SESSION_KEYRING, %#lx(%s) )", ARG2,(char*)ARG2);
4929 PRE_REG_READ2(long, "keyctl(KEYCTL_JOIN_SESSION_KEYRING)",
4930 int, option, const char *, name);
4931 if (ARG2 != (UWord)NULL)
4932 PRE_MEM_RASCIIZ("keyctl(KEYCTL_JOIN_SESSION_KEYRING, name)", ARG2);
4933 break;
4934 case VKI_KEYCTL_UPDATE:
4935 PRINT("sys_keyctl ( KEYCTL_UPDATE, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
4936 PRE_REG_READ4(long, "keyctl(KEYCTL_UPDATE)",
4937 int, option, vki_key_serial_t, key,
4938 const void *, payload, vki_size_t, plen);
4939 if (ARG3 != (UWord)NULL)
4940 PRE_MEM_READ("keyctl(KEYCTL_UPDATE, payload)", ARG3, ARG4);
4941 break;
4942 case VKI_KEYCTL_REVOKE:
4943 PRINT("sys_keyctl ( KEYCTL_REVOKE, %ld )", ARG2);
4944 PRE_REG_READ2(long, "keyctl(KEYCTL_REVOKE)",
4945 int, option, vki_key_serial_t, id);
4946 break;
4947 case VKI_KEYCTL_CHOWN:
4948 PRINT("sys_keyctl ( KEYCTL_CHOWN, %ld, %ld, %ld )", ARG2,ARG3,ARG4);
4949 PRE_REG_READ4(long, "keyctl(KEYCTL_CHOWN)",
4950 int, option, vki_key_serial_t, id,
4951 vki_uid_t, uid, vki_gid_t, gid);
4952 break;
4953 case VKI_KEYCTL_SETPERM:
4954 PRINT("sys_keyctl ( KEYCTL_SETPERM, %ld, %ld )", ARG2,ARG3);
4955 PRE_REG_READ3(long, "keyctl(KEYCTL_SETPERM)",
4956 int, option, vki_key_serial_t, id, vki_key_perm_t, perm);
4957 break;
4958 case VKI_KEYCTL_DESCRIBE:
4959 PRINT("sys_keyctl ( KEYCTL_DESCRIBE, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
4960 PRE_REG_READ4(long, "keyctl(KEYCTL_DESCRIBE)",
4961 int, option, vki_key_serial_t, id,
4962 char *, buffer, vki_size_t, buflen);
4963 if (ARG3 != (UWord)NULL)
4964 PRE_MEM_WRITE("keyctl(KEYCTL_DESCRIBE, buffer)", ARG3, ARG4);
4965 break;
4966 case VKI_KEYCTL_CLEAR:
4967 PRINT("sys_keyctl ( KEYCTL_CLEAR, %ld )", ARG2);
4968 PRE_REG_READ2(long, "keyctl(KEYCTL_CLEAR)",
4969 int, option, vki_key_serial_t, keyring);
4970 break;
4971 case VKI_KEYCTL_LINK:
4972 PRINT("sys_keyctl ( KEYCTL_LINK, %ld, %ld )", ARG2,ARG3);
4973 PRE_REG_READ3(long, "keyctl(KEYCTL_LINK)", int, option,
4974 vki_key_serial_t, keyring, vki_key_serial_t, key);
4975 break;
4976 case VKI_KEYCTL_UNLINK:
4977 PRINT("sys_keyctl ( KEYCTL_UNLINK, %ld, %ld )", ARG2,ARG3);
4978 PRE_REG_READ3(long, "keyctl(KEYCTL_UNLINK)", int, option,
4979 vki_key_serial_t, keyring, vki_key_serial_t, key);
4980 break;
4981 case VKI_KEYCTL_SEARCH:
4982 PRINT("sys_keyctl ( KEYCTL_SEARCH, %ld, %#lx(%s), %#lx(%s), %ld )",
4983 ARG2,ARG3,(char*)ARG3,ARG4,(char*)ARG4,ARG5);
4984 PRE_REG_READ5(long, "keyctl(KEYCTL_SEARCH)",
4985 int, option, vki_key_serial_t, keyring,
4986 const char *, type, const char *, description,
4987 vki_key_serial_t, destring);
4988 PRE_MEM_RASCIIZ("sys_keyctl(KEYCTL_SEARCH, type)", ARG3);
4989 PRE_MEM_RASCIIZ("sys_keyctl(KEYCTL_SEARCH, description)", ARG4);
4990 break;
4991 case VKI_KEYCTL_READ:
4992 PRINT("sys_keyctl ( KEYCTL_READ, %ld, %#lx, %ld )", ARG2,ARG3,ARG4);
4993 PRE_REG_READ4(long, "keyctl(KEYCTL_READ)",
4994 int, option, vki_key_serial_t, keyring,
4995 char *, buffer, vki_size_t, buflen);
4996 if (ARG3 != (UWord)NULL)
4997 PRE_MEM_WRITE("keyctl(KEYCTL_READ, buffer)", ARG3, ARG4);
4998 break;
4999 case VKI_KEYCTL_INSTANTIATE:
5000 PRINT("sys_keyctl ( KEYCTL_INSTANTIATE, %ld, %#lx, %ld, %ld )",
5001 ARG2,ARG3,ARG4,ARG5);
5002 PRE_REG_READ5(long, "keyctl(KEYCTL_INSTANTIATE)",
5003 int, option, vki_key_serial_t, key,
5004 char *, payload, vki_size_t, plen,
5005 vki_key_serial_t, keyring);
5006 if (ARG3 != (UWord)NULL)
5007 PRE_MEM_READ("keyctl(KEYCTL_INSTANTIATE, payload)", ARG3, ARG4);
5008 break;
5009 case VKI_KEYCTL_NEGATE:
5010 PRINT("sys_keyctl ( KEYCTL_NEGATE, %ld, %lu, %ld )", ARG2,ARG3,ARG4);
5011 PRE_REG_READ4(long, "keyctl(KEYCTL_NEGATE)",
5012 int, option, vki_key_serial_t, key,
5013 unsigned, timeout, vki_key_serial_t, keyring);
5014 break;
5015 case VKI_KEYCTL_SET_REQKEY_KEYRING:
5016 PRINT("sys_keyctl ( KEYCTL_SET_REQKEY_KEYRING, %ld )", ARG2);
5017 PRE_REG_READ2(long, "keyctl(KEYCTL_SET_REQKEY_KEYRING)",
5018 int, option, int, reqkey_defl);
5019 break;
5020 case VKI_KEYCTL_SET_TIMEOUT:
5021 PRINT("sys_keyctl ( KEYCTL_SET_TIMEOUT, %ld, %ld )", ARG2,ARG3);
5022 PRE_REG_READ3(long, "keyctl(KEYCTL_SET_TIMEOUT)",
5023 int, option, vki_key_serial_t, key, unsigned, timeout);
5024 break;
5025 case VKI_KEYCTL_ASSUME_AUTHORITY:
5026 PRINT("sys_keyctl ( KEYCTL_ASSUME_AUTHORITY, %ld )", ARG2);
5027 PRE_REG_READ2(long, "keyctl(KEYCTL_ASSUME_AUTHORITY)",
5028 int, option, vki_key_serial_t, key);
5029 break;
5030 default:
5031 PRINT("sys_keyctl ( %ld ) ", ARG1);
5032 PRE_REG_READ1(long, "keyctl", int, option);
5033 break;
5037 POST(sys_keyctl)
5039 vg_assert(SUCCESS);
5040 switch (ARG1 /* option */) {
5041 case VKI_KEYCTL_DESCRIBE:
5042 case VKI_KEYCTL_READ:
5043 if (RES > ARG4)
5044 POST_MEM_WRITE(ARG3, ARG4);
5045 else
5046 POST_MEM_WRITE(ARG3, RES);
5047 break;
5048 default:
5049 break;
5053 /* ---------------------------------------------------------------------
5054 ioprio_ wrappers
5055 ------------------------------------------------------------------ */
5057 PRE(sys_ioprio_set)
5059 PRINT("sys_ioprio_set ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5060 PRE_REG_READ3(int, "ioprio_set", int, which, int, who, int, ioprio);
5063 PRE(sys_ioprio_get)
5065 PRINT("sys_ioprio_get ( %ld, %ld )", ARG1,ARG2);
5066 PRE_REG_READ2(int, "ioprio_get", int, which, int, who);
5069 /* ---------------------------------------------------------------------
5070 _module wrappers
5071 ------------------------------------------------------------------ */
5073 PRE(sys_init_module)
5075 *flags |= SfMayBlock;
5076 PRINT("sys_init_module ( %#lx, %llu, %#lx(\"%s\") )",
5077 ARG1, (ULong)ARG2, ARG3, (char*)ARG3);
5078 PRE_REG_READ3(long, "init_module",
5079 void *, umod, unsigned long, len, const char *, uargs);
5080 PRE_MEM_READ( "init_module(umod)", ARG1, ARG2 );
5081 PRE_MEM_RASCIIZ( "init_module(uargs)", ARG3 );
5084 PRE(sys_delete_module)
5086 *flags |= SfMayBlock;
5087 PRINT("sys_delete_module ( %#lx(\"%s\"), 0x%lx )", ARG1,(char*)ARG1, ARG2);
5088 PRE_REG_READ2(long, "delete_module",
5089 const char *, name_user, unsigned int, flags);
5090 PRE_MEM_RASCIIZ("delete_module(name_user)", ARG1);
5093 /* ---------------------------------------------------------------------
5094 splice wrappers
5095 ------------------------------------------------------------------ */
5097 PRE(sys_splice)
5099 *flags |= SfMayBlock;
5100 PRINT("sys_splice ( %ld, %#lx, %ld, %#lx, %ld, %ld )",
5101 ARG1,ARG2,ARG3,ARG4,ARG5,ARG6);
5102 PRE_REG_READ6(vki_ssize_t, "splice",
5103 int, fd_in, vki_loff_t *, off_in,
5104 int, fd_out, vki_loff_t *, off_out,
5105 vki_size_t, len, unsigned int, flags);
5106 if (!ML_(fd_allowed)(ARG1, "splice(fd_in)", tid, False) ||
5107 !ML_(fd_allowed)(ARG3, "splice(fd_out)", tid, False)) {
5108 SET_STATUS_Failure( VKI_EBADF );
5109 } else {
5110 if (ARG2 != 0)
5111 PRE_MEM_READ( "splice(off_in)", ARG2, sizeof(vki_loff_t));
5112 if (ARG4 != 0)
5113 PRE_MEM_READ( "splice(off_out)", ARG4, sizeof(vki_loff_t));
5117 PRE(sys_tee)
5119 *flags |= SfMayBlock;
5120 PRINT("sys_tree ( %ld, %ld, %ld, %ld )", ARG1,ARG2,ARG3,ARG4);
5121 PRE_REG_READ4(vki_ssize_t, "tee",
5122 int, fd_in, int, fd_out,
5123 vki_size_t, len, unsigned int, flags);
5124 if (!ML_(fd_allowed)(ARG1, "tee(fd_in)", tid, False) ||
5125 !ML_(fd_allowed)(ARG2, "tee(fd_out)", tid, False)) {
5126 SET_STATUS_Failure( VKI_EBADF );
5130 PRE(sys_vmsplice)
5132 Int fdfl;
5133 *flags |= SfMayBlock;
5134 PRINT("sys_vmsplice ( %ld, %#lx, %ld, %ld )",
5135 ARG1,ARG2,ARG3,ARG4);
5136 PRE_REG_READ4(vki_ssize_t, "splice",
5137 int, fd, struct vki_iovec *, iov,
5138 unsigned long, nr_segs, unsigned int, flags);
5139 if (!ML_(fd_allowed)(ARG1, "vmsplice(fd)", tid, False)) {
5140 SET_STATUS_Failure( VKI_EBADF );
5141 } else if ((fdfl = VG_(fcntl)(ARG1, VKI_F_GETFL, 0)) < 0) {
5142 SET_STATUS_Failure( VKI_EBADF );
5143 } else {
5144 const struct vki_iovec *iov;
5145 PRE_MEM_READ( "vmsplice(iov)", ARG2, sizeof(struct vki_iovec) * ARG3 );
5146 for (iov = (struct vki_iovec *)ARG2;
5147 iov < (struct vki_iovec *)ARG2 + ARG3; iov++)
5149 if ((fdfl & VKI_O_ACCMODE) == VKI_O_RDONLY)
5150 PRE_MEM_WRITE( "vmsplice(iov[...])", (Addr)iov->iov_base, iov->iov_len );
5151 else
5152 PRE_MEM_READ( "vmsplice(iov[...])", (Addr)iov->iov_base, iov->iov_len );
5157 POST(sys_vmsplice)
5159 vg_assert(SUCCESS);
5160 if (RES > 0) {
5161 Int fdfl = VG_(fcntl)(ARG1, VKI_F_GETFL, 0);
5162 vg_assert(fdfl >= 0);
5163 if ((fdfl & VKI_O_ACCMODE) == VKI_O_RDONLY)
5165 const struct vki_iovec *iov;
5166 for (iov = (struct vki_iovec *)ARG2;
5167 iov < (struct vki_iovec *)ARG2 + ARG3; iov++)
5169 POST_MEM_WRITE( (Addr)iov->iov_base, iov->iov_len );
5175 /* ---------------------------------------------------------------------
5176 oprofile-related wrappers
5177 ------------------------------------------------------------------ */
5179 #if defined(VGP_x86_linux)
5180 PRE(sys_lookup_dcookie)
5182 PRINT("sys_lookup_dcookie (0x%llx, %#lx, %ld)",
5183 MERGE64(ARG1,ARG2), ARG3, ARG4);
5184 PRE_REG_READ4(long, "lookup_dcookie",
5185 vki_u32, MERGE64_FIRST(cookie), vki_u32, MERGE64_SECOND(cookie),
5186 char *, buf, vki_size_t, len);
5187 PRE_MEM_WRITE( "lookup_dcookie(buf)", ARG3, ARG4);
5189 POST(sys_lookup_dcookie)
5191 vg_assert(SUCCESS);
5192 if (ARG3 != (Addr)NULL)
5193 POST_MEM_WRITE( ARG3, RES);
5195 #endif
5197 #if defined(VGP_amd64_linux) || defined(VGP_s390x_linux)
5198 PRE(sys_lookup_dcookie)
5200 *flags |= SfMayBlock;
5201 PRINT("sys_lookup_dcookie ( %llu, %#lx, %llu )",
5202 (ULong)ARG1, ARG2, (ULong)ARG3);
5203 PRE_REG_READ3(int, "lookup_dcookie",
5204 unsigned long long, cookie, char *, buf, vki_size_t, len);
5206 PRE_MEM_WRITE( "sys_lookup_dcookie(buf)", ARG2, ARG3 );
5209 POST(sys_lookup_dcookie)
5211 vg_assert(SUCCESS);
5212 if (ARG2 != (Addr)NULL)
5213 POST_MEM_WRITE( ARG2, RES );
5215 #endif
5217 /* ---------------------------------------------------------------------
5218 fcntl wrappers
5219 ------------------------------------------------------------------ */
5221 PRE(sys_fcntl)
5223 switch (ARG2) {
5224 // These ones ignore ARG3.
5225 case VKI_F_GETFD:
5226 case VKI_F_GETFL:
5227 case VKI_F_GETOWN:
5228 case VKI_F_GETSIG:
5229 case VKI_F_GETLEASE:
5230 case VKI_F_GETPIPE_SZ:
5231 PRINT("sys_fcntl ( %ld, %ld )", ARG1,ARG2);
5232 PRE_REG_READ2(long, "fcntl", unsigned int, fd, unsigned int, cmd);
5233 break;
5235 // These ones use ARG3 as "arg".
5236 case VKI_F_DUPFD:
5237 case VKI_F_DUPFD_CLOEXEC:
5238 case VKI_F_SETFD:
5239 case VKI_F_SETFL:
5240 case VKI_F_SETLEASE:
5241 case VKI_F_NOTIFY:
5242 case VKI_F_SETOWN:
5243 case VKI_F_SETSIG:
5244 case VKI_F_SETPIPE_SZ:
5245 PRINT("sys_fcntl[ARG3=='arg'] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5246 PRE_REG_READ3(long, "fcntl",
5247 unsigned int, fd, unsigned int, cmd, unsigned long, arg);
5248 break;
5250 // These ones use ARG3 as "lock".
5251 case VKI_F_GETLK:
5252 case VKI_F_SETLK:
5253 case VKI_F_SETLKW:
5254 # if defined(VGP_x86_linux) || defined(VGP_mips64_linux)
5255 case VKI_F_GETLK64:
5256 case VKI_F_SETLK64:
5257 case VKI_F_SETLKW64:
5258 # endif
5259 case VKI_F_OFD_GETLK:
5260 case VKI_F_OFD_SETLK:
5261 case VKI_F_OFD_SETLKW:
5262 PRINT("sys_fcntl[ARG3=='lock'] ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
5263 PRE_REG_READ3(long, "fcntl",
5264 unsigned int, fd, unsigned int, cmd,
5265 struct flock64 *, lock);
5266 break;
5268 case VKI_F_SETOWN_EX:
5269 PRINT("sys_fcntl[F_SETOWN_EX] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5270 PRE_REG_READ3(long, "fcntl",
5271 unsigned int, fd, unsigned int, cmd,
5272 struct vki_f_owner_ex *, arg);
5273 PRE_MEM_READ("fcntl(F_SETOWN_EX)", ARG3, sizeof(struct vki_f_owner_ex));
5274 break;
5276 case VKI_F_GETOWN_EX:
5277 PRINT("sys_fcntl[F_GETOWN_EX] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5278 PRE_REG_READ3(long, "fcntl",
5279 unsigned int, fd, unsigned int, cmd,
5280 struct vki_f_owner_ex *, arg);
5281 PRE_MEM_WRITE("fcntl(F_GETOWN_EX)", ARG3, sizeof(struct vki_f_owner_ex));
5282 break;
5284 default:
5285 PRINT("sys_fcntl[UNKNOWN] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5286 I_die_here;
5287 break;
5290 # if defined(VGP_x86_linux)
5291 if (ARG2 == VKI_F_SETLKW || ARG2 == VKI_F_SETLKW64)
5292 # else
5293 if (ARG2 == VKI_F_SETLKW)
5294 # endif
5295 *flags |= SfMayBlock;
5298 POST(sys_fcntl)
5300 vg_assert(SUCCESS);
5301 if (ARG2 == VKI_F_DUPFD) {
5302 if (!ML_(fd_allowed)(RES, "fcntl(DUPFD)", tid, True)) {
5303 VG_(close)(RES);
5304 SET_STATUS_Failure( VKI_EMFILE );
5305 } else {
5306 if (VG_(clo_track_fds))
5307 ML_(record_fd_open_named)(tid, RES);
5310 else if (ARG2 == VKI_F_DUPFD_CLOEXEC) {
5311 if (!ML_(fd_allowed)(RES, "fcntl(DUPFD_CLOEXEC)", tid, True)) {
5312 VG_(close)(RES);
5313 SET_STATUS_Failure( VKI_EMFILE );
5314 } else {
5315 if (VG_(clo_track_fds))
5316 ML_(record_fd_open_named)(tid, RES);
5318 } else if (ARG2 == VKI_F_GETOWN_EX) {
5319 POST_MEM_WRITE(ARG3, sizeof(struct vki_f_owner_ex));
5323 // XXX: wrapper only suitable for 32-bit systems
5324 PRE(sys_fcntl64)
5326 switch (ARG2) {
5327 // These ones ignore ARG3.
5328 case VKI_F_GETFD:
5329 case VKI_F_GETFL:
5330 case VKI_F_GETOWN:
5331 case VKI_F_SETOWN:
5332 case VKI_F_GETSIG:
5333 case VKI_F_SETSIG:
5334 case VKI_F_GETLEASE:
5335 PRINT("sys_fcntl64 ( %ld, %ld )", ARG1,ARG2);
5336 PRE_REG_READ2(long, "fcntl64", unsigned int, fd, unsigned int, cmd);
5337 break;
5339 // These ones use ARG3 as "arg".
5340 case VKI_F_DUPFD:
5341 case VKI_F_DUPFD_CLOEXEC:
5342 case VKI_F_SETFD:
5343 case VKI_F_SETFL:
5344 case VKI_F_SETLEASE:
5345 case VKI_F_NOTIFY:
5346 PRINT("sys_fcntl64[ARG3=='arg'] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5347 PRE_REG_READ3(long, "fcntl64",
5348 unsigned int, fd, unsigned int, cmd, unsigned long, arg);
5349 break;
5351 // These ones use ARG3 as "lock".
5352 case VKI_F_GETLK:
5353 case VKI_F_SETLK:
5354 case VKI_F_SETLKW:
5355 # if defined(VGP_x86_linux)
5356 case VKI_F_GETLK64:
5357 case VKI_F_SETLK64:
5358 case VKI_F_SETLKW64:
5359 # endif
5360 case VKI_F_OFD_GETLK:
5361 case VKI_F_OFD_SETLK:
5362 case VKI_F_OFD_SETLKW:
5363 PRINT("sys_fcntl64[ARG3=='lock'] ( %ld, %ld, %#lx )", ARG1,ARG2,ARG3);
5364 PRE_REG_READ3(long, "fcntl64",
5365 unsigned int, fd, unsigned int, cmd,
5366 struct flock64 *, lock);
5367 break;
5369 case VKI_F_SETOWN_EX:
5370 PRINT("sys_fcntl[F_SETOWN_EX] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5371 PRE_REG_READ3(long, "fcntl",
5372 unsigned int, fd, unsigned int, cmd,
5373 struct vki_f_owner_ex *, arg);
5374 PRE_MEM_READ("fcntl(F_SETOWN_EX)", ARG3, sizeof(struct vki_f_owner_ex));
5375 break;
5377 case VKI_F_GETOWN_EX:
5378 PRINT("sys_fcntl[F_GETOWN_EX] ( %ld, %ld, %ld )", ARG1,ARG2,ARG3);
5379 PRE_REG_READ3(long, "fcntl",
5380 unsigned int, fd, unsigned int, cmd,
5381 struct vki_f_owner_ex *, arg);
5382 PRE_MEM_WRITE("fcntl(F_GETOWN_EX)", ARG3, sizeof(struct vki_f_owner_ex));
5383 break;
5386 # if defined(VGP_x86_linux)
5387 if (ARG2 == VKI_F_SETLKW || ARG2 == VKI_F_SETLKW64)
5388 # else
5389 if (ARG2 == VKI_F_SETLKW)
5390 # endif
5391 *flags |= SfMayBlock;
5394 POST(sys_fcntl64)
5396 vg_assert(SUCCESS);
5397 if (ARG2 == VKI_F_DUPFD) {
5398 if (!ML_(fd_allowed)(RES, "fcntl64(DUPFD)", tid, True)) {
5399 VG_(close)(RES);
5400 SET_STATUS_Failure( VKI_EMFILE );
5401 } else {
5402 if (VG_(clo_track_fds))
5403 ML_(record_fd_open_named)(tid, RES);
5406 else if (ARG2 == VKI_F_DUPFD_CLOEXEC) {
5407 if (!ML_(fd_allowed)(RES, "fcntl64(DUPFD_CLOEXEC)", tid, True)) {
5408 VG_(close)(RES);
5409 SET_STATUS_Failure( VKI_EMFILE );
5410 } else {
5411 if (VG_(clo_track_fds))
5412 ML_(record_fd_open_named)(tid, RES);
5414 } else if (ARG2 == VKI_F_GETOWN_EX) {
5415 POST_MEM_WRITE(ARG3, sizeof(struct vki_f_owner_ex));
5419 /* ---------------------------------------------------------------------
5420 ioctl wrappers
5421 ------------------------------------------------------------------ */
5423 PRE(sys_ioctl)
5425 *flags |= SfMayBlock;
5427 ARG2 = (UInt)ARG2;
5429 // We first handle the ones that don't use ARG3 (even as a
5430 // scalar/non-pointer argument).
5431 switch (ARG2 /* request */) {
5433 /* asm-generic/ioctls.h */
5434 case VKI_FIOCLEX:
5435 case VKI_FIONCLEX:
5436 case VKI_TIOCNOTTY:
5438 /* linux/soundcard interface (ALSA) */
5439 case VKI_SNDRV_PCM_IOCTL_HW_FREE:
5440 case VKI_SNDRV_PCM_IOCTL_HWSYNC:
5441 case VKI_SNDRV_PCM_IOCTL_PREPARE:
5442 case VKI_SNDRV_PCM_IOCTL_RESET:
5443 case VKI_SNDRV_PCM_IOCTL_START:
5444 case VKI_SNDRV_PCM_IOCTL_DROP:
5445 case VKI_SNDRV_PCM_IOCTL_DRAIN:
5446 case VKI_SNDRV_PCM_IOCTL_RESUME:
5447 case VKI_SNDRV_PCM_IOCTL_XRUN:
5448 case VKI_SNDRV_PCM_IOCTL_UNLINK:
5449 case VKI_SNDRV_TIMER_IOCTL_START:
5450 case VKI_SNDRV_TIMER_IOCTL_STOP:
5451 case VKI_SNDRV_TIMER_IOCTL_CONTINUE:
5452 case VKI_SNDRV_TIMER_IOCTL_PAUSE:
5454 /* SCSI no operand */
5455 case VKI_SCSI_IOCTL_DOORLOCK:
5456 case VKI_SCSI_IOCTL_DOORUNLOCK:
5458 /* CDROM stuff. */
5459 case VKI_CDROM_DISC_STATUS:
5461 /* KVM ioctls that dont check for a numeric value as parameter */
5462 case VKI_KVM_S390_ENABLE_SIE:
5463 case VKI_KVM_CREATE_IRQCHIP:
5464 case VKI_KVM_S390_INITIAL_RESET:
5465 case VKI_KVM_KVMCLOCK_CTRL:
5467 /* vhost without parameter */
5468 case VKI_VHOST_SET_OWNER:
5469 case VKI_VHOST_RESET_OWNER:
5471 /* User input device creation */
5472 case VKI_UI_DEV_CREATE:
5473 case VKI_UI_DEV_DESTROY:
5475 /* InfiniBand */
5476 case VKI_IB_USER_MAD_ENABLE_PKEY:
5478 /* V4L2 */
5479 case VKI_V4L2_LOG_STATUS:
5480 PRINT("sys_ioctl ( %ld, 0x%lx )",ARG1,ARG2);
5481 PRE_REG_READ2(long, "ioctl",
5482 unsigned int, fd, unsigned int, request);
5483 return;
5485 default:
5486 PRINT("sys_ioctl ( %ld, 0x%lx, 0x%lx )",ARG1,ARG2,ARG3);
5487 PRE_REG_READ3(long, "ioctl",
5488 unsigned int, fd, unsigned int, request, unsigned long, arg);
5489 break;
5492 // We now handle those that do look at ARG3 (and unknown ones fall into
5493 // this category). Nb: some of these may well belong in the
5494 // doesn't-use-ARG3 switch above.
5495 switch (ARG2 /* request */) {
5496 case VKI_TCSETS:
5497 case VKI_TCSETSW:
5498 case VKI_TCSETSF:
5499 PRE_MEM_READ( "ioctl(TCSET{S,SW,SF})", ARG3, sizeof(struct vki_termios) );
5500 break;
5501 case VKI_TCGETS:
5502 PRE_MEM_WRITE( "ioctl(TCGETS)", ARG3, sizeof(struct vki_termios) );
5503 break;
5504 case VKI_TCSETA:
5505 case VKI_TCSETAW:
5506 case VKI_TCSETAF:
5507 PRE_MEM_READ( "ioctl(TCSET{A,AW,AF})", ARG3, sizeof(struct vki_termio) );
5508 break;
5509 case VKI_TCGETA:
5510 PRE_MEM_WRITE( "ioctl(TCGETA)", ARG3, sizeof(struct vki_termio) );
5511 break;
5512 case VKI_TCSBRK:
5513 case VKI_TCXONC:
5514 case VKI_TCSBRKP:
5515 case VKI_TCFLSH:
5516 case VKI_TIOCSIG:
5517 /* These just take an int by value */
5518 break;
5519 case VKI_TIOCGWINSZ:
5520 PRE_MEM_WRITE( "ioctl(TIOCGWINSZ)", ARG3, sizeof(struct vki_winsize) );
5521 break;
5522 case VKI_TIOCSWINSZ:
5523 PRE_MEM_READ( "ioctl(TIOCSWINSZ)", ARG3, sizeof(struct vki_winsize) );
5524 break;
5525 case VKI_TIOCMBIS:
5526 PRE_MEM_READ( "ioctl(TIOCMBIS)", ARG3, sizeof(unsigned int) );
5527 break;
5528 case VKI_TIOCMBIC:
5529 PRE_MEM_READ( "ioctl(TIOCMBIC)", ARG3, sizeof(unsigned int) );
5530 break;
5531 case VKI_TIOCMSET:
5532 PRE_MEM_READ( "ioctl(TIOCMSET)", ARG3, sizeof(unsigned int) );
5533 break;
5534 case VKI_TIOCMGET:
5535 PRE_MEM_WRITE( "ioctl(TIOCMGET)", ARG3, sizeof(unsigned int) );
5536 break;
5537 case VKI_TIOCLINUX:
5538 PRE_MEM_READ( "ioctl(TIOCLINUX)", ARG3, sizeof(char *) );
5539 if (*(char *)ARG3 == 11) {
5540 PRE_MEM_READ( "ioctl(TIOCLINUX, 11)", ARG3, 2 * sizeof(char *) );
5542 break;
5543 case VKI_TIOCGPGRP:
5544 /* Get process group ID for foreground processing group. */
5545 PRE_MEM_WRITE( "ioctl(TIOCGPGRP)", ARG3, sizeof(vki_pid_t) );
5546 break;
5547 case VKI_TIOCSPGRP:
5548 /* Set a process group ID? */
5549 PRE_MEM_WRITE( "ioctl(TIOCGPGRP)", ARG3, sizeof(vki_pid_t) );
5550 break;
5551 case VKI_TIOCGPTN: /* Get Pty Number (of pty-mux device) */
5552 PRE_MEM_WRITE( "ioctl(TIOCGPTN)", ARG3, sizeof(int) );
5553 break;
5554 case VKI_TIOCSCTTY:
5555 /* Just takes an int value. */
5556 break;
5557 case VKI_TIOCSPTLCK: /* Lock/unlock Pty */
5558 PRE_MEM_READ( "ioctl(TIOCSPTLCK)", ARG3, sizeof(int) );
5559 break;
5560 case VKI_FIONBIO:
5561 PRE_MEM_READ( "ioctl(FIONBIO)", ARG3, sizeof(int) );
5562 break;
5563 case VKI_FIOASYNC:
5564 PRE_MEM_READ( "ioctl(FIOASYNC)", ARG3, sizeof(int) );
5565 break;
5566 case VKI_FIONREAD: /* identical to SIOCINQ */
5567 PRE_MEM_WRITE( "ioctl(FIONREAD)", ARG3, sizeof(int) );
5568 break;
5569 case VKI_FIOQSIZE:
5570 PRE_MEM_WRITE( "ioctl(FIOQSIZE)", ARG3, sizeof(vki_loff_t) );
5571 break;
5573 case VKI_TIOCSERGETLSR:
5574 PRE_MEM_WRITE( "ioctl(TIOCSERGETLSR)", ARG3, sizeof(int) );
5575 break;
5576 case VKI_TIOCGICOUNT:
5577 PRE_MEM_WRITE( "ioctl(TIOCGICOUNT)", ARG3,
5578 sizeof(struct vki_serial_icounter_struct) );
5579 break;
5581 case VKI_SG_SET_COMMAND_Q:
5582 PRE_MEM_READ( "ioctl(SG_SET_COMMAND_Q)", ARG3, sizeof(int) );
5583 break;
5584 case VKI_SG_IO:
5585 PRE_MEM_READ( "ioctl(SG_IO)", ARG3, sizeof(vki_sg_io_hdr_t) );
5587 vki_sg_io_hdr_t *sgio = (vki_sg_io_hdr_t*)ARG3;
5588 PRE_MEM_READ( "ioctl(SG_IO)", (Addr)sgio->cmdp, sgio->cmd_len );
5589 if ( sgio->dxfer_direction == VKI_SG_DXFER_TO_DEV ||
5590 sgio->dxfer_direction == VKI_SG_DXFER_TO_FROM_DEV ) {
5591 PRE_MEM_READ( "ioctl(SG_IO)", (Addr)sgio->dxferp, sgio->dxfer_len );
5594 break;
5595 case VKI_SG_GET_SCSI_ID:
5596 PRE_MEM_WRITE( "ioctl(SG_GET_SCSI_ID)", ARG3, sizeof(vki_sg_scsi_id_t) );
5597 break;
5598 case VKI_SG_SET_RESERVED_SIZE:
5599 PRE_MEM_READ( "ioctl(SG_SET_RESERVED_SIZE)", ARG3, sizeof(int) );
5600 break;
5601 case VKI_SG_SET_TIMEOUT:
5602 PRE_MEM_READ( "ioctl(SG_SET_TIMEOUT)", ARG3, sizeof(int) );
5603 break;
5604 case VKI_SG_GET_RESERVED_SIZE:
5605 PRE_MEM_WRITE( "ioctl(SG_GET_RESERVED_SIZE)", ARG3, sizeof(int) );
5606 break;
5607 case VKI_SG_GET_TIMEOUT:
5608 break;
5609 case VKI_SG_GET_VERSION_NUM:
5610 PRE_MEM_WRITE( "ioctl(SG_GET_VERSION_NUM)", ARG3, sizeof(int) );
5611 break;
5612 case VKI_SG_EMULATED_HOST: /* 0x2203 */
5613 PRE_MEM_WRITE( "ioctl(SG_EMULATED_HOST)", ARG3, sizeof(int) );
5614 break;
5615 case VKI_SG_GET_SG_TABLESIZE: /* 0x227f */
5616 PRE_MEM_WRITE( "ioctl(SG_GET_SG_TABLESIZE)", ARG3, sizeof(int) );
5617 break;
5619 case VKI_IIOCGETCPS:
5620 PRE_MEM_WRITE( "ioctl(IIOCGETCPS)", ARG3,
5621 VKI_ISDN_MAX_CHANNELS * 2 * sizeof(unsigned long) );
5622 break;
5623 case VKI_IIOCNETGPN:
5624 PRE_MEM_READ( "ioctl(IIOCNETGPN)",
5625 (Addr)&((vki_isdn_net_ioctl_phone *)ARG3)->name,
5626 sizeof(((vki_isdn_net_ioctl_phone *)ARG3)->name) );
5627 PRE_MEM_WRITE( "ioctl(IIOCNETGPN)", ARG3,
5628 sizeof(vki_isdn_net_ioctl_phone) );
5629 break;
5631 /* These all use struct ifreq AFAIK */
5632 case VKI_SIOCGIFINDEX: /* get iface index */
5633 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFINDEX)",
5634 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5635 PRE_MEM_WRITE( "ioctl(SIOCGIFINDEX)", ARG3, sizeof(struct vki_ifreq));
5636 break;
5637 case VKI_SIOCGIFFLAGS: /* get flags */
5638 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFFLAGS)",
5639 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5640 PRE_MEM_WRITE( "ioctl(SIOCGIFFLAGS)", ARG3, sizeof(struct vki_ifreq));
5641 break;
5642 case VKI_SIOCGIFHWADDR: /* Get hardware address */
5643 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFHWADDR)",
5644 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5645 PRE_MEM_WRITE( "ioctl(SIOCGIFHWADDR)", ARG3, sizeof(struct vki_ifreq));
5646 break;
5647 case VKI_SIOCGIFMTU: /* get MTU size */
5648 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMTU)",
5649 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5650 PRE_MEM_WRITE( "ioctl(SIOCGIFMTU)", ARG3, sizeof(struct vki_ifreq));
5651 break;
5652 case VKI_SIOCGIFADDR: /* get PA address */
5653 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFADDR)",
5654 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5655 PRE_MEM_WRITE( "ioctl(SIOCGIFADDR)", ARG3, sizeof(struct vki_ifreq));
5656 break;
5657 case VKI_SIOCGIFNETMASK: /* get network PA mask */
5658 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFNETMASK)",
5659 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5660 PRE_MEM_WRITE( "ioctl(SIOCGIFNETMASK)", ARG3, sizeof(struct vki_ifreq));
5661 break;
5662 case VKI_SIOCGIFMETRIC: /* get metric */
5663 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMETRIC)",
5664 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5665 PRE_MEM_WRITE( "ioctl(SIOCGIFMETRIC)", ARG3, sizeof(struct vki_ifreq));
5666 break;
5667 case VKI_SIOCGIFMAP: /* Get device parameters */
5668 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMAP)",
5669 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5670 PRE_MEM_WRITE( "ioctl(SIOCGIFMAP)", ARG3, sizeof(struct vki_ifreq));
5671 break;
5672 case VKI_SIOCGIFTXQLEN: /* Get the tx queue length */
5673 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFTXQLEN)",
5674 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5675 PRE_MEM_WRITE( "ioctl(SIOCGIFTXQLEN)", ARG3, sizeof(struct vki_ifreq));
5676 break;
5677 case VKI_SIOCGIFDSTADDR: /* get remote PA address */
5678 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFDSTADDR)",
5679 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5680 PRE_MEM_WRITE( "ioctl(SIOCGIFDSTADDR)", ARG3, sizeof(struct vki_ifreq));
5681 break;
5682 case VKI_SIOCGIFBRDADDR: /* get broadcast PA address */
5683 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFBRDADDR)",
5684 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5685 PRE_MEM_WRITE( "ioctl(SIOCGIFBRDADDR)", ARG3, sizeof(struct vki_ifreq));
5686 break;
5687 case VKI_SIOCGIFNAME: /* get iface name */
5688 PRE_MEM_READ( "ioctl(SIOCGIFNAME)",
5689 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_ifindex,
5690 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_ifindex) );
5691 PRE_MEM_WRITE( "ioctl(SIOCGIFNAME)", ARG3, sizeof(struct vki_ifreq));
5692 break;
5693 case VKI_SIOCETHTOOL: { /* ethtool(8) interface */
5694 struct vki_ifreq *ir = (struct vki_ifreq *)ARG3;
5695 PRE_MEM_READ( "ioctl(SIOCETHTOOL)", (Addr)ir, sizeof(struct vki_ifreq) );
5696 PRE_MEM_RASCIIZ( "ioctl(SIOCETHTOOL)", (Addr)ir->vki_ifr_name );
5697 PRE_MEM_READ( "ioctl(SIOCETHTOOL)", (Addr)ir->vki_ifr_data, sizeof(vki_u32) );
5698 PRINT("SIOCETHTOOL( 0x%x )", *(vki_u32 *)ir->vki_ifr_data );
5699 switch ( *(vki_u32 *)ir->vki_ifr_data ) {
5700 case VKI_ETHTOOL_GSET:
5701 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GSET)",
5702 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_cmd) );
5703 break;
5704 case VKI_ETHTOOL_SSET:
5705 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SSET)",
5706 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_cmd) );
5707 break;
5708 case VKI_ETHTOOL_GDRVINFO:
5709 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GDRVINFO)",
5710 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_drvinfo) );
5711 break;
5712 case VKI_ETHTOOL_GREGS:
5713 PRE_MEM_READ( "ioctl(SIOCETHTOOL,GREGS)",
5714 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_regs) );
5715 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GREGS)",
5716 (Addr)((struct vki_ethtool_regs *)ir->vki_ifr_data)->data,
5717 ((struct vki_ethtool_regs *)ir->vki_ifr_data)->len );
5718 break;
5719 case VKI_ETHTOOL_GWOL:
5720 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GWOL)",
5721 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_wolinfo) );
5722 break;
5723 case VKI_ETHTOOL_SWOL:
5724 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SWOL)",
5725 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_wolinfo) );
5726 break;
5727 case VKI_ETHTOOL_GMSGLVL:
5728 case VKI_ETHTOOL_GLINK:
5729 case VKI_ETHTOOL_GRXCSUM:
5730 case VKI_ETHTOOL_GSG:
5731 case VKI_ETHTOOL_GTSO:
5732 case VKI_ETHTOOL_GUFO:
5733 case VKI_ETHTOOL_GGSO:
5734 case VKI_ETHTOOL_GFLAGS:
5735 case VKI_ETHTOOL_GGRO:
5736 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,Gvalue)",
5737 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_value) );
5738 break;
5739 case VKI_ETHTOOL_SMSGLVL:
5740 case VKI_ETHTOOL_SRXCSUM:
5741 case VKI_ETHTOOL_SSG:
5742 case VKI_ETHTOOL_STSO:
5743 case VKI_ETHTOOL_SUFO:
5744 case VKI_ETHTOOL_SGSO:
5745 case VKI_ETHTOOL_SFLAGS:
5746 case VKI_ETHTOOL_SGRO:
5747 PRE_MEM_READ( "ioctl(SIOCETHTOOL,Svalue)",
5748 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_value) );
5749 break;
5750 case VKI_ETHTOOL_NWAY_RST:
5751 break;
5752 case VKI_ETHTOOL_GRINGPARAM:
5753 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GRINGPARAM)",
5754 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_ringparam) );
5755 break;
5756 case VKI_ETHTOOL_SRINGPARAM:
5757 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SRINGPARAM)",
5758 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_ringparam) );
5759 break;
5760 case VKI_ETHTOOL_TEST:
5761 PRE_MEM_READ( "ioctl(SIOCETHTOOL,TEST)",
5762 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_test) );
5763 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,TEST)",
5764 (Addr)((struct vki_ethtool_test *)ir->vki_ifr_data)->data,
5765 ((struct vki_ethtool_test *)ir->vki_ifr_data)->len * sizeof(__vki_u64) );
5766 break;
5767 case VKI_ETHTOOL_PHYS_ID:
5768 break;
5769 case VKI_ETHTOOL_GPERMADDR:
5770 PRE_MEM_READ( "ioctl(SIOCETHTOOL,GPERMADDR)",
5771 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_perm_addr) );
5772 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GPERMADDR)",
5773 (Addr)((struct vki_ethtool_perm_addr *)ir->vki_ifr_data)->data,
5774 ((struct vki_ethtool_perm_addr *)ir->vki_ifr_data)->size );
5775 break;
5776 case VKI_ETHTOOL_RESET:
5777 break;
5778 case VKI_ETHTOOL_GSSET_INFO:
5779 PRE_MEM_READ( "ioctl(SIOCETHTOOL,GSSET_INFO)",
5780 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_sset_info) );
5781 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GSSET_INFO)",
5782 (Addr)((struct vki_ethtool_sset_info *)ir->vki_ifr_data)->data,
5783 __builtin_popcountll(((struct vki_ethtool_sset_info *)ir->vki_ifr_data)->sset_mask) * sizeof(__vki_u32) );
5784 break;
5785 case VKI_ETHTOOL_GFEATURES:
5786 PRE_MEM_READ( "ioctl(SIOCETHTOOL,GFEATURES)",
5787 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_gfeatures) );
5788 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GFEATURES)",
5789 (Addr)((struct vki_ethtool_gfeatures *)ir->vki_ifr_data)->features,
5790 ((struct vki_ethtool_gfeatures *)ir->vki_ifr_data)->size * sizeof(struct vki_ethtool_get_features_block) );
5791 break;
5792 case VKI_ETHTOOL_SFEATURES:
5793 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SFEATURES)",
5794 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_sfeatures) );
5795 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SFEATURES)",
5796 (Addr)((struct vki_ethtool_sfeatures *)ir->vki_ifr_data)->features,
5797 ((struct vki_ethtool_sfeatures *)ir->vki_ifr_data)->size * sizeof(struct vki_ethtool_set_features_block) );
5798 break;
5799 case VKI_ETHTOOL_GCHANNELS:
5800 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GCHANNELS)",
5801 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_channels) );
5802 break;
5803 case VKI_ETHTOOL_SCHANNELS:
5804 PRE_MEM_READ( "ioctl(SIOCETHTOOL,SCHANNELS)",
5805 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_channels) );
5806 break;
5807 case VKI_ETHTOOL_GET_TS_INFO:
5808 PRE_MEM_WRITE( "ioctl(SIOCETHTOOL,GET_TS_INFO)",
5809 (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_ts_info) );
5810 break;
5812 break;
5814 case VKI_SIOCGMIIPHY: /* get hardware entry */
5815 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMIIPHY)",
5816 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5817 PRE_MEM_WRITE( "ioctl(SIOCGIFMIIPHY)", ARG3, sizeof(struct vki_ifreq));
5818 break;
5819 case VKI_SIOCGMIIREG: /* get hardware entry registers */
5820 PRE_MEM_RASCIIZ( "ioctl(SIOCGIFMIIREG)",
5821 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5822 PRE_MEM_READ( "ioctl(SIOCGIFMIIREG)",
5823 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
5824 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
5825 PRE_MEM_READ( "ioctl(SIOCGIFMIIREG)",
5826 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num,
5827 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num) );
5828 PRE_MEM_WRITE( "ioctl(SIOCGIFMIIREG)", ARG3,
5829 sizeof(struct vki_ifreq));
5830 break;
5831 case VKI_SIOCGIFCONF: /* get iface list */
5832 /* WAS:
5833 PRE_MEM_WRITE( "ioctl(SIOCGIFCONF)", ARG3, sizeof(struct ifconf));
5834 KERNEL_DO_SYSCALL(tid,RES);
5835 if (!VG_(is_kerror)(RES) && RES == 0)
5836 POST_MEM_WRITE(ARG3, sizeof(struct ifconf));
5838 PRE_MEM_READ( "ioctl(SIOCGIFCONF)",
5839 (Addr)&((struct vki_ifconf *)ARG3)->ifc_len,
5840 sizeof(((struct vki_ifconf *)ARG3)->ifc_len));
5841 PRE_MEM_READ( "ioctl(SIOCGIFCONF)",
5842 (Addr)&((struct vki_ifconf *)ARG3)->vki_ifc_buf,
5843 sizeof(((struct vki_ifconf *)ARG3)->vki_ifc_buf));
5844 if ( ARG3 ) {
5845 // TODO len must be readable and writable
5846 // buf pointer only needs to be readable
5847 struct vki_ifconf *ifc = (struct vki_ifconf *) ARG3;
5848 PRE_MEM_WRITE( "ioctl(SIOCGIFCONF).ifc_buf",
5849 (Addr)(ifc->vki_ifc_buf), ifc->ifc_len );
5851 break;
5852 case VKI_SIOCGSTAMP:
5853 PRE_MEM_WRITE( "ioctl(SIOCGSTAMP)", ARG3, sizeof(struct vki_timeval));
5854 break;
5855 case VKI_SIOCGSTAMPNS:
5856 PRE_MEM_WRITE( "ioctl(SIOCGSTAMPNS)", ARG3, sizeof(struct vki_timespec));
5857 break;
5858 /* SIOCOUTQ is an ioctl that, when called on a socket, returns
5859 the number of bytes currently in that socket's send buffer.
5860 It writes this value as an int to the memory location
5861 indicated by the third argument of ioctl(2). */
5862 case VKI_SIOCOUTQ:
5863 PRE_MEM_WRITE( "ioctl(SIOCOUTQ)", ARG3, sizeof(int));
5864 break;
5865 case VKI_SIOCGRARP: /* get RARP table entry */
5866 case VKI_SIOCGARP: /* get ARP table entry */
5867 PRE_MEM_WRITE( "ioctl(SIOCGARP)", ARG3, sizeof(struct vki_arpreq));
5868 break;
5870 case VKI_SIOCSIFFLAGS: /* set flags */
5871 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFFLAGS)",
5872 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5873 PRE_MEM_READ( "ioctl(SIOCSIFFLAGS)",
5874 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
5875 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
5876 break;
5877 case VKI_SIOCSIFMAP: /* Set device parameters */
5878 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMAP)",
5879 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5880 PRE_MEM_READ( "ioctl(SIOCSIFMAP)",
5881 (Addr)&((struct vki_ifreq *)ARG3)->ifr_map,
5882 sizeof(((struct vki_ifreq *)ARG3)->ifr_map) );
5883 break;
5884 case VKI_SIOCSHWTSTAMP: /* Set hardware time stamping */
5885 PRE_MEM_RASCIIZ( "ioctl(SIOCSHWTSTAMP)",
5886 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5887 PRE_MEM_READ( "ioctl(SIOCSHWTSTAMP)",
5888 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_data,
5889 sizeof(struct vki_hwtstamp_config) );
5890 break;
5891 case VKI_SIOCSIFTXQLEN: /* Set the tx queue length */
5892 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFTXQLEN)",
5893 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5894 PRE_MEM_READ( "ioctl(SIOCSIFTXQLEN)",
5895 (Addr)&((struct vki_ifreq *)ARG3)->ifr_qlen,
5896 sizeof(((struct vki_ifreq *)ARG3)->ifr_qlen) );
5897 break;
5898 case VKI_SIOCSIFADDR: /* set PA address */
5899 case VKI_SIOCSIFDSTADDR: /* set remote PA address */
5900 case VKI_SIOCSIFBRDADDR: /* set broadcast PA address */
5901 case VKI_SIOCSIFNETMASK: /* set network PA mask */
5902 PRE_MEM_RASCIIZ( "ioctl(SIOCSIF*ADDR)",
5903 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5904 PRE_MEM_READ( "ioctl(SIOCSIF*ADDR)",
5905 (Addr)&((struct vki_ifreq *)ARG3)->ifr_addr,
5906 sizeof(((struct vki_ifreq *)ARG3)->ifr_addr) );
5907 break;
5908 case VKI_SIOCSIFMETRIC: /* set metric */
5909 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMETRIC)",
5910 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5911 PRE_MEM_READ( "ioctl(SIOCSIFMETRIC)",
5912 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_metric,
5913 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_metric) );
5914 break;
5915 case VKI_SIOCSIFMTU: /* set MTU size */
5916 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFMTU)",
5917 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5918 PRE_MEM_READ( "ioctl(SIOCSIFMTU)",
5919 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_mtu,
5920 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_mtu) );
5921 break;
5922 case VKI_SIOCSIFHWADDR: /* set hardware address */
5923 PRE_MEM_RASCIIZ( "ioctl(SIOCSIFHWADDR)",
5924 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5925 PRE_MEM_READ( "ioctl(SIOCSIFHWADDR)",
5926 (Addr)&((struct vki_ifreq *)ARG3)->ifr_hwaddr,
5927 sizeof(((struct vki_ifreq *)ARG3)->ifr_hwaddr) );
5928 break;
5929 case VKI_SIOCSMIIREG: /* set hardware entry registers */
5930 PRE_MEM_RASCIIZ( "ioctl(SIOCSMIIREG)",
5931 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5932 PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
5933 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
5934 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
5935 PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
5936 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num,
5937 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->reg_num) );
5938 PRE_MEM_READ( "ioctl(SIOCSMIIREG)",
5939 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_in,
5940 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_in) );
5941 break;
5942 /* Routing table calls. */
5943 case VKI_SIOCADDRT: /* add routing table entry */
5944 case VKI_SIOCDELRT: /* delete routing table entry */
5945 PRE_MEM_READ( "ioctl(SIOCADDRT/DELRT)", ARG3,
5946 sizeof(struct vki_rtentry));
5947 break;
5949 /* tun/tap related ioctls */
5950 case VKI_TUNSETNOCSUM:
5951 case VKI_TUNSETDEBUG:
5952 break;
5953 case VKI_TUNSETIFF:
5954 PRE_MEM_RASCIIZ( "ioctl(TUNSETIFF)",
5955 (Addr)((struct vki_ifreq *)ARG3)->vki_ifr_name );
5956 PRE_MEM_READ( "ioctl(TUNSETIFF)",
5957 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
5958 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
5959 PRE_MEM_WRITE( "ioctl(TUNSETIFF)", ARG3, sizeof(struct vki_ifreq) );
5960 break;
5961 case VKI_TUNSETPERSIST:
5962 case VKI_TUNSETOWNER:
5963 case VKI_TUNSETLINK:
5964 case VKI_TUNSETGROUP:
5965 break;
5966 case VKI_TUNGETFEATURES:
5967 PRE_MEM_WRITE( "ioctl(TUNGETFEATURES)", ARG3, sizeof(unsigned int) );
5968 break;
5969 case VKI_TUNSETOFFLOAD:
5970 break;
5971 case VKI_TUNGETIFF:
5972 PRE_MEM_WRITE( "ioctl(TUNGETIFF)", ARG3, sizeof(struct vki_ifreq) );
5973 break;
5974 case VKI_TUNGETSNDBUF:
5975 PRE_MEM_WRITE( "ioctl(TUNGETSNDBUF)", ARG3, sizeof(int) );
5976 break;
5977 case VKI_TUNSETSNDBUF:
5978 PRE_MEM_READ( "ioctl(TUNSETSNDBUF)", ARG3, sizeof(int) );
5979 break;
5980 case VKI_TUNGETVNETHDRSZ:
5981 PRE_MEM_WRITE( "ioctl(TUNGETVNETHDRSZ)", ARG3, sizeof(int) );
5982 break;
5983 case VKI_TUNSETVNETHDRSZ:
5984 PRE_MEM_READ( "ioctl(TUNSETVNETHDRSZ)", ARG3, sizeof(int) );
5985 break;
5986 case VKI_TUNSETQUEUE:
5987 PRE_MEM_READ( "ioctl(TUNSETQUEUE)",
5988 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
5989 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
5990 break;
5991 case VKI_TUNSETIFINDEX:
5992 PRE_MEM_READ( "ioctl(TUNSETIFINDEX)", ARG3, sizeof(unsigned int));
5993 break;
5995 /* RARP cache control calls. */
5996 case VKI_SIOCDRARP: /* delete RARP table entry */
5997 case VKI_SIOCSRARP: /* set RARP table entry */
5998 /* ARP cache control calls. */
5999 case VKI_SIOCSARP: /* set ARP table entry */
6000 case VKI_SIOCDARP: /* delete ARP table entry */
6001 PRE_MEM_READ( "ioctl(SIOCSIFFLAGS)", ARG3, sizeof(struct vki_ifreq));
6002 break;
6004 case VKI_SIOCGPGRP:
6005 PRE_MEM_WRITE( "ioctl(SIOCGPGRP)", ARG3, sizeof(int) );
6006 break;
6007 case VKI_SIOCSPGRP:
6008 PRE_MEM_READ( "ioctl(SIOCSPGRP)", ARG3, sizeof(int) );
6009 //tst->sys_flags &= ~SfMayBlock;
6010 break;
6012 case VKI_SIOCATMARK:
6013 PRE_MEM_READ( "ioctl(SIOCATMARK)", ARG3, sizeof(int) );
6014 break;
6016 /* linux/soundcard interface (OSS) */
6017 case VKI_SNDCTL_SEQ_GETOUTCOUNT:
6018 case VKI_SNDCTL_SEQ_GETINCOUNT:
6019 case VKI_SNDCTL_SEQ_PERCMODE:
6020 case VKI_SNDCTL_SEQ_TESTMIDI:
6021 case VKI_SNDCTL_SEQ_RESETSAMPLES:
6022 case VKI_SNDCTL_SEQ_NRSYNTHS:
6023 case VKI_SNDCTL_SEQ_NRMIDIS:
6024 case VKI_SNDCTL_SEQ_GETTIME:
6025 case VKI_SNDCTL_DSP_GETBLKSIZE:
6026 case VKI_SNDCTL_DSP_GETFMTS:
6027 case VKI_SNDCTL_DSP_GETTRIGGER:
6028 case VKI_SNDCTL_DSP_GETODELAY:
6029 case VKI_SNDCTL_DSP_GETSPDIF:
6030 case VKI_SNDCTL_DSP_GETCAPS:
6031 case VKI_SOUND_PCM_READ_RATE:
6032 case VKI_SOUND_PCM_READ_CHANNELS:
6033 case VKI_SOUND_PCM_READ_BITS:
6034 case VKI_SOUND_PCM_READ_FILTER:
6035 PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOR, int))",
6036 ARG3, sizeof(int));
6037 break;
6038 case VKI_SNDCTL_SEQ_CTRLRATE:
6039 case VKI_SNDCTL_DSP_SPEED:
6040 case VKI_SNDCTL_DSP_STEREO:
6041 case VKI_SNDCTL_DSP_CHANNELS:
6042 case VKI_SOUND_PCM_WRITE_FILTER:
6043 case VKI_SNDCTL_DSP_SUBDIVIDE:
6044 case VKI_SNDCTL_DSP_SETFRAGMENT:
6045 case VKI_SNDCTL_DSP_SETFMT:
6046 case VKI_SNDCTL_DSP_GETCHANNELMASK:
6047 case VKI_SNDCTL_DSP_BIND_CHANNEL:
6048 case VKI_SNDCTL_TMR_TIMEBASE:
6049 case VKI_SNDCTL_TMR_TEMPO:
6050 case VKI_SNDCTL_TMR_SOURCE:
6051 case VKI_SNDCTL_MIDI_PRETIME:
6052 case VKI_SNDCTL_MIDI_MPUMODE:
6053 PRE_MEM_READ( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOWR, int))",
6054 ARG3, sizeof(int));
6055 PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOWR, int))",
6056 ARG3, sizeof(int));
6057 break;
6058 case VKI_SNDCTL_DSP_GETOSPACE:
6059 case VKI_SNDCTL_DSP_GETISPACE:
6060 PRE_MEM_WRITE( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOR, audio_buf_info))",
6061 ARG3, sizeof(vki_audio_buf_info));
6062 break;
6063 case VKI_SNDCTL_DSP_NONBLOCK:
6064 break;
6065 case VKI_SNDCTL_DSP_SETTRIGGER:
6066 PRE_MEM_READ( "ioctl(SNDCTL_XXX|SOUND_XXX (SIOW, int))",
6067 ARG3, sizeof(int));
6068 break;
6070 case VKI_SNDCTL_DSP_POST:
6071 case VKI_SNDCTL_DSP_RESET:
6072 case VKI_SNDCTL_DSP_SYNC:
6073 case VKI_SNDCTL_DSP_SETSYNCRO:
6074 case VKI_SNDCTL_DSP_SETDUPLEX:
6075 break;
6077 /* linux/soundcard interface (ALSA) */
6078 case VKI_SNDRV_PCM_IOCTL_PAUSE:
6079 case VKI_SNDRV_PCM_IOCTL_LINK:
6080 /* these just take an int by value */
6081 break;
6082 case VKI_SNDRV_CTL_IOCTL_PVERSION:
6083 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_PVERSION)", (Addr)ARG3, sizeof(int) );
6084 break;
6085 case VKI_SNDRV_CTL_IOCTL_CARD_INFO:
6086 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_CARD_INFO)", (Addr)ARG3, sizeof(struct vki_snd_ctl_card_info) );
6087 break;
6088 case VKI_SNDRV_CTL_IOCTL_ELEM_LIST: {
6089 struct vki_snd_ctl_elem_list *data = (struct vki_snd_ctl_elem_list *)ARG3;
6090 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)&data->offset, sizeof(data->offset) );
6091 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)&data->space, sizeof(data->space) );
6092 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)&data->used, sizeof(data->used) );
6093 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)&data->count, sizeof(data->count) );
6094 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)&data->pids, sizeof(data->pids) );
6095 if (data->pids) {
6096 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_ELEM_LIST)", (Addr)data->pids, sizeof(struct vki_snd_ctl_elem_id) * data->space );
6098 break;
6100 case VKI_SNDRV_CTL_IOCTL_TLV_READ: {
6101 struct vki_snd_ctl_tlv *data = (struct vki_snd_ctl_tlv *)ARG3;
6102 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_TLV_READ)", (Addr)&data->numid, sizeof(data->numid) );
6103 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_TLV_READ)", (Addr)&data->length, sizeof(data->length) );
6104 PRE_MEM_WRITE( "ioctl(SNDRV_CTL_IOCTL_TLV_READ)", (Addr)data->tlv, data->length );
6105 break;
6107 case VKI_SNDRV_CTL_IOCTL_TLV_WRITE:
6108 case VKI_SNDRV_CTL_IOCTL_TLV_COMMAND: {
6109 struct vki_snd_ctl_tlv *data = (struct vki_snd_ctl_tlv *)ARG3;
6110 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_TLV_WRITE)", (Addr)&data->numid, sizeof(data->numid) );
6111 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_TLV_WRITE)", (Addr)&data->length, sizeof(data->length) );
6112 PRE_MEM_READ( "ioctl(SNDRV_CTL_IOCTL_TLV_WRITE)", (Addr)data->tlv, data->length );
6113 break;
6116 /* Real Time Clock (/dev/rtc) ioctls */
6117 case VKI_RTC_UIE_ON:
6118 case VKI_RTC_UIE_OFF:
6119 case VKI_RTC_AIE_ON:
6120 case VKI_RTC_AIE_OFF:
6121 case VKI_RTC_PIE_ON:
6122 case VKI_RTC_PIE_OFF:
6123 case VKI_RTC_IRQP_SET:
6124 break;
6125 case VKI_RTC_RD_TIME:
6126 case VKI_RTC_ALM_READ:
6127 PRE_MEM_WRITE( "ioctl(RTC_RD_TIME/ALM_READ)",
6128 ARG3, sizeof(struct vki_rtc_time));
6129 break;
6130 case VKI_RTC_ALM_SET:
6131 PRE_MEM_READ( "ioctl(RTC_ALM_SET)", ARG3, sizeof(struct vki_rtc_time));
6132 break;
6133 case VKI_RTC_IRQP_READ:
6134 PRE_MEM_WRITE( "ioctl(RTC_IRQP_READ)", ARG3, sizeof(unsigned long));
6135 break;
6137 /* Block devices */
6138 case VKI_BLKROSET:
6139 PRE_MEM_READ( "ioctl(BLKROSET)", ARG3, sizeof(int));
6140 break;
6141 case VKI_BLKROGET:
6142 PRE_MEM_WRITE( "ioctl(BLKROGET)", ARG3, sizeof(int));
6143 break;
6144 case VKI_BLKGETSIZE:
6145 PRE_MEM_WRITE( "ioctl(BLKGETSIZE)", ARG3, sizeof(unsigned long));
6146 break;
6147 case VKI_BLKRASET:
6148 break;
6149 case VKI_BLKRAGET:
6150 PRE_MEM_WRITE( "ioctl(BLKRAGET)", ARG3, sizeof(long));
6151 break;
6152 case VKI_BLKFRASET:
6153 break;
6154 case VKI_BLKFRAGET:
6155 PRE_MEM_WRITE( "ioctl(BLKFRAGET)", ARG3, sizeof(long));
6156 break;
6157 case VKI_BLKSECTGET:
6158 PRE_MEM_WRITE( "ioctl(BLKSECTGET)", ARG3, sizeof(unsigned short));
6159 break;
6160 case VKI_BLKSSZGET:
6161 PRE_MEM_WRITE( "ioctl(BLKSSZGET)", ARG3, sizeof(int));
6162 break;
6163 case VKI_BLKBSZGET:
6164 PRE_MEM_WRITE( "ioctl(BLKBSZGET)", ARG3, sizeof(int));
6165 break;
6166 case VKI_BLKBSZSET:
6167 PRE_MEM_READ( "ioctl(BLKBSZSET)", ARG3, sizeof(int));
6168 break;
6169 case VKI_BLKGETSIZE64:
6170 PRE_MEM_WRITE( "ioctl(BLKGETSIZE64)", ARG3, sizeof(unsigned long long));
6171 break;
6172 case VKI_BLKPBSZGET:
6173 PRE_MEM_WRITE( "ioctl(BLKPBSZGET)", ARG3, sizeof(int));
6174 break;
6175 case VKI_BLKDISCARDZEROES:
6176 PRE_MEM_WRITE( "ioctl(BLKDISCARDZEROES)", ARG3, sizeof(vki_uint));
6177 break;
6179 /* Hard disks */
6180 case VKI_HDIO_GETGEO: /* 0x0301 */
6181 PRE_MEM_WRITE( "ioctl(HDIO_GETGEO)", ARG3, sizeof(struct vki_hd_geometry));
6182 break;
6183 case VKI_HDIO_GET_DMA: /* 0x030b */
6184 PRE_MEM_WRITE( "ioctl(HDIO_GET_DMA)", ARG3, sizeof(long));
6185 break;
6186 case VKI_HDIO_GET_IDENTITY: /* 0x030d */
6187 PRE_MEM_WRITE( "ioctl(HDIO_GET_IDENTITY)", ARG3,
6188 VKI_SIZEOF_STRUCT_HD_DRIVEID );
6189 break;
6191 /* SCSI */
6192 case VKI_SCSI_IOCTL_GET_IDLUN: /* 0x5382 */
6193 PRE_MEM_WRITE( "ioctl(SCSI_IOCTL_GET_IDLUN)", ARG3, sizeof(struct vki_scsi_idlun));
6194 break;
6195 case VKI_SCSI_IOCTL_GET_BUS_NUMBER: /* 0x5386 */
6196 PRE_MEM_WRITE( "ioctl(SCSI_IOCTL_GET_BUS_NUMBER)", ARG3, sizeof(int));
6197 break;
6199 /* CD ROM stuff (??) */
6200 case VKI_CDROM_GET_MCN:
6201 PRE_MEM_READ( "ioctl(CDROM_GET_MCN)", ARG3,
6202 sizeof(struct vki_cdrom_mcn) );
6203 break;
6204 case VKI_CDROM_SEND_PACKET:
6205 PRE_MEM_READ( "ioctl(CDROM_SEND_PACKET)", ARG3,
6206 sizeof(struct vki_cdrom_generic_command));
6207 break;
6208 case VKI_CDROMSUBCHNL:
6209 PRE_MEM_READ( "ioctl(CDROMSUBCHNL (cdsc_format, char))",
6210 (Addr) &(((struct vki_cdrom_subchnl*) ARG3)->cdsc_format),
6211 sizeof(((struct vki_cdrom_subchnl*) ARG3)->cdsc_format));
6212 PRE_MEM_WRITE( "ioctl(CDROMSUBCHNL)", ARG3,
6213 sizeof(struct vki_cdrom_subchnl));
6214 break;
6215 case VKI_CDROMREADMODE2:
6216 PRE_MEM_READ( "ioctl(CDROMREADMODE2)", ARG3, VKI_CD_FRAMESIZE_RAW0 );
6217 break;
6218 case VKI_CDROMREADTOCHDR:
6219 PRE_MEM_WRITE( "ioctl(CDROMREADTOCHDR)", ARG3,
6220 sizeof(struct vki_cdrom_tochdr));
6221 break;
6222 case VKI_CDROMREADTOCENTRY:
6223 PRE_MEM_READ( "ioctl(CDROMREADTOCENTRY (cdte_format, char))",
6224 (Addr) &(((struct vki_cdrom_tocentry*) ARG3)->cdte_format),
6225 sizeof(((struct vki_cdrom_tocentry*) ARG3)->cdte_format));
6226 PRE_MEM_READ( "ioctl(CDROMREADTOCENTRY (cdte_track, char))",
6227 (Addr) &(((struct vki_cdrom_tocentry*) ARG3)->cdte_track),
6228 sizeof(((struct vki_cdrom_tocentry*) ARG3)->cdte_track));
6229 PRE_MEM_WRITE( "ioctl(CDROMREADTOCENTRY)", ARG3,
6230 sizeof(struct vki_cdrom_tocentry));
6231 break;
6232 case VKI_CDROMMULTISESSION: /* 0x5310 */
6233 PRE_MEM_WRITE( "ioctl(CDROMMULTISESSION)", ARG3,
6234 sizeof(struct vki_cdrom_multisession));
6235 break;
6236 case VKI_CDROMVOLREAD: /* 0x5313 */
6237 PRE_MEM_WRITE( "ioctl(CDROMVOLREAD)", ARG3,
6238 sizeof(struct vki_cdrom_volctrl));
6239 break;
6240 case VKI_CDROMREADRAW: /* 0x5314 */
6241 PRE_MEM_READ( "ioctl(CDROMREADRAW)", ARG3, sizeof(struct vki_cdrom_msf));
6242 PRE_MEM_WRITE( "ioctl(CDROMREADRAW)", ARG3, VKI_CD_FRAMESIZE_RAW);
6243 break;
6244 case VKI_CDROMREADAUDIO: /* 0x530e */
6245 PRE_MEM_READ( "ioctl(CDROMREADAUDIO)", ARG3,
6246 sizeof (struct vki_cdrom_read_audio));
6247 if ( ARG3 ) {
6248 /* ToDo: don't do any of the following if the structure is invalid */
6249 struct vki_cdrom_read_audio *cra = (struct vki_cdrom_read_audio *) ARG3;
6250 PRE_MEM_WRITE( "ioctl(CDROMREADAUDIO).buf",
6251 (Addr)(cra->buf), cra->nframes * VKI_CD_FRAMESIZE_RAW);
6253 break;
6254 case VKI_CDROMPLAYMSF:
6255 PRE_MEM_READ( "ioctl(CDROMPLAYMSF)", ARG3, sizeof(struct vki_cdrom_msf));
6256 break;
6257 /* The following two are probably bogus (should check args
6258 for readability). JRS 20021117 */
6259 case VKI_CDROM_DRIVE_STATUS: /* 0x5326 */
6260 case VKI_CDROM_CLEAR_OPTIONS: /* 0x5321 */
6261 break;
6262 case VKI_CDROM_GET_CAPABILITY: /* 0x5331 */
6263 break;
6265 case VKI_FIGETBSZ:
6266 PRE_MEM_WRITE( "ioctl(FIGETBSZ)", ARG3, sizeof(unsigned long));
6267 break;
6268 case VKI_FIBMAP:
6269 PRE_MEM_READ( "ioctl(FIBMAP)", ARG3, sizeof(int));
6270 break;
6272 case VKI_FBIOGET_VSCREENINFO: /* 0x4600 */
6273 PRE_MEM_WRITE( "ioctl(FBIOGET_VSCREENINFO)", ARG3,
6274 sizeof(struct vki_fb_var_screeninfo));
6275 break;
6276 case VKI_FBIOPUT_VSCREENINFO:
6277 PRE_MEM_READ( "ioctl(FBIOPUT_VSCREENINFO)", ARG3,
6278 sizeof(struct vki_fb_var_screeninfo));
6279 break;
6280 case VKI_FBIOGET_FSCREENINFO: /* 0x4602 */
6281 PRE_MEM_WRITE( "ioctl(FBIOGET_FSCREENINFO)", ARG3,
6282 sizeof(struct vki_fb_fix_screeninfo));
6283 break;
6284 case VKI_FBIOPAN_DISPLAY:
6285 PRE_MEM_READ( "ioctl(FBIOPAN_DISPLAY)", ARG3,
6286 sizeof(struct vki_fb_var_screeninfo));
6288 break;
6289 case VKI_PPCLAIM:
6290 case VKI_PPEXCL:
6291 case VKI_PPYIELD:
6292 case VKI_PPRELEASE:
6293 break;
6294 case VKI_PPSETMODE:
6295 PRE_MEM_READ( "ioctl(PPSETMODE)", ARG3, sizeof(int) );
6296 break;
6297 case VKI_PPGETMODE:
6298 PRE_MEM_WRITE( "ioctl(PPGETMODE)", ARG3, sizeof(int) );
6299 break;
6300 case VKI_PPSETPHASE:
6301 PRE_MEM_READ( "ioctl(PPSETPHASE)", ARG3, sizeof(int) );
6302 break;
6303 case VKI_PPGETPHASE:
6304 PRE_MEM_WRITE( "ioctl(PPGETPHASE)", ARG3, sizeof(int) );
6305 break;
6306 case VKI_PPGETMODES:
6307 PRE_MEM_WRITE( "ioctl(PPGETMODES)", ARG3, sizeof(unsigned int) );
6308 break;
6309 case VKI_PPSETFLAGS:
6310 PRE_MEM_READ( "ioctl(PPSETFLAGS)", ARG3, sizeof(int) );
6311 break;
6312 case VKI_PPGETFLAGS:
6313 PRE_MEM_WRITE( "ioctl(PPGETFLAGS)", ARG3, sizeof(int) );
6314 break;
6315 case VKI_PPRSTATUS:
6316 PRE_MEM_WRITE( "ioctl(PPRSTATUS)", ARG3, sizeof(unsigned char) );
6317 break;
6318 case VKI_PPRDATA:
6319 PRE_MEM_WRITE( "ioctl(PPRDATA)", ARG3, sizeof(unsigned char) );
6320 break;
6321 case VKI_PPRCONTROL:
6322 PRE_MEM_WRITE( "ioctl(PPRCONTROL)", ARG3, sizeof(unsigned char) );
6323 break;
6324 case VKI_PPWDATA:
6325 PRE_MEM_READ( "ioctl(PPWDATA)", ARG3, sizeof(unsigned char) );
6326 break;
6327 case VKI_PPWCONTROL:
6328 PRE_MEM_READ( "ioctl(PPWCONTROL)", ARG3, sizeof(unsigned char) );
6329 break;
6330 case VKI_PPFCONTROL:
6331 PRE_MEM_READ( "ioctl(PPFCONTROL)", ARG3, 2 * sizeof(unsigned char) );
6332 break;
6333 case VKI_PPDATADIR:
6334 PRE_MEM_READ( "ioctl(PPDATADIR)", ARG3, sizeof(int) );
6335 break;
6336 case VKI_PPNEGOT:
6337 PRE_MEM_READ( "ioctl(PPNEGOT)", ARG3, sizeof(int) );
6338 break;
6339 case VKI_PPWCTLONIRQ:
6340 PRE_MEM_READ( "ioctl(PPWCTLONIRQ)",ARG3, sizeof(unsigned char) );
6341 break;
6342 case VKI_PPCLRIRQ:
6343 PRE_MEM_WRITE( "ioctl(PPCLRIRQ)", ARG3, sizeof(int) );
6344 break;
6345 case VKI_PPSETTIME:
6346 PRE_MEM_READ( "ioctl(PPSETTIME)", ARG3, sizeof(struct vki_timeval) );
6347 break;
6348 case VKI_PPGETTIME:
6349 PRE_MEM_WRITE( "ioctl(PPGETTIME)", ARG3, sizeof(struct vki_timeval) );
6350 break;
6352 case VKI_GIO_FONT:
6353 PRE_MEM_WRITE( "ioctl(GIO_FONT)", ARG3, 32 * 256 );
6354 break;
6355 case VKI_PIO_FONT:
6356 PRE_MEM_READ( "ioctl(PIO_FONT)", ARG3, 32 * 256 );
6357 break;
6359 case VKI_GIO_FONTX:
6360 PRE_MEM_READ( "ioctl(GIO_FONTX)", ARG3, sizeof(struct vki_consolefontdesc) );
6361 if ( ARG3 ) {
6362 /* ToDo: don't do any of the following if the structure is invalid */
6363 struct vki_consolefontdesc *cfd = (struct vki_consolefontdesc *)ARG3;
6364 PRE_MEM_WRITE( "ioctl(GIO_FONTX).chardata", (Addr)cfd->chardata,
6365 32 * cfd->charcount );
6367 break;
6368 case VKI_PIO_FONTX:
6369 PRE_MEM_READ( "ioctl(PIO_FONTX)", ARG3, sizeof(struct vki_consolefontdesc) );
6370 if ( ARG3 ) {
6371 /* ToDo: don't do any of the following if the structure is invalid */
6372 struct vki_consolefontdesc *cfd = (struct vki_consolefontdesc *)ARG3;
6373 PRE_MEM_READ( "ioctl(PIO_FONTX).chardata", (Addr)cfd->chardata,
6374 32 * cfd->charcount );
6376 break;
6378 case VKI_PIO_FONTRESET:
6379 break;
6381 case VKI_GIO_CMAP:
6382 PRE_MEM_WRITE( "ioctl(GIO_CMAP)", ARG3, 16 * 3 );
6383 break;
6384 case VKI_PIO_CMAP:
6385 PRE_MEM_READ( "ioctl(PIO_CMAP)", ARG3, 16 * 3 );
6386 break;
6388 case VKI_KIOCSOUND:
6389 case VKI_KDMKTONE:
6390 break;
6392 case VKI_KDGETLED:
6393 PRE_MEM_WRITE( "ioctl(KDGETLED)", ARG3, sizeof(char) );
6394 break;
6395 case VKI_KDSETLED:
6396 break;
6398 case VKI_KDGKBTYPE:
6399 PRE_MEM_WRITE( "ioctl(KDGKBTYPE)", ARG3, sizeof(char) );
6400 break;
6402 case VKI_KDADDIO:
6403 case VKI_KDDELIO:
6404 case VKI_KDENABIO:
6405 case VKI_KDDISABIO:
6406 break;
6408 case VKI_KDSETMODE:
6409 break;
6410 case VKI_KDGETMODE:
6411 PRE_MEM_WRITE( "ioctl(KDGETMODE)", ARG3, sizeof(int) );
6412 break;
6414 case VKI_KDMAPDISP:
6415 case VKI_KDUNMAPDISP:
6416 break;
6418 case VKI_GIO_SCRNMAP:
6419 PRE_MEM_WRITE( "ioctl(GIO_SCRNMAP)", ARG3, VKI_E_TABSZ );
6420 break;
6421 case VKI_PIO_SCRNMAP:
6422 PRE_MEM_READ( "ioctl(PIO_SCRNMAP)", ARG3, VKI_E_TABSZ );
6423 break;
6424 case VKI_GIO_UNISCRNMAP:
6425 PRE_MEM_WRITE( "ioctl(GIO_UNISCRNMAP)", ARG3,
6426 VKI_E_TABSZ * sizeof(unsigned short) );
6427 break;
6428 case VKI_PIO_UNISCRNMAP:
6429 PRE_MEM_READ( "ioctl(PIO_UNISCRNMAP)", ARG3,
6430 VKI_E_TABSZ * sizeof(unsigned short) );
6431 break;
6433 case VKI_GIO_UNIMAP:
6434 if ( ARG3 ) {
6435 struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
6436 PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entry_ct,
6437 sizeof(unsigned short));
6438 PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entries,
6439 sizeof(struct vki_unipair *));
6440 PRE_MEM_WRITE( "ioctl(GIO_UNIMAP).entries", (Addr)desc->entries,
6441 desc->entry_ct * sizeof(struct vki_unipair));
6443 break;
6444 case VKI_PIO_UNIMAP:
6445 if ( ARG3 ) {
6446 struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
6447 PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entry_ct,
6448 sizeof(unsigned short) );
6449 PRE_MEM_READ( "ioctl(GIO_UNIMAP)", (Addr)&desc->entries,
6450 sizeof(struct vki_unipair *) );
6451 PRE_MEM_READ( "ioctl(PIO_UNIMAP).entries", (Addr)desc->entries,
6452 desc->entry_ct * sizeof(struct vki_unipair) );
6454 break;
6455 case VKI_PIO_UNIMAPCLR:
6456 PRE_MEM_READ( "ioctl(GIO_UNIMAP)", ARG3, sizeof(struct vki_unimapinit));
6457 break;
6459 case VKI_KDGKBMODE:
6460 PRE_MEM_WRITE( "ioctl(KDGKBMODE)", ARG3, sizeof(int) );
6461 break;
6462 case VKI_KDSKBMODE:
6463 break;
6465 case VKI_KDGKBMETA:
6466 PRE_MEM_WRITE( "ioctl(KDGKBMETA)", ARG3, sizeof(int) );
6467 break;
6468 case VKI_KDSKBMETA:
6469 break;
6471 case VKI_KDGKBLED:
6472 PRE_MEM_WRITE( "ioctl(KDGKBLED)", ARG3, sizeof(char) );
6473 break;
6474 case VKI_KDSKBLED:
6475 break;
6477 case VKI_KDGKBENT:
6478 PRE_MEM_READ( "ioctl(KDGKBENT).kb_table",
6479 (Addr)&((struct vki_kbentry *)ARG3)->kb_table,
6480 sizeof(((struct vki_kbentry *)ARG3)->kb_table) );
6481 PRE_MEM_READ( "ioctl(KDGKBENT).kb_index",
6482 (Addr)&((struct vki_kbentry *)ARG3)->kb_index,
6483 sizeof(((struct vki_kbentry *)ARG3)->kb_index) );
6484 PRE_MEM_WRITE( "ioctl(KDGKBENT).kb_value",
6485 (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
6486 sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
6487 break;
6488 case VKI_KDSKBENT:
6489 PRE_MEM_READ( "ioctl(KDSKBENT).kb_table",
6490 (Addr)&((struct vki_kbentry *)ARG3)->kb_table,
6491 sizeof(((struct vki_kbentry *)ARG3)->kb_table) );
6492 PRE_MEM_READ( "ioctl(KDSKBENT).kb_index",
6493 (Addr)&((struct vki_kbentry *)ARG3)->kb_index,
6494 sizeof(((struct vki_kbentry *)ARG3)->kb_index) );
6495 PRE_MEM_READ( "ioctl(KDSKBENT).kb_value",
6496 (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
6497 sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
6498 break;
6500 case VKI_KDGKBSENT:
6501 PRE_MEM_READ( "ioctl(KDGKBSENT).kb_func",
6502 (Addr)&((struct vki_kbsentry *)ARG3)->kb_func,
6503 sizeof(((struct vki_kbsentry *)ARG3)->kb_func) );
6504 PRE_MEM_WRITE( "ioctl(KDGKSENT).kb_string",
6505 (Addr)((struct vki_kbsentry *)ARG3)->kb_string,
6506 sizeof(((struct vki_kbsentry *)ARG3)->kb_string) );
6507 break;
6508 case VKI_KDSKBSENT:
6509 PRE_MEM_READ( "ioctl(KDSKBSENT).kb_func",
6510 (Addr)&((struct vki_kbsentry *)ARG3)->kb_func,
6511 sizeof(((struct vki_kbsentry *)ARG3)->kb_func) );
6512 PRE_MEM_RASCIIZ( "ioctl(KDSKBSENT).kb_string",
6513 (Addr)((struct vki_kbsentry *)ARG3)->kb_string );
6514 break;
6516 case VKI_KDGKBDIACR:
6517 PRE_MEM_WRITE( "ioctl(KDGKBDIACR)", ARG3, sizeof(struct vki_kbdiacrs) );
6518 break;
6519 case VKI_KDSKBDIACR:
6520 PRE_MEM_READ( "ioctl(KDSKBDIACR)", ARG3, sizeof(struct vki_kbdiacrs) );
6521 break;
6523 case VKI_KDGETKEYCODE:
6524 PRE_MEM_READ( "ioctl(KDGETKEYCODE).scancode",
6525 (Addr)&((struct vki_kbkeycode *)ARG3)->scancode,
6526 sizeof(((struct vki_kbkeycode *)ARG3)->scancode) );
6527 PRE_MEM_WRITE( "ioctl(KDGETKEYCODE).keycode",
6528 (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
6529 sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
6530 break;
6531 case VKI_KDSETKEYCODE:
6532 PRE_MEM_READ( "ioctl(KDSETKEYCODE).scancode",
6533 (Addr)&((struct vki_kbkeycode *)ARG3)->scancode,
6534 sizeof(((struct vki_kbkeycode *)ARG3)->scancode) );
6535 PRE_MEM_READ( "ioctl(KDSETKEYCODE).keycode",
6536 (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
6537 sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
6538 break;
6540 case VKI_KDSIGACCEPT:
6541 break;
6543 case VKI_KDKBDREP:
6544 PRE_MEM_READ( "ioctl(KBKBDREP)", ARG3, sizeof(struct vki_kbd_repeat) );
6545 break;
6547 case VKI_KDFONTOP:
6548 if ( ARG3 ) {
6549 struct vki_console_font_op *op = (struct vki_console_font_op *) ARG3;
6550 PRE_MEM_READ( "ioctl(KDFONTOP)", (Addr)op,
6551 sizeof(struct vki_console_font_op) );
6552 switch ( op->op ) {
6553 case VKI_KD_FONT_OP_SET:
6554 PRE_MEM_READ( "ioctl(KDFONTOP,KD_FONT_OP_SET).data",
6555 (Addr)op->data,
6556 (op->width + 7) / 8 * 32 * op->charcount );
6557 break;
6558 case VKI_KD_FONT_OP_GET:
6559 if ( op->data )
6560 PRE_MEM_WRITE( "ioctl(KDFONTOP,KD_FONT_OP_GET).data",
6561 (Addr)op->data,
6562 (op->width + 7) / 8 * 32 * op->charcount );
6563 break;
6564 case VKI_KD_FONT_OP_SET_DEFAULT:
6565 if ( op->data )
6566 PRE_MEM_RASCIIZ( "ioctl(KDFONTOP,KD_FONT_OP_SET_DEFAULT).data",
6567 (Addr)op->data );
6568 break;
6569 case VKI_KD_FONT_OP_COPY:
6570 break;
6573 break;
6575 case VKI_VT_OPENQRY:
6576 PRE_MEM_WRITE( "ioctl(VT_OPENQRY)", ARG3, sizeof(int) );
6577 break;
6578 case VKI_VT_GETMODE:
6579 PRE_MEM_WRITE( "ioctl(VT_GETMODE)", ARG3, sizeof(struct vki_vt_mode) );
6580 break;
6581 case VKI_VT_SETMODE:
6582 PRE_MEM_READ( "ioctl(VT_SETMODE)", ARG3, sizeof(struct vki_vt_mode) );
6583 break;
6584 case VKI_VT_GETSTATE:
6585 PRE_MEM_WRITE( "ioctl(VT_GETSTATE).v_active",
6586 (Addr) &(((struct vki_vt_stat*) ARG3)->v_active),
6587 sizeof(((struct vki_vt_stat*) ARG3)->v_active));
6588 PRE_MEM_WRITE( "ioctl(VT_GETSTATE).v_state",
6589 (Addr) &(((struct vki_vt_stat*) ARG3)->v_state),
6590 sizeof(((struct vki_vt_stat*) ARG3)->v_state));
6591 break;
6592 case VKI_VT_RELDISP:
6593 case VKI_VT_ACTIVATE:
6594 case VKI_VT_WAITACTIVE:
6595 case VKI_VT_DISALLOCATE:
6596 break;
6597 case VKI_VT_RESIZE:
6598 PRE_MEM_READ( "ioctl(VT_RESIZE)", ARG3, sizeof(struct vki_vt_sizes) );
6599 break;
6600 case VKI_VT_RESIZEX:
6601 PRE_MEM_READ( "ioctl(VT_RESIZEX)", ARG3, sizeof(struct vki_vt_consize) );
6602 break;
6603 case VKI_VT_LOCKSWITCH:
6604 case VKI_VT_UNLOCKSWITCH:
6605 break;
6607 case VKI_USBDEVFS_CONTROL:
6608 if ( ARG3 ) {
6609 struct vki_usbdevfs_ctrltransfer *vkuc = (struct vki_usbdevfs_ctrltransfer *)ARG3;
6610 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).bRequestType", (Addr)&vkuc->bRequestType, sizeof(vkuc->bRequestType));
6611 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).bRequest", (Addr)&vkuc->bRequest, sizeof(vkuc->bRequest));
6612 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wValue", (Addr)&vkuc->wValue, sizeof(vkuc->wValue));
6613 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wIndex", (Addr)&vkuc->wIndex, sizeof(vkuc->wIndex));
6614 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).wLength", (Addr)&vkuc->wLength, sizeof(vkuc->wLength));
6615 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).timeout", (Addr)&vkuc->timeout, sizeof(vkuc->timeout));
6616 if (vkuc->bRequestType & 0x80)
6617 PRE_MEM_WRITE( "ioctl(USBDEVFS_CONTROL).data", (Addr)vkuc->data, vkuc->wLength);
6618 else
6619 PRE_MEM_READ( "ioctl(USBDEVFS_CONTROL).data", (Addr)vkuc->data, vkuc->wLength);
6621 break;
6622 case VKI_USBDEVFS_BULK:
6623 if ( ARG3 ) {
6624 struct vki_usbdevfs_bulktransfer *vkub = (struct vki_usbdevfs_bulktransfer *)ARG3;
6625 PRE_MEM_READ( "ioctl(USBDEVFS_BULK)", ARG3, sizeof(struct vki_usbdevfs_bulktransfer));
6626 if (vkub->ep & 0x80)
6627 PRE_MEM_WRITE( "ioctl(USBDEVFS_BULK).data", (Addr)vkub->data, vkub->len);
6628 else
6629 PRE_MEM_READ( "ioctl(USBDEVFS_BULK).data", (Addr)vkub->data, vkub->len);
6631 break;
6632 case VKI_USBDEVFS_GETDRIVER:
6633 if ( ARG3 ) {
6634 struct vki_usbdevfs_getdriver *vkugd = (struct vki_usbdevfs_getdriver *) ARG3;
6635 PRE_MEM_WRITE( "ioctl(USBDEVFS_GETDRIVER)", (Addr)&vkugd->driver, sizeof(vkugd->driver));
6637 break;
6638 case VKI_USBDEVFS_SUBMITURB:
6639 if ( ARG3 ) {
6640 struct vki_usbdevfs_urb *vkuu = (struct vki_usbdevfs_urb *)ARG3;
6642 /* Not the whole struct needs to be initialized */
6643 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).endpoint", (Addr)&vkuu->endpoint, sizeof(vkuu->endpoint));
6644 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).type", (Addr)&vkuu->type, sizeof(vkuu->type));
6645 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).flags", (Addr)&vkuu->flags, sizeof(vkuu->flags));
6646 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)&vkuu->buffer, sizeof(vkuu->buffer));
6647 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).signr", (Addr)&vkuu->signr, sizeof(vkuu->signr));
6648 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).status", (Addr)&vkuu->status, sizeof(vkuu->status));
6649 if (vkuu->type == VKI_USBDEVFS_URB_TYPE_CONTROL) {
6650 struct vki_usbdevfs_setuppacket *vkusp = (struct vki_usbdevfs_setuppacket *)vkuu->buffer;
6651 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer_length", (Addr)&vkuu->buffer_length, sizeof(vkuu->buffer_length));
6652 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer.setup_packet", (Addr)vkusp, sizeof(*vkusp));
6653 if (vkusp->bRequestType & 0x80)
6654 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer.data", (Addr)(vkusp+1), vkuu->buffer_length - sizeof(*vkusp));
6655 else
6656 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer.data", (Addr)(vkusp+1), vkuu->buffer_length - sizeof(*vkusp));
6657 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).actual_length", (Addr)&vkuu->actual_length, sizeof(vkuu->actual_length));
6658 } else if (vkuu->type == VKI_USBDEVFS_URB_TYPE_ISO) {
6659 int total_length = 0;
6660 int i;
6661 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).number_of_packets", (Addr)&vkuu->number_of_packets, sizeof(vkuu->number_of_packets));
6662 for(i=0; i<vkuu->number_of_packets; i++) {
6663 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).iso_frame_desc[].length", (Addr)&vkuu->iso_frame_desc[i].length, sizeof(vkuu->iso_frame_desc[i].length));
6664 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));
6665 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).iso_frame_desc[].status", (Addr)&vkuu->iso_frame_desc[i].status, sizeof(vkuu->iso_frame_desc[i].status));
6666 total_length += vkuu->iso_frame_desc[i].length;
6668 if (vkuu->endpoint & 0x80)
6669 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, total_length);
6670 else
6671 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, total_length);
6672 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).error_count", (Addr)&vkuu->error_count, sizeof(vkuu->error_count));
6673 } else {
6674 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer_length", (Addr)&vkuu->buffer_length, sizeof(vkuu->buffer_length));
6675 if (vkuu->endpoint & 0x80)
6676 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, vkuu->buffer_length);
6677 else
6678 PRE_MEM_READ( "ioctl(USBDEVFS_SUBMITURB).buffer", (Addr)vkuu->buffer, vkuu->buffer_length);
6679 PRE_MEM_WRITE( "ioctl(USBDEVFS_SUBMITURB).actual_length", (Addr)&vkuu->actual_length, sizeof(vkuu->actual_length));
6682 break;
6683 case VKI_USBDEVFS_DISCARDURB:
6684 break;
6685 case VKI_USBDEVFS_REAPURB:
6686 if ( ARG3 ) {
6687 PRE_MEM_WRITE( "ioctl(USBDEVFS_REAPURB)", ARG3, sizeof(struct vki_usbdevfs_urb **));
6689 break;
6690 case VKI_USBDEVFS_REAPURBNDELAY:
6691 if ( ARG3 ) {
6692 PRE_MEM_WRITE( "ioctl(USBDEVFS_REAPURBNDELAY)", ARG3, sizeof(struct vki_usbdevfs_urb **));
6694 break;
6695 case VKI_USBDEVFS_CONNECTINFO:
6696 PRE_MEM_WRITE( "ioctl(USBDEVFS_CONNECTINFO)", ARG3, sizeof(struct vki_usbdevfs_connectinfo));
6697 break;
6698 case VKI_USBDEVFS_IOCTL:
6699 if ( ARG3 ) {
6700 struct vki_usbdevfs_ioctl *vkui = (struct vki_usbdevfs_ioctl *)ARG3;
6701 UInt dir2, size2;
6702 PRE_MEM_READ("ioctl(USBDEVFS_IOCTL)", (Addr)vkui, sizeof(struct vki_usbdevfs_ioctl));
6703 dir2 = _VKI_IOC_DIR(vkui->ioctl_code);
6704 size2 = _VKI_IOC_SIZE(vkui->ioctl_code);
6705 if (size2 > 0) {
6706 if (dir2 & _VKI_IOC_WRITE)
6707 PRE_MEM_READ("ioctl(USBDEVFS_IOCTL).dataWrite", (Addr)vkui->data, size2);
6708 else if (dir2 & _VKI_IOC_READ)
6709 PRE_MEM_WRITE("ioctl(USBDEVFS_IOCTL).dataRead", (Addr)vkui->data, size2);
6712 break;
6713 case VKI_USBDEVFS_RESET:
6714 break;
6716 /* I2C (/dev/i2c-*) ioctls */
6717 case VKI_I2C_SLAVE:
6718 case VKI_I2C_SLAVE_FORCE:
6719 case VKI_I2C_TENBIT:
6720 case VKI_I2C_PEC:
6721 break;
6722 case VKI_I2C_FUNCS:
6723 PRE_MEM_WRITE( "ioctl(I2C_FUNCS)", ARG3, sizeof(unsigned long) );
6724 break;
6725 case VKI_I2C_RDWR:
6726 if ( ARG3 ) {
6727 struct vki_i2c_rdwr_ioctl_data *vkui = (struct vki_i2c_rdwr_ioctl_data *)ARG3;
6728 UInt i;
6729 PRE_MEM_READ("ioctl(I2C_RDWR)", (Addr)vkui, sizeof(struct vki_i2c_rdwr_ioctl_data));
6730 for (i=0; i < vkui->nmsgs; i++) {
6731 struct vki_i2c_msg *msg = vkui->msgs + i;
6732 PRE_MEM_READ("ioctl(I2C_RDWR).msgs", (Addr)msg, sizeof(struct vki_i2c_msg));
6733 if (msg->flags & VKI_I2C_M_RD)
6734 PRE_MEM_WRITE("ioctl(I2C_RDWR).msgs.buf", (Addr)msg->buf, msg->len);
6735 else
6736 PRE_MEM_READ("ioctl(I2C_RDWR).msgs.buf", (Addr)msg->buf, msg->len);
6739 break;
6741 /* Wireless extensions ioctls */
6742 case VKI_SIOCSIWCOMMIT:
6743 case VKI_SIOCSIWNWID:
6744 case VKI_SIOCSIWFREQ:
6745 case VKI_SIOCSIWMODE:
6746 case VKI_SIOCSIWSENS:
6747 case VKI_SIOCSIWRANGE:
6748 case VKI_SIOCSIWPRIV:
6749 case VKI_SIOCSIWSTATS:
6750 case VKI_SIOCSIWSPY:
6751 case VKI_SIOCSIWTHRSPY:
6752 case VKI_SIOCSIWAP:
6753 case VKI_SIOCSIWSCAN:
6754 case VKI_SIOCSIWESSID:
6755 case VKI_SIOCSIWRATE:
6756 case VKI_SIOCSIWNICKN:
6757 case VKI_SIOCSIWRTS:
6758 case VKI_SIOCSIWFRAG:
6759 case VKI_SIOCSIWTXPOW:
6760 case VKI_SIOCSIWRETRY:
6761 case VKI_SIOCSIWENCODE:
6762 case VKI_SIOCSIWPOWER:
6763 case VKI_SIOCSIWGENIE:
6764 case VKI_SIOCSIWMLME:
6765 case VKI_SIOCSIWAUTH:
6766 case VKI_SIOCSIWENCODEEXT:
6767 case VKI_SIOCSIWPMKSA:
6768 break;
6769 case VKI_SIOCGIWNAME:
6770 if (ARG3) {
6771 PRE_MEM_WRITE("ioctl(SIOCGIWNAME)",
6772 (Addr)((struct vki_iwreq *)ARG3)->u.name,
6773 sizeof(((struct vki_iwreq *)ARG3)->u.name));
6775 break;
6776 case VKI_SIOCGIWNWID:
6777 case VKI_SIOCGIWSENS:
6778 case VKI_SIOCGIWRATE:
6779 case VKI_SIOCGIWRTS:
6780 case VKI_SIOCGIWFRAG:
6781 case VKI_SIOCGIWTXPOW:
6782 case VKI_SIOCGIWRETRY:
6783 case VKI_SIOCGIWPOWER:
6784 case VKI_SIOCGIWAUTH:
6785 if (ARG3) {
6786 PRE_MEM_WRITE("ioctl(SIOCGIW[NWID|SENS|RATE|RTS|FRAG|TXPOW|"
6787 "RETRY|PARAM|AUTH])",
6788 (Addr)&((struct vki_iwreq *)ARG3)->u.nwid,
6789 sizeof(struct vki_iw_param));
6791 break;
6792 case VKI_SIOCGIWFREQ:
6793 if (ARG3) {
6794 PRE_MEM_WRITE("ioctl(SIOCGIWFREQ",
6795 (Addr)&((struct vki_iwreq *)ARG3)->u.freq,
6796 sizeof(struct vki_iw_freq));
6798 break;
6799 case VKI_SIOCGIWMODE:
6800 if (ARG3) {
6801 PRE_MEM_WRITE("ioctl(SIOCGIWMODE",
6802 (Addr)&((struct vki_iwreq *)ARG3)->u.mode,
6803 sizeof(__vki_u32));
6805 break;
6806 case VKI_SIOCGIWRANGE:
6807 case VKI_SIOCGIWPRIV:
6808 case VKI_SIOCGIWSTATS:
6809 case VKI_SIOCGIWSPY:
6810 case VKI_SIOCGIWTHRSPY:
6811 case VKI_SIOCGIWAPLIST:
6812 case VKI_SIOCGIWSCAN:
6813 case VKI_SIOCGIWESSID:
6814 case VKI_SIOCGIWNICKN:
6815 case VKI_SIOCGIWENCODE:
6816 case VKI_SIOCGIWGENIE:
6817 case VKI_SIOCGIWENCODEEXT:
6818 if (ARG3) {
6819 struct vki_iw_point* point;
6820 point = &((struct vki_iwreq *)ARG3)->u.data;
6821 PRE_MEM_WRITE("ioctl(SIOCGIW[RANGE|PRIV|STATS|SPY|THRSPY|"
6822 "APLIST|SCAN|ESSID|NICKN|ENCODE|GENIE|ENCODEEXT])",
6823 (Addr)point->pointer, point->length);
6825 break;
6826 case VKI_SIOCGIWAP:
6827 if (ARG3) {
6828 PRE_MEM_WRITE("ioctl(SIOCGIWAP)",
6829 (Addr)&((struct vki_iwreq *)ARG3)->u.ap_addr,
6830 sizeof(struct vki_sockaddr));
6832 break;
6834 /* User input device creation */
6835 case VKI_UI_SET_EVBIT:
6836 case VKI_UI_SET_KEYBIT:
6837 case VKI_UI_SET_RELBIT:
6838 case VKI_UI_SET_ABSBIT:
6839 case VKI_UI_SET_MSCBIT:
6840 case VKI_UI_SET_LEDBIT:
6841 case VKI_UI_SET_SNDBIT:
6842 case VKI_UI_SET_FFBIT:
6843 case VKI_UI_SET_SWBIT:
6844 case VKI_UI_SET_PROPBIT:
6845 /* These just take an int by value */
6846 break;
6848 # if defined(VGPV_arm_linux_android) || defined(VGPV_x86_linux_android) \
6849 || defined(VGPV_mips32_linux_android)
6850 /* ashmem */
6851 case VKI_ASHMEM_GET_SIZE:
6852 case VKI_ASHMEM_SET_SIZE:
6853 case VKI_ASHMEM_GET_PROT_MASK:
6854 case VKI_ASHMEM_SET_PROT_MASK:
6855 case VKI_ASHMEM_GET_PIN_STATUS:
6856 case VKI_ASHMEM_PURGE_ALL_CACHES:
6857 break;
6858 case VKI_ASHMEM_GET_NAME:
6859 PRE_MEM_WRITE( "ioctl(ASHMEM_SET_NAME)", ARG3, VKI_ASHMEM_NAME_LEN );
6860 break;
6861 case VKI_ASHMEM_SET_NAME:
6862 PRE_MEM_RASCIIZ( "ioctl(ASHMEM_SET_NAME)", ARG3);
6863 break;
6864 case VKI_ASHMEM_PIN:
6865 case VKI_ASHMEM_UNPIN:
6866 PRE_MEM_READ( "ioctl(ASHMEM_PIN|ASHMEM_UNPIN)",
6867 ARG3, sizeof(struct vki_ashmem_pin) );
6868 break;
6870 /* binder */
6871 case VKI_BINDER_WRITE_READ:
6872 if (ARG3) {
6873 struct vki_binder_write_read* bwr
6874 = (struct vki_binder_write_read*)ARG3;
6876 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_buffer",
6877 bwr->write_buffer);
6878 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_size",
6879 bwr->write_size);
6880 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).write_consumed",
6881 bwr->write_consumed);
6882 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_buffer",
6883 bwr->read_buffer);
6884 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_size",
6885 bwr->read_size);
6886 PRE_FIELD_READ("ioctl(BINDER_WRITE_READ).read_consumed",
6887 bwr->read_consumed);
6889 PRE_FIELD_WRITE("ioctl(BINDER_WRITE_READ).write_consumed",
6890 bwr->write_consumed);
6891 PRE_FIELD_WRITE("ioctl(BINDER_WRITE_READ).read_consumed",
6892 bwr->read_consumed);
6894 if (bwr->read_size)
6895 PRE_MEM_WRITE("ioctl(BINDER_WRITE_READ).read_buffer[]",
6896 (Addr)bwr->read_buffer, bwr->read_size);
6897 if (bwr->write_size)
6898 PRE_MEM_READ("ioctl(BINDER_WRITE_READ).write_buffer[]",
6899 (Addr)bwr->write_buffer, bwr->write_size);
6901 break;
6903 case VKI_BINDER_SET_IDLE_TIMEOUT:
6904 case VKI_BINDER_SET_MAX_THREADS:
6905 case VKI_BINDER_SET_IDLE_PRIORITY:
6906 case VKI_BINDER_SET_CONTEXT_MGR:
6907 case VKI_BINDER_THREAD_EXIT:
6908 break;
6909 case VKI_BINDER_VERSION:
6910 if (ARG3) {
6911 struct vki_binder_version* bv = (struct vki_binder_version*)ARG3;
6912 PRE_FIELD_WRITE("ioctl(BINDER_VERSION)", bv->protocol_version);
6914 break;
6915 # endif /* defined(VGPV_*_linux_android) */
6917 case VKI_HCIGETDEVLIST:
6918 if (ARG3) {
6919 struct vki_hci_dev_list_req* dlr = (struct vki_hci_dev_list_req*)ARG3;
6920 PRE_MEM_READ("ioctl(HCIGETDEVLIST)",
6921 (Addr)ARG3, sizeof(struct vki_hci_dev_list_req));
6922 PRE_MEM_WRITE("ioctl(HCIGETDEVLIST)",
6923 (Addr)ARG3 + sizeof(struct vki_hci_dev_list_req),
6924 dlr->dev_num * sizeof(struct vki_hci_dev_req));
6926 break;
6928 case VKI_HCIINQUIRY:
6929 if (ARG3) {
6930 struct vki_hci_inquiry_req* ir = (struct vki_hci_inquiry_req*)ARG3;
6931 PRE_MEM_READ("ioctl(HCIINQUIRY)",
6932 (Addr)ARG3, sizeof(struct vki_hci_inquiry_req));
6933 PRE_MEM_WRITE("ioctl(HCIINQUIRY)",
6934 (Addr)ARG3 + sizeof(struct vki_hci_inquiry_req),
6935 ir->num_rsp * sizeof(struct vki_inquiry_info));
6937 break;
6939 case VKI_DRM_IOCTL_VERSION:
6940 if (ARG3) {
6941 struct vki_drm_version *data = (struct vki_drm_version *)ARG3;
6942 PRE_MEM_WRITE("ioctl(DRM_VERSION).version_major", (Addr)&data->version_major, sizeof(data->version_major));
6943 PRE_MEM_WRITE("ioctl(DRM_VERSION).version_minor", (Addr)&data->version_minor, sizeof(data->version_minor));
6944 PRE_MEM_WRITE("ioctl(DRM_VERSION).version_patchlevel", (Addr)&data->version_patchlevel, sizeof(data->version_patchlevel));
6945 PRE_MEM_READ("ioctl(DRM_VERSION).name_len", (Addr)&data->name_len, sizeof(data->name_len));
6946 PRE_MEM_READ("ioctl(DRM_VERSION).name", (Addr)&data->name, sizeof(data->name));
6947 PRE_MEM_WRITE("ioctl(DRM_VERSION).name", (Addr)data->name, data->name_len);
6948 PRE_MEM_READ("ioctl(DRM_VERSION).date_len", (Addr)&data->date_len, sizeof(data->date_len));
6949 PRE_MEM_READ("ioctl(DRM_VERSION).date", (Addr)&data->date, sizeof(data->date));
6950 PRE_MEM_WRITE("ioctl(DRM_VERSION).date", (Addr)data->date, data->date_len);
6951 PRE_MEM_READ("ioctl(DRM_VERSION).desc_len", (Addr)&data->desc_len, sizeof(data->desc_len));
6952 PRE_MEM_READ("ioctl(DRM_VERSION).desc", (Addr)&data->desc, sizeof(data->desc));
6953 PRE_MEM_WRITE("ioctl(DRM_VERSION).desc", (Addr)data->desc, data->desc_len);
6955 break;
6956 case VKI_DRM_IOCTL_GET_UNIQUE:
6957 if (ARG3) {
6958 struct vki_drm_unique *data = (struct vki_drm_unique *)ARG3;
6959 PRE_MEM_READ("ioctl(DRM_GET_UNIQUE).unique_len", (Addr)&data->unique_len, sizeof(data->unique_len));
6960 PRE_MEM_READ("ioctl(DRM_GET_UNIQUE).unique", (Addr)&data->unique, sizeof(data->unique));
6961 PRE_MEM_WRITE("ioctl(DRM_GET_UNIQUE).unique", (Addr)data->unique, data->unique_len);
6963 break;
6964 case VKI_DRM_IOCTL_GET_MAGIC:
6965 if (ARG3) {
6966 struct vki_drm_auth *data = (struct vki_drm_auth *)ARG3;
6967 PRE_MEM_WRITE("ioctl(DRM_GET_MAGIC).magic", (Addr)&data->magic, sizeof(data->magic));
6969 break;
6970 case VKI_DRM_IOCTL_WAIT_VBLANK:
6971 if (ARG3) {
6972 union vki_drm_wait_vblank *data = (union vki_drm_wait_vblank *)ARG3;
6973 PRE_MEM_READ("ioctl(DRM_WAIT_VBLANK).request.type", (Addr)&data->request.type, sizeof(data->request.type));
6974 PRE_MEM_READ("ioctl(DRM_WAIT_VBLANK).request.sequence", (Addr)&data->request.sequence, sizeof(data->request.sequence));
6975 /* XXX: It seems request.signal isn't used */
6976 PRE_MEM_WRITE("ioctl(DRM_WAIT_VBLANK).reply", (Addr)&data->reply, sizeof(data->reply));
6978 break;
6979 case VKI_DRM_IOCTL_GEM_CLOSE:
6980 if (ARG3) {
6981 struct vki_drm_gem_close *data = (struct vki_drm_gem_close *)ARG3;
6982 PRE_MEM_READ("ioctl(DRM_GEM_CLOSE).handle", (Addr)&data->handle, sizeof(data->handle));
6984 break;
6985 case VKI_DRM_IOCTL_GEM_FLINK:
6986 if (ARG3) {
6987 struct vki_drm_gem_flink *data = (struct vki_drm_gem_flink *)ARG3;
6988 PRE_MEM_READ("ioctl(DRM_GEM_FLINK).handle", (Addr)&data->handle, sizeof(data->handle));
6989 PRE_MEM_WRITE("ioctl(DRM_GEM_FLINK).name", (Addr)&data->name, sizeof(data->name));
6991 break;
6992 case VKI_DRM_IOCTL_GEM_OPEN:
6993 if (ARG3) {
6994 struct vki_drm_gem_open *data = (struct vki_drm_gem_open *)ARG3;
6995 PRE_MEM_READ("ioctl(DRM_GEM_OPEN).name", (Addr)&data->name, sizeof(data->name));
6996 PRE_MEM_WRITE("ioctl(DRM_GEM_OPEN).handle", (Addr)&data->handle, sizeof(data->handle));
6997 PRE_MEM_WRITE("ioctl(DRM_GEM_OPEN).size", (Addr)&data->size, sizeof(data->size));
6999 break;
7000 case VKI_DRM_IOCTL_I915_GETPARAM:
7001 if (ARG3) {
7002 vki_drm_i915_getparam_t *data = (vki_drm_i915_getparam_t *)ARG3;
7003 PRE_MEM_READ("ioctl(DRM_I915_GETPARAM).param", (Addr)&data->param, sizeof(data->param));
7004 PRE_MEM_WRITE("ioctl(DRM_I915_GETPARAM).value", (Addr)data->value, sizeof(int));
7006 break;
7007 case VKI_DRM_IOCTL_I915_GEM_BUSY:
7008 if (ARG3) {
7009 struct vki_drm_i915_gem_busy *data = (struct vki_drm_i915_gem_busy *)ARG3;
7010 PRE_MEM_READ("ioctl(DRM_I915_GEM_BUSY).handle", (Addr)&data->handle, sizeof(data->handle));
7011 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_BUSY).busy", (Addr)&data->busy, sizeof(data->busy));
7013 break;
7014 case VKI_DRM_IOCTL_I915_GEM_CREATE:
7015 if (ARG3) {
7016 struct vki_drm_i915_gem_create *data = (struct vki_drm_i915_gem_create *)ARG3;
7017 PRE_MEM_READ("ioctl(DRM_I915_GEM_CREATE).size", (Addr)&data->size, sizeof(data->size));
7018 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_CREATE).handle", (Addr)&data->handle, sizeof(data->handle));
7020 break;
7021 case VKI_DRM_IOCTL_I915_GEM_PREAD:
7022 if (ARG3) {
7023 struct vki_drm_i915_gem_pread *data = (struct vki_drm_i915_gem_pread *)ARG3;
7024 PRE_MEM_READ("ioctl(DRM_I915_GEM_PREAD).handle", (Addr)&data->handle, sizeof(data->handle));
7025 PRE_MEM_READ("ioctl(DRM_I915_GEM_PREAD).offset", (Addr)&data->offset, sizeof(data->offset));
7026 PRE_MEM_READ("ioctl(DRM_I915_GEM_PREAD).size", (Addr)&data->size, sizeof(data->size));
7027 PRE_MEM_READ("ioctl(DRM_I915_GEM_PREAD).data_ptr", (Addr)&data->data_ptr, sizeof(data->data_ptr));
7028 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_PREAD).data_ptr", (Addr)data->data_ptr, data->size);
7030 break;
7031 case VKI_DRM_IOCTL_I915_GEM_PWRITE:
7032 if (ARG3) {
7033 struct vki_drm_i915_gem_pwrite *data = (struct vki_drm_i915_gem_pwrite *)ARG3;
7034 PRE_MEM_READ("ioctl(DRM_I915_GEM_PWRITE).handle", (Addr)&data->handle, sizeof(data->handle));
7035 PRE_MEM_READ("ioctl(DRM_I915_GEM_PWRITE).offset", (Addr)&data->offset, sizeof(data->offset));
7036 PRE_MEM_READ("ioctl(DRM_I915_GEM_PWRITE).size", (Addr)&data->size, sizeof(data->size));
7037 PRE_MEM_READ("ioctl(DRM_I915_GEM_PWRITE).data_ptr", (Addr)&data->data_ptr, sizeof(data->data_ptr));
7038 /* PRE_MEM_READ("ioctl(DRM_I915_GEM_PWRITE).data_ptr", (Addr)data->data_ptr, data->size);
7039 * NB: the buffer is allowed to contain any amount of uninitialized data (e.g.
7040 * interleaved vertex attributes may have a wide stride with uninitialized data between
7041 * consecutive vertices) */
7043 break;
7044 case VKI_DRM_IOCTL_I915_GEM_MMAP_GTT:
7045 if (ARG3) {
7046 struct vki_drm_i915_gem_mmap_gtt *data = (struct vki_drm_i915_gem_mmap_gtt *)ARG3;
7047 PRE_MEM_READ("ioctl(DRM_I915_GEM_MMAP_GTT).handle", (Addr)&data->handle, sizeof(data->handle));
7048 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_MMAP_GTT).offset", (Addr)&data->offset, sizeof(data->offset));
7050 break;
7051 case VKI_DRM_IOCTL_I915_GEM_SET_DOMAIN:
7052 if (ARG3) {
7053 struct vki_drm_i915_gem_set_domain *data = (struct vki_drm_i915_gem_set_domain *)ARG3;
7054 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_DOMAIN).handle", (Addr)&data->handle, sizeof(data->handle));
7055 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_DOMAIN).read_domains", (Addr)&data->read_domains, sizeof(data->read_domains));
7056 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_DOMAIN).write_domain", (Addr)&data->write_domain, sizeof(data->write_domain));
7058 break;
7059 case VKI_DRM_IOCTL_I915_GEM_SET_TILING:
7060 if (ARG3) {
7061 struct vki_drm_i915_gem_set_tiling *data = (struct vki_drm_i915_gem_set_tiling *)ARG3;
7062 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_TILING).handle", (Addr)&data->handle, sizeof(data->handle));
7063 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_TILING).tiling_mode", (Addr)&data->tiling_mode, sizeof(data->tiling_mode));
7064 PRE_MEM_READ("ioctl(DRM_I915_GEM_SET_TILING).stride", (Addr)&data->stride, sizeof(data->stride));
7065 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_SET_TILING).swizzle_mode", (Addr)&data->swizzle_mode, sizeof(data->swizzle_mode));
7067 break;
7068 case VKI_DRM_IOCTL_I915_GEM_GET_TILING:
7069 if (ARG3) {
7070 struct vki_drm_i915_gem_get_tiling *data = (struct vki_drm_i915_gem_get_tiling *)ARG3;
7071 PRE_MEM_READ("ioctl(DRM_I915_GEM_GET_TILING).handle", (Addr)&data->handle, sizeof(data->handle));
7072 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_GET_TILING).tiling_mode", (Addr)&data->tiling_mode, sizeof(data->tiling_mode));
7073 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_GET_TILING).swizzle_mode", (Addr)&data->swizzle_mode, sizeof(data->swizzle_mode));
7075 break;
7076 case VKI_DRM_IOCTL_I915_GEM_GET_APERTURE:
7077 if (ARG3) {
7078 struct vki_drm_i915_gem_get_aperture *data = (struct vki_drm_i915_gem_get_aperture *)ARG3;
7079 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_GET_APERTURE).aper_size", (Addr)&data->aper_size, sizeof(data->aper_size));
7080 PRE_MEM_WRITE("ioctl(DRM_I915_GEM_GET_APERTURE).aper_available_size", (Addr)&data->aper_available_size, sizeof(data->aper_available_size));
7082 break;
7084 /* KVM ioctls that check for a numeric value as parameter */
7085 case VKI_KVM_GET_API_VERSION:
7086 case VKI_KVM_CREATE_VM:
7087 case VKI_KVM_GET_VCPU_MMAP_SIZE:
7088 case VKI_KVM_CHECK_EXTENSION:
7089 case VKI_KVM_SET_TSS_ADDR:
7090 case VKI_KVM_CREATE_VCPU:
7091 case VKI_KVM_RUN:
7092 break;
7094 #ifdef ENABLE_XEN
7095 case VKI_XEN_IOCTL_PRIVCMD_HYPERCALL: {
7096 SyscallArgs harrghs;
7097 struct vki_xen_privcmd_hypercall *args =
7098 (struct vki_xen_privcmd_hypercall *)(ARG3);
7100 if (!args)
7101 break;
7103 VG_(memset)(&harrghs, 0, sizeof(harrghs));
7104 harrghs.sysno = args->op;
7105 harrghs.arg1 = args->arg[0];
7106 harrghs.arg2 = args->arg[1];
7107 harrghs.arg3 = args->arg[2];
7108 harrghs.arg4 = args->arg[3];
7109 harrghs.arg5 = args->arg[4];
7110 harrghs.arg6 = harrghs.arg7 = harrghs.arg8 = 0;
7112 WRAPPER_PRE_NAME(xen, hypercall) (tid, layout, &harrghs, status, flags);
7114 /* HACK. arg8 is used to return the number of hypercall
7115 * arguments actually consumed! */
7116 PRE_MEM_READ("hypercall", ARG3, sizeof(args->op) +
7117 ( sizeof(args->arg[0]) * harrghs.arg8 ) );
7119 break;
7122 case VKI_XEN_IOCTL_PRIVCMD_MMAP: {
7123 struct vki_xen_privcmd_mmap *args =
7124 (struct vki_xen_privcmd_mmap *)(ARG3);
7125 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAP(num)",
7126 (Addr)&args->num, sizeof(args->num));
7127 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAP(dom)",
7128 (Addr)&args->dom, sizeof(args->dom));
7129 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAP(entry)",
7130 (Addr)args->entry, sizeof(*(args->entry)) * args->num);
7131 break;
7133 case VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH: {
7134 struct vki_xen_privcmd_mmapbatch *args =
7135 (struct vki_xen_privcmd_mmapbatch *)(ARG3);
7136 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH(num)",
7137 (Addr)&args->num, sizeof(args->num));
7138 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH(dom)",
7139 (Addr)&args->dom, sizeof(args->dom));
7140 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH(addr)",
7141 (Addr)&args->addr, sizeof(args->addr));
7142 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH(arr)",
7143 (Addr)args->arr, sizeof(*(args->arr)) * args->num);
7144 break;
7146 case VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2: {
7147 struct vki_xen_privcmd_mmapbatch_v2 *args =
7148 (struct vki_xen_privcmd_mmapbatch_v2 *)(ARG3);
7149 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2(num)",
7150 (Addr)&args->num, sizeof(args->num));
7151 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2(dom)",
7152 (Addr)&args->dom, sizeof(args->dom));
7153 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2(addr)",
7154 (Addr)&args->addr, sizeof(args->addr));
7155 PRE_MEM_READ("VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2(arr)",
7156 (Addr)args->arr, sizeof(*(args->arr)) * args->num);
7157 break;
7160 case VKI_XEN_IOCTL_EVTCHN_BIND_VIRQ: {
7161 struct vki_xen_ioctl_evtchn_bind_virq *args =
7162 (struct vki_xen_ioctl_evtchn_bind_virq *)(ARG3);
7163 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_BIND_VIRQ(virq)",
7164 (Addr)&args->virq, sizeof(args->virq));
7166 break;
7167 case VKI_XEN_IOCTL_EVTCHN_BIND_INTERDOMAIN: {
7168 struct vki_xen_ioctl_evtchn_bind_interdomain *args =
7169 (struct vki_xen_ioctl_evtchn_bind_interdomain *)(ARG3);
7170 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_BIND_INTERDOMAIN(remote_domain)",
7171 (Addr)&args->remote_domain, sizeof(args->remote_domain));
7172 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_BIND_INTERDOMAIN(remote_port)",
7173 (Addr)&args->remote_port, sizeof(args->remote_port));
7175 break;
7176 case VKI_XEN_IOCTL_EVTCHN_BIND_UNBOUND_PORT: {
7177 struct vki_xen_ioctl_evtchn_bind_unbound_port *args =
7178 (struct vki_xen_ioctl_evtchn_bind_unbound_port *)(ARG3);
7179 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_BIND_UNBOUND_PORT(remote_domain)",
7180 (Addr)&args->remote_domain, sizeof(args->remote_domain));
7182 break;
7183 case VKI_XEN_IOCTL_EVTCHN_UNBIND: {
7184 struct vki_xen_ioctl_evtchn_unbind *args =
7185 (struct vki_xen_ioctl_evtchn_unbind *)(ARG3);
7186 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_UNBIND(port)",
7187 (Addr)&args->port, sizeof(args->port));
7189 break;
7190 case VKI_XEN_IOCTL_EVTCHN_NOTIFY: {
7191 struct vki_xen_ioctl_evtchn_notify *args =
7192 (struct vki_xen_ioctl_evtchn_notify*)(ARG3);
7193 PRE_MEM_READ("VKI_XEN_IOCTL_EVTCHN_notify(port)",
7194 (Addr)&args->port, sizeof(args->port));
7196 break;
7197 case VKI_XEN_IOCTL_EVTCHN_RESET:
7198 /* No input*/
7199 break;
7200 #endif
7202 /* To do: figure out which software layer extends the sign of 'request' */
7203 case VKI_OBD_IOC_FID2PATH:
7204 PRE_MEM_READ("VKI_OBD_IOC_FID2PATH(args)", ARG3,
7205 sizeof(struct vki_getinfo_fid2path));
7206 break;
7208 /* V4L2 */
7209 case VKI_V4L2_QUERYCAP: {
7210 struct vki_v4l2_capability *data = (struct vki_v4l2_capability *)ARG3;
7211 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERYCAP)", (Addr)data, sizeof(*data));
7212 break;
7214 case VKI_V4L2_ENUM_FMT: {
7215 struct vki_v4l2_fmtdesc *data = (struct vki_v4l2_fmtdesc *)ARG3;
7216 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FMT).index", data->index);
7217 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FMT).type", data->type);
7218 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FMT).flags", data->flags);
7219 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FMT).description", data->description);
7220 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FMT).pixelformat", data->pixelformat);
7221 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FMT).reserved", data->reserved);
7222 break;
7224 case VKI_V4L2_G_FMT: {
7225 struct vki_v4l2_format *data = (struct vki_v4l2_format *)ARG3;
7226 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FMT).type", data->type);
7227 switch (data->type) {
7228 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE:
7229 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT:
7230 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FMT).fmt.pix.priv", data->fmt.pix.priv);
7231 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.pix", data->fmt.pix);
7232 PRE_MEM_READ("ioctl(VKI_V4L2_G_FMT)",
7233 (Addr)&data->type + sizeof(data->type) + sizeof(data->fmt.pix),
7234 sizeof(*data) - sizeof(data->type) - sizeof(data->fmt.pix));
7235 break;
7236 case VKI_V4L2_BUF_TYPE_VBI_CAPTURE:
7237 case VKI_V4L2_BUF_TYPE_VBI_OUTPUT:
7238 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.vbi", data->fmt.vbi);
7239 break;
7240 case VKI_V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
7241 case VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
7242 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.sliced", data->fmt.sliced);
7243 break;
7244 case VKI_V4L2_BUF_TYPE_VIDEO_OVERLAY:
7245 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
7246 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FMT).fmt.win.clips", data->fmt.win.clips);
7247 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FMT).fmt.win.bitmap", data->fmt.win.bitmap);
7248 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FMT).fmt.win.clipcount", data->fmt.win.clipcount);
7249 if (data->fmt.win.clipcount && data->fmt.win.clips)
7250 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.clips[]",
7251 (Addr)data->fmt.win.clips,
7252 data->fmt.win.clipcount * sizeof(data->fmt.win.clips[0]));
7253 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.clipcount", data->fmt.win.clipcount);
7254 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.w", data->fmt.win.w);
7255 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.field", data->fmt.win.field);
7256 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.chromakey", data->fmt.win.chromakey);
7257 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.win.global_alpha", data->fmt.win.global_alpha);
7258 break;
7259 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
7260 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
7261 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.pix_mp", data->fmt.pix_mp);
7262 break;
7263 case VKI_V4L2_BUF_TYPE_SDR_CAPTURE:
7264 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FMT).fmt.sdr", data->fmt.sdr);
7265 break;
7267 break;
7269 case VKI_V4L2_S_FMT: {
7270 struct vki_v4l2_format *data = (struct vki_v4l2_format *)ARG3;
7271 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).type", data->type);
7272 switch (data->type) {
7273 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE:
7274 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT:
7275 PRE_MEM_READ("ioctl(VKI_V4L2_S_FMT)",
7276 (Addr)&data->type + sizeof(data->type),
7277 sizeof(*data) - sizeof(data->type));
7278 break;
7279 case VKI_V4L2_BUF_TYPE_VBI_CAPTURE:
7280 case VKI_V4L2_BUF_TYPE_VBI_OUTPUT:
7281 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).fmt.vbi", data->fmt.vbi);
7282 break;
7283 case VKI_V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
7284 case VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
7285 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).fmt.sliced", data->fmt.sliced);
7286 break;
7287 case VKI_V4L2_BUF_TYPE_VIDEO_OVERLAY:
7288 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
7289 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).fmt.win", data->fmt.win);
7290 if (data->fmt.win.clipcount && data->fmt.win.clips)
7291 PRE_MEM_READ("ioctl(VKI_V4L2_S_FMT).fmt.win.clips[]",
7292 (Addr)data->fmt.win.clips,
7293 data->fmt.win.clipcount * sizeof(data->fmt.win.clips[0]));
7294 if (data->fmt.win.bitmap)
7295 PRE_MEM_READ("ioctl(VKI_V4L2_S_FMT).fmt.win.bitmap[]",
7296 (Addr)data->fmt.win.bitmap,
7297 data->fmt.win.w.height * ((data->fmt.win.w.width + 7) / 8));
7298 break;
7299 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
7300 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
7301 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).fmt.pix_mp", data->fmt.pix_mp);
7302 break;
7303 case VKI_V4L2_BUF_TYPE_SDR_CAPTURE:
7304 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FMT).fmt.sdr", data->fmt.sdr);
7305 break;
7307 break;
7309 case VKI_V4L2_TRY_FMT: {
7310 struct vki_v4l2_format *data = (struct vki_v4l2_format *)ARG3;
7311 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).type", data->type);
7312 switch (data->type) {
7313 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE:
7314 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT:
7315 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_FMT)",
7316 (Addr)&data->type + sizeof(data->type),
7317 sizeof(*data) - sizeof(data->type));
7318 break;
7319 case VKI_V4L2_BUF_TYPE_VBI_CAPTURE:
7320 case VKI_V4L2_BUF_TYPE_VBI_OUTPUT:
7321 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.vbi", data->fmt.vbi);
7322 break;
7323 case VKI_V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
7324 case VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
7325 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.sliced", data->fmt.sliced);
7326 break;
7327 case VKI_V4L2_BUF_TYPE_VIDEO_OVERLAY:
7328 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
7329 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.win", data->fmt.win);
7330 if (data->fmt.win.clipcount && data->fmt.win.clips)
7331 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.win.clips[]",
7332 (Addr)data->fmt.win.clips,
7333 data->fmt.win.clipcount * sizeof(data->fmt.win.clips[0]));
7334 if (data->fmt.win.bitmap)
7335 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.win.bitmap[]",
7336 (Addr)data->fmt.win.bitmap,
7337 data->fmt.win.w.height * ((data->fmt.win.w.width + 7) / 8));
7338 break;
7339 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
7340 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
7341 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.pix_mp", data->fmt.pix_mp);
7342 break;
7343 case VKI_V4L2_BUF_TYPE_SDR_CAPTURE:
7344 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_FMT).fmt.sdr", data->fmt.sdr);
7345 break;
7347 break;
7349 case VKI_V4L2_REQBUFS: {
7350 struct vki_v4l2_requestbuffers *data = (struct vki_v4l2_requestbuffers *)ARG3;
7351 PRE_MEM_READ("ioctl(VKI_V4L2_REQBUFS)", (Addr)data, sizeof(*data));
7352 break;
7354 case VKI_V4L2_QUERYBUF: {
7355 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
7356 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).type", data->type);
7357 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).index", data->index);
7358 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).reserved", data->reserved);
7359 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).reserved2", data->reserved2);
7360 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
7361 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
7362 unsigned i;
7364 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).length", data->length);
7365 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYBUF).m.planes", data->m.planes);
7366 for (i = 0; i < data->length; i++) {
7367 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m.planes[].bytesused", data->m.planes[i].bytesused);
7368 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m.planes[].length", data->m.planes[i].length);
7369 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m.planes[].m", data->m.planes[i].m);
7370 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m.planes[].data_offset", data->m.planes[i].data_offset);
7371 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m.planes[].reserved", data->m.planes[i].reserved);
7373 } else {
7374 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).m", data->m);
7375 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).length", data->length);
7377 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).bytesused", data->bytesused);
7378 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).flags", data->flags);
7379 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).field", data->field);
7380 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).timestamp", data->timestamp);
7381 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).timecode", data->timecode);
7382 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).sequence", data->sequence);
7383 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).memory", data->memory);
7384 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QUERYBUF).sequence", data->sequence);
7385 break;
7387 case VKI_V4L2_G_FBUF: {
7388 struct vki_v4l2_framebuffer *data = (struct vki_v4l2_framebuffer *)ARG3;
7389 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_FBUF)", (Addr)data, sizeof(*data));
7390 break;
7392 case VKI_V4L2_S_FBUF: {
7393 struct vki_v4l2_framebuffer *data = (struct vki_v4l2_framebuffer *)ARG3;
7394 PRE_FIELD_WRITE("ioctl(VKI_V4L2_S_FBUF).capability", data->capability);
7395 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FBUF).flags", data->flags);
7396 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FBUF).base", data->base);
7397 PRE_FIELD_READ("ioctl(VKI_V4L2_S_FBUF).fmt", data->fmt);
7398 break;
7400 case VKI_V4L2_OVERLAY: {
7401 int *data = (int *)ARG3;
7402 PRE_MEM_READ("ioctl(VKI_V4L2_OVERLAY)", (Addr)data, sizeof(*data));
7403 break;
7405 case VKI_V4L2_QBUF: {
7406 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
7407 int is_output = data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT ||
7408 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE ||
7409 data->type == VKI_V4L2_BUF_TYPE_VBI_OUTPUT ||
7410 data->type == VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT;
7412 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).type", data->type);
7413 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).index", data->index);
7414 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).flags", data->flags);
7415 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).memory", data->memory);
7416 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).reserved", data->reserved);
7417 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).reserved2", data->reserved2);
7418 if (is_output) {
7419 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).bytesused", data->bytesused);
7420 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).field", data->field);
7422 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
7423 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
7424 unsigned i;
7426 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).length", data->length);
7427 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes", data->m.planes);
7428 for (i = 0; i < data->length; i++) {
7429 if (is_output) {
7430 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes[].bytesused", data->m.planes[i].bytesused);
7431 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes[].data_offset", data->m.planes[i].data_offset);
7433 if (data->memory == VKI_V4L2_MEMORY_MMAP)
7434 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QBUF).m.planes[].m", data->m.planes[i].m);
7435 else if (data->memory == VKI_V4L2_MEMORY_DMABUF)
7436 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes[].m.fd", data->m.planes[i].m.fd);
7437 else
7438 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes[].m", data->m.planes[i].m);
7439 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.planes[].reserved", data->m.planes[i].reserved);
7441 } else {
7442 if (data->memory == VKI_V4L2_MEMORY_MMAP)
7443 PRE_FIELD_WRITE("ioctl(VKI_V4L2_QBUF).m", data->m);
7444 else if (data->memory == VKI_V4L2_MEMORY_DMABUF)
7445 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m.fd", data->m.fd);
7446 else
7447 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).m", data->m);
7448 if (is_output) {
7449 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).bytesused", data->bytesused);
7450 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).field", data->field);
7453 if (is_output && (data->flags & VKI_V4L2_BUF_FLAG_TIMESTAMP_MASK) == VKI_V4L2_BUF_FLAG_TIMESTAMP_COPY) {
7454 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).timestamp", data->timestamp);
7455 PRE_FIELD_READ("ioctl(VKI_V4L2_QBUF).timecode", data->timecode);
7457 break;
7459 case VKI_V4L2_EXPBUF: {
7460 struct vki_v4l2_exportbuffer *data = (struct vki_v4l2_exportbuffer *)ARG3;
7461 PRE_FIELD_READ("ioctl(VKI_V4L2_EXPBUF).type", data->type);
7462 PRE_FIELD_READ("ioctl(VKI_V4L2_EXPBUF).index", data->index);
7463 PRE_FIELD_READ("ioctl(VKI_V4L2_EXPBUF).plane", data->plane);
7464 PRE_FIELD_READ("ioctl(VKI_V4L2_EXPBUF).flags", data->flags);
7465 PRE_FIELD_WRITE("ioctl(VKI_V4L2_EXPBUF).fd", data->fd);
7466 PRE_FIELD_READ("ioctl(VKI_V4L2_EXPBUF).reserved", data->reserved);
7467 break;
7469 case VKI_V4L2_DQBUF: {
7470 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
7471 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).type", data->type);
7472 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).index", data->index);
7473 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).memory", data->memory);
7474 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).reserved", data->reserved);
7475 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).reserved2", data->reserved2);
7476 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).bytesused", data->bytesused);
7477 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).field", data->field);
7478 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
7479 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
7480 unsigned i;
7482 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).length", data->length);
7483 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).m.planes", data->m.planes);
7484 for (i = 0; i < data->length; i++) {
7485 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).m.planes[].bytesused", data->m.planes[i].bytesused);
7486 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).m.planes[].data_offset", data->m.planes[i].data_offset);
7487 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).m.planes[].length", data->m.planes[i].length);
7488 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).m.planes[].m", data->m.planes[i].m);
7489 PRE_FIELD_READ("ioctl(VKI_V4L2_DQBUF).m.planes[].reserved", data->m.planes[i].reserved);
7491 } else {
7492 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).m", data->m);
7493 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).length", data->length);
7494 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).bytesused", data->bytesused);
7495 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).field", data->field);
7497 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).timestamp", data->timestamp);
7498 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).timecode", data->timecode);
7499 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DQBUF).sequence", data->sequence);
7500 break;
7502 case VKI_V4L2_STREAMON: {
7503 int *data = (int *)ARG3;
7504 PRE_MEM_READ("ioctl(VKI_V4L2_STREAMON)", (Addr)data, sizeof(*data));
7505 break;
7507 case VKI_V4L2_STREAMOFF: {
7508 int *data = (int *)ARG3;
7509 PRE_MEM_READ("ioctl(VKI_V4L2_STREAMOFF)", (Addr)data, sizeof(*data));
7510 break;
7512 case VKI_V4L2_G_PARM: {
7513 struct vki_v4l2_streamparm *data = (struct vki_v4l2_streamparm *)ARG3;
7514 int is_output = data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT ||
7515 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE ||
7516 data->type == VKI_V4L2_BUF_TYPE_VBI_OUTPUT ||
7517 data->type == VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT;
7519 PRE_FIELD_READ("ioctl(VKI_V4L2_G_PARM).type", data->type);
7520 if (is_output) {
7521 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_PARM)", (Addr)&data->parm.output,
7522 sizeof(data->parm.output) - sizeof(data->parm.output.reserved));
7523 PRE_FIELD_READ("ioctl(VKI_V4L2_G_PARM).parm.output.reserved", data->parm.output.reserved);
7524 } else {
7525 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_PARM)", (Addr)&data->parm.capture,
7526 sizeof(data->parm.capture) - sizeof(data->parm.capture.reserved));
7527 PRE_FIELD_READ("ioctl(VKI_V4L2_G_PARM).parm.capture.reserved", data->parm.capture.reserved);
7529 break;
7531 case VKI_V4L2_S_PARM: {
7532 struct vki_v4l2_streamparm *data = (struct vki_v4l2_streamparm *)ARG3;
7533 int is_output = data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT ||
7534 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE ||
7535 data->type == VKI_V4L2_BUF_TYPE_VBI_OUTPUT ||
7536 data->type == VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT;
7538 PRE_FIELD_READ("ioctl(VKI_V4L2_S_PARM).type", data->type);
7539 if (is_output)
7540 PRE_FIELD_READ("ioctl(VKI_V4L2_S_PARM).parm.output", data->parm.output);
7541 else
7542 PRE_FIELD_READ("ioctl(VKI_V4L2_S_PARM).parm.capture", data->parm.capture);
7543 break;
7545 case VKI_V4L2_G_STD: {
7546 vki_v4l2_std_id *data = (vki_v4l2_std_id *)ARG3;
7547 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_STD)", (Addr)data, sizeof(*data));
7548 break;
7550 case VKI_V4L2_S_STD: {
7551 vki_v4l2_std_id *data = (vki_v4l2_std_id *)ARG3;
7552 PRE_MEM_READ("ioctl(VKI_V4L2_S_STD)", (Addr)data, sizeof(*data));
7553 break;
7555 case VKI_V4L2_ENUMSTD: {
7556 struct vki_v4l2_standard *data = (struct vki_v4l2_standard *)ARG3;
7557 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMSTD).index", data->index);
7558 PRE_MEM_WRITE("ioctl(VKI_V4L2_ENUMSTD)", (Addr)&data->id, sizeof(*data) - sizeof(data->index));
7559 break;
7561 case VKI_V4L2_ENUMINPUT: {
7562 struct vki_v4l2_input *data = (struct vki_v4l2_input *)ARG3;
7563 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMINPUT).index", data->index);
7564 PRE_MEM_WRITE("ioctl(VKI_V4L2_ENUMINPUT)", (Addr)data->name, sizeof(*data) - sizeof(data->index));
7565 break;
7567 case VKI_V4L2_G_CTRL: {
7568 struct vki_v4l2_control *data = (struct vki_v4l2_control *)ARG3;
7569 PRE_FIELD_READ("ioctl(VKI_V4L2_G_CTRL).id", data->id);
7570 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_CTRL).value", data->value);
7571 break;
7573 case VKI_V4L2_S_CTRL: {
7574 struct vki_v4l2_control *data = (struct vki_v4l2_control *)ARG3;
7575 PRE_MEM_READ("ioctl(VKI_V4L2_S_CTRL)", (Addr)data, sizeof(*data));
7576 break;
7578 case VKI_V4L2_G_TUNER: {
7579 struct vki_v4l2_tuner *data = (struct vki_v4l2_tuner *)ARG3;
7580 PRE_FIELD_READ("ioctl(VKI_V4L2_G_TUNER).index", data->index);
7581 PRE_FIELD_READ("ioctl(VKI_V4L2_G_TUNER).reserved", data->reserved);
7582 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_TUNER)", (Addr)data->name,
7583 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7584 break;
7586 case VKI_V4L2_S_TUNER: {
7587 struct vki_v4l2_tuner *data = (struct vki_v4l2_tuner *)ARG3;
7588 PRE_FIELD_READ("ioctl(VKI_V4L2_S_TUNER).index", data->index);
7589 PRE_FIELD_READ("ioctl(VKI_V4L2_S_TUNER).audmode", data->audmode);
7590 PRE_FIELD_READ("ioctl(VKI_V4L2_S_TUNER).reserved", data->reserved);
7591 break;
7593 case VKI_V4L2_G_AUDIO: {
7594 struct vki_v4l2_audio *data = (struct vki_v4l2_audio *)ARG3;
7595 PRE_FIELD_READ("ioctl(VKI_V4L2_G_AUDIO).index", data->index);
7596 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_AUDIO)", (Addr)data->name,
7597 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7598 PRE_FIELD_READ("ioctl(VKI_V4L2_G_AUDIO).reserved", data->reserved);
7599 break;
7601 case VKI_V4L2_S_AUDIO: {
7602 struct vki_v4l2_audio *data = (struct vki_v4l2_audio *)ARG3;
7603 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDIO).index", data->index);
7604 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDIO).mode", data->mode);
7605 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDIO).reserved", data->reserved);
7606 break;
7608 case VKI_V4L2_QUERYCTRL: {
7609 struct vki_v4l2_queryctrl *data = (struct vki_v4l2_queryctrl *)ARG3;
7610 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYCTRL).id", data->id);
7611 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERYCTRL)", (Addr)&data->type,
7612 sizeof(*data) - sizeof(data->id));
7613 break;
7615 case VKI_V4L2_QUERYMENU: {
7616 struct vki_v4l2_querymenu *data = (struct vki_v4l2_querymenu *)ARG3;
7617 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYMENU).id", data->id);
7618 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERYMENU).index", data->index);
7619 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERYMENU)", (Addr)data->name,
7620 sizeof(*data) - sizeof(data->id) - sizeof(data->index));
7621 break;
7623 case VKI_V4L2_G_INPUT: {
7624 int *data = (int *)ARG3;
7625 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_INPUT)", (Addr)data, sizeof(*data));
7626 break;
7628 case VKI_V4L2_S_INPUT: {
7629 int *data = (int *)ARG3;
7630 PRE_MEM_READ("ioctl(VKI_V4L2_S_INPUT)", (Addr)data, sizeof(*data));
7631 break;
7633 case VKI_V4L2_G_EDID: {
7634 struct vki_v4l2_edid *data = (struct vki_v4l2_edid *)ARG3;
7635 PRE_MEM_READ("ioctl(VKI_V4L2_G_EDID)", (Addr)data, sizeof(*data));
7636 if (data->blocks && data->edid)
7637 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_EDID)", (Addr)data->edid, data->blocks * 128);
7638 break;
7640 case VKI_V4L2_S_EDID: {
7641 struct vki_v4l2_edid *data = (struct vki_v4l2_edid *)ARG3;
7642 PRE_MEM_READ("ioctl(VKI_V4L2_S_EDID)", (Addr)data, sizeof(*data));
7643 if (data->blocks && data->edid)
7644 PRE_MEM_READ("ioctl(VKI_V4L2_S_EDID)", (Addr)data->edid, data->blocks * 128);
7645 break;
7647 case VKI_V4L2_G_OUTPUT: {
7648 int *data = (int *)ARG3;
7649 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_OUTPUT)", (Addr)data, sizeof(*data));
7650 break;
7652 case VKI_V4L2_S_OUTPUT: {
7653 int *data = (int *)ARG3;
7654 PRE_MEM_READ("ioctl(VKI_V4L2_S_OUTPUT)", (Addr)data, sizeof(*data));
7655 break;
7657 case VKI_V4L2_ENUMOUTPUT: {
7658 struct vki_v4l2_output *data = (struct vki_v4l2_output *)ARG3;
7659 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMOUTPUT).index", data->index);
7660 PRE_MEM_WRITE("ioctl(VKI_V4L2_ENUMOUTPUT)", (Addr)data->name, sizeof(*data) - sizeof(data->index));
7661 break;
7663 case VKI_V4L2_G_AUDOUT: {
7664 struct vki_v4l2_audioout *data = (struct vki_v4l2_audioout *)ARG3;
7665 PRE_FIELD_READ("ioctl(VKI_V4L2_G_AUDOUT).index", data->index);
7666 PRE_FIELD_READ("ioctl(VKI_V4L2_G_AUDOUT).reserved", data->reserved);
7667 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_AUDOUT)", (Addr)data->name,
7668 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7669 break;
7671 case VKI_V4L2_S_AUDOUT: {
7672 struct vki_v4l2_audioout *data = (struct vki_v4l2_audioout *)ARG3;
7673 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDOUT).index", data->index);
7674 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDOUT).reserved", data->reserved);
7675 PRE_FIELD_READ("ioctl(VKI_V4L2_S_AUDOUT).mode", data->mode);
7676 break;
7678 case VKI_V4L2_G_MODULATOR: {
7679 struct vki_v4l2_modulator *data = (struct vki_v4l2_modulator *)ARG3;
7680 PRE_FIELD_READ("ioctl(VKI_V4L2_G_MODULATOR).index", data->index);
7681 PRE_FIELD_READ("ioctl(VKI_V4L2_G_MODULATOR).reserved", data->reserved);
7682 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_MODULATOR)", (Addr)data->name,
7683 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7684 break;
7686 case VKI_V4L2_S_MODULATOR: {
7687 struct vki_v4l2_modulator *data = (struct vki_v4l2_modulator *)ARG3;
7688 PRE_FIELD_READ("ioctl(VKI_V4L2_S_MODULATOR).index", data->index);
7689 PRE_FIELD_READ("ioctl(VKI_V4L2_S_MODULATOR).txsubchans", data->txsubchans);
7690 PRE_FIELD_READ("ioctl(VKI_V4L2_S_MODULATOR).reserved", data->reserved);
7691 break;
7693 case VKI_V4L2_G_FREQUENCY: {
7694 struct vki_v4l2_frequency *data = (struct vki_v4l2_frequency *)ARG3;
7695 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FREQUENCY).tuner", data->tuner);
7696 PRE_FIELD_READ("ioctl(VKI_V4L2_G_FREQUENCY).reserved", data->reserved);
7697 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FREQUENCY).type", data->type);
7698 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_FREQUENCY).frequency", data->frequency);
7699 break;
7701 case VKI_V4L2_S_FREQUENCY: {
7702 struct vki_v4l2_frequency *data = (struct vki_v4l2_frequency *)ARG3;
7703 PRE_MEM_READ("ioctl(VKI_V4L2_S_FREQUENCY)", (Addr)data, sizeof(*data));
7704 break;
7706 case VKI_V4L2_CROPCAP: {
7707 struct vki_v4l2_cropcap *data = (struct vki_v4l2_cropcap *)ARG3;
7708 PRE_FIELD_READ("ioctl(VKI_V4L2_CROPCAP)", data->type);
7709 PRE_MEM_WRITE("ioctl(VKI_V4L2_CROPCAP)", (Addr)&data->bounds, sizeof(*data) - sizeof(data->type));
7710 break;
7712 case VKI_V4L2_G_CROP: {
7713 struct vki_v4l2_crop *data = (struct vki_v4l2_crop *)ARG3;
7714 PRE_FIELD_READ("ioctl(VKI_V4L2_G_CROP).type", data->type);
7715 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_CROP).c", data->c);
7716 break;
7718 case VKI_V4L2_S_CROP: {
7719 struct vki_v4l2_crop *data = (struct vki_v4l2_crop *)ARG3;
7720 PRE_MEM_READ("ioctl(VKI_V4L2_S_CROP)", (Addr)data, sizeof(*data));
7721 break;
7723 case VKI_V4L2_G_JPEGCOMP: {
7724 struct vki_v4l2_jpegcompression *data = (struct vki_v4l2_jpegcompression *)ARG3;
7725 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_JPEGCOMP)", (Addr)data, sizeof(*data));
7726 break;
7728 case VKI_V4L2_S_JPEGCOMP: {
7729 struct vki_v4l2_jpegcompression *data = (struct vki_v4l2_jpegcompression *)ARG3;
7730 PRE_MEM_READ("ioctl(VKI_V4L2_S_JPEGCOMP)", (Addr)data, sizeof(*data));
7731 break;
7733 case VKI_V4L2_QUERYSTD: {
7734 vki_v4l2_std_id *data = (vki_v4l2_std_id *)ARG3;
7735 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERYSTD)", (Addr)data, sizeof(*data));
7736 break;
7738 case VKI_V4L2_ENUMAUDIO: {
7739 struct vki_v4l2_audio *data = (struct vki_v4l2_audio *)ARG3;
7740 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMAUDIO).index", data->index);
7741 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMAUDIO).reserved", data->reserved);
7742 PRE_MEM_WRITE("ioctl(VKI_V4L2_ENUMAUDIO)", (Addr)data->name,
7743 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7744 break;
7746 case VKI_V4L2_ENUMAUDOUT: {
7747 struct vki_v4l2_audioout *data = (struct vki_v4l2_audioout *)ARG3;
7748 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMAUDOUT).index", data->index);
7749 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUMAUDOUT).reserved", data->reserved);
7750 PRE_MEM_WRITE("ioctl(VKI_V4L2_ENUMAUDOUT)", (Addr)data->name,
7751 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
7752 break;
7754 case VKI_V4L2_G_PRIORITY: {
7755 __vki_u32 *data = (__vki_u32 *)ARG3;
7756 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_PRIORITY)", (Addr)data, sizeof(*data));
7757 break;
7759 case VKI_V4L2_S_PRIORITY: {
7760 __vki_u32 *data = (__vki_u32 *)ARG3;
7761 PRE_MEM_READ("ioctl(VKI_V4L2_S_PRIORITY)", (Addr)data, sizeof(*data));
7762 break;
7764 case VKI_V4L2_G_SLICED_VBI_CAP: {
7765 struct vki_v4l2_sliced_vbi_cap *data = (struct vki_v4l2_sliced_vbi_cap *)ARG3;
7766 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SLICED_VBI_CAP).type", data->type);
7767 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SLICED_VBI_CAP).reserved", data->reserved);
7768 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_SLICED_VBI_CAP)", (Addr)data,
7769 sizeof(*data) - sizeof(data->type) - sizeof(data->reserved));
7770 break;
7772 case VKI_V4L2_G_EXT_CTRLS: {
7773 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
7774 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).ctrl_class", data->ctrl_class);
7775 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).count", data->count);
7776 if (data->count) {
7777 unsigned i;
7779 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).controls", data->controls);
7780 for (i = 0; i < data->count; i++) {
7781 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].id", data->controls[i].id);
7782 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].size", data->controls[i].size);
7783 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].reserved2", data->controls[i].reserved2);
7784 if (data->controls[i].size) {
7785 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].ptr", data->controls[i].ptr);
7786 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].ptr[]",
7787 (Addr)data->controls[i].ptr, data->controls[i].size);
7788 } else {
7789 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_EXT_CTRLS).controls[].value64",
7790 data->controls[i].value64);
7794 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_EXT_CTRLS).error_idx", data->error_idx);
7795 PRE_FIELD_READ("ioctl(VKI_V4L2_G_EXT_CTRLS).reserved", data->reserved);
7796 break;
7798 case VKI_V4L2_S_EXT_CTRLS: {
7799 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
7800 PRE_FIELD_READ("ioctl(VKI_V4L2_S_EXT_CTRLS).ctrl_class", data->ctrl_class);
7801 PRE_FIELD_READ("ioctl(VKI_V4L2_S_EXT_CTRLS).count", data->count);
7802 if (data->count) {
7803 unsigned i;
7805 PRE_FIELD_READ("ioctl(VKI_V4L2_S_EXT_CTRLS).controls", data->controls);
7806 PRE_MEM_READ("ioctl(VKI_V4L2_S_EXT_CTRLS)", (Addr)data->controls,
7807 data->count * sizeof(data->controls[0]));
7808 for (i = 0; i < data->count; i++) {
7809 if (data->controls[i].size) {
7810 PRE_MEM_READ("ioctl(VKI_V4L2_S_EXT_CTRLS).controls[].ptr[]",
7811 (Addr)data->controls[i].ptr, data->controls[i].size);
7815 PRE_FIELD_WRITE("ioctl(VKI_V4L2_S_EXT_CTRLS).error_idx", data->error_idx);
7816 PRE_FIELD_READ("ioctl(VKI_V4L2_S_EXT_CTRLS).reserved", data->reserved);
7817 break;
7819 case VKI_V4L2_TRY_EXT_CTRLS: {
7820 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
7821 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS).ctrl_class", data->ctrl_class);
7822 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS).count", data->count);
7823 if (data->count) {
7824 unsigned i;
7826 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS).controls", data->controls);
7827 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS)", (Addr)data->controls,
7828 data->count * sizeof(data->controls[0]));
7829 for (i = 0; i < data->count; i++) {
7830 if (data->controls[i].size) {
7831 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS).controls[].ptr[]",
7832 (Addr)data->controls[i].ptr, data->controls[i].size);
7836 PRE_FIELD_WRITE("ioctl(VKI_V4L2_TRY_EXT_CTRLS).error_idx", data->error_idx);
7837 PRE_FIELD_READ("ioctl(VKI_V4L2_TRY_EXT_CTRLS).reserved", data->reserved);
7838 break;
7840 case VKI_V4L2_ENUM_FRAMESIZES: {
7841 struct vki_v4l2_frmsizeenum *data = (struct vki_v4l2_frmsizeenum *)ARG3;
7842 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMESIZES).index", data->index);
7843 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMESIZES).pixel_format", data->pixel_format);
7844 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMESIZES).reserved", data->reserved);
7845 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FRAMESIZES).type", data->type);
7846 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FRAMESIZES).stepwise", data->stepwise);
7847 break;
7849 case VKI_V4L2_ENUM_FRAMEINTERVALS: {
7850 struct vki_v4l2_frmivalenum *data = (struct vki_v4l2_frmivalenum *)ARG3;
7851 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).index", data->index);
7852 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).pixel_format", data->pixel_format);
7853 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).width", data->width);
7854 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).height", data->height);
7855 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).reserved", data->reserved);
7856 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).type", data->type);
7857 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FRAMEINTERVALS).stepwise", data->stepwise);
7858 break;
7860 case VKI_V4L2_G_ENC_INDEX: {
7861 struct vki_v4l2_enc_idx *data = (struct vki_v4l2_enc_idx *)ARG3;
7862 PRE_MEM_READ("ioctl(VKI_V4L2_G_ENC_INDEX)", (Addr)data, sizeof(*data));
7863 break;
7865 case VKI_V4L2_ENCODER_CMD: {
7866 struct vki_v4l2_encoder_cmd *data = (struct vki_v4l2_encoder_cmd *)ARG3;
7867 PRE_MEM_READ("ioctl(VKI_V4L2_ENCODER_CMD)", (Addr)data, sizeof(*data));
7868 break;
7870 case VKI_V4L2_TRY_ENCODER_CMD: {
7871 struct vki_v4l2_encoder_cmd *data = (struct vki_v4l2_encoder_cmd *)ARG3;
7872 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_ENCODER_CMD)", (Addr)data, sizeof(*data));
7873 break;
7875 case VKI_V4L2_DBG_S_REGISTER: {
7876 struct vki_v4l2_dbg_register *data = (struct vki_v4l2_dbg_register *)ARG3;
7877 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_S_REGISTER).match.type", data->match.type);
7878 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_S_REGISTER).match.addr", data->match.addr);
7879 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_S_REGISTER).reg", data->reg);
7880 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_S_REGISTER).val", data->val);
7881 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DBG_S_REGISTER).size", data->size);
7882 break;
7884 case VKI_V4L2_DBG_G_REGISTER: {
7885 struct vki_v4l2_dbg_register *data = (struct vki_v4l2_dbg_register *)ARG3;
7886 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_REGISTER).match.type", data->match.type);
7887 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_REGISTER).match.addr", data->match.addr);
7888 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_REGISTER).reg", data->reg);
7889 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DBG_G_REGISTER).val", data->val);
7890 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DBG_G_REGISTER).size", data->size);
7891 break;
7893 case VKI_V4L2_S_HW_FREQ_SEEK: {
7894 struct vki_v4l2_hw_freq_seek *data = (struct vki_v4l2_hw_freq_seek *)ARG3;
7895 PRE_MEM_READ("ioctl(VKI_V4L2_S_HW_FREQ_SEEK)", (Addr)data, sizeof(*data));
7896 break;
7898 case VKI_V4L2_S_DV_TIMINGS: {
7899 struct vki_v4l2_dv_timings *data = (struct vki_v4l2_dv_timings *)ARG3;
7900 PRE_FIELD_READ("ioctl(VKI_V4L2_S_DV_TIMINGS).type", data->type);
7901 PRE_FIELD_READ("ioctl(VKI_V4L2_S_DV_TIMINGS).bt", data->bt);
7902 break;
7904 case VKI_V4L2_G_DV_TIMINGS: {
7905 struct vki_v4l2_dv_timings *data = (struct vki_v4l2_dv_timings *)ARG3;
7906 PRE_MEM_WRITE("ioctl(VKI_V4L2_G_DV_TIMINGS)", (Addr)data, sizeof(*data));
7907 break;
7909 case VKI_V4L2_DQEVENT: {
7910 struct vki_v4l2_event *data = (struct vki_v4l2_event *)ARG3;
7911 PRE_MEM_WRITE("ioctl(VKI_V4L2_DQEVENT)", (Addr)data, sizeof(*data));
7912 break;
7914 case VKI_V4L2_SUBSCRIBE_EVENT: {
7915 struct vki_v4l2_event_subscription *data = (struct vki_v4l2_event_subscription *)ARG3;
7916 PRE_MEM_READ("ioctl(VKI_V4L2_SUBSCRIBE_EVENT)", (Addr)data, sizeof(*data));
7917 break;
7919 case VKI_V4L2_UNSUBSCRIBE_EVENT: {
7920 struct vki_v4l2_event_subscription *data = (struct vki_v4l2_event_subscription *)ARG3;
7921 PRE_MEM_READ("ioctl(VKI_V4L2_UNSUBSCRIBE_EVENT)", (Addr)data, sizeof(*data));
7922 break;
7924 case VKI_V4L2_CREATE_BUFS: {
7925 struct vki_v4l2_create_buffers *data = (struct vki_v4l2_create_buffers *)ARG3;
7926 struct vki_v4l2_format *fmt = &data->format;
7927 PRE_FIELD_WRITE("ioctl(VKI_V4L2_CREATE_BUFS).index", data->index);
7928 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).count", data->count);
7929 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).memory", data->memory);
7930 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).reserved", data->reserved);
7931 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.type", fmt->type);
7932 switch (fmt->type) {
7933 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE:
7934 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT:
7935 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.pix", fmt->fmt.raw_data);
7936 break;
7937 case VKI_V4L2_BUF_TYPE_VBI_CAPTURE:
7938 case VKI_V4L2_BUF_TYPE_VBI_OUTPUT:
7939 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.vbi", fmt->fmt.vbi);
7940 break;
7941 case VKI_V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
7942 case VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
7943 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.sliced", fmt->fmt.sliced);
7944 break;
7945 case VKI_V4L2_BUF_TYPE_VIDEO_OVERLAY:
7946 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
7947 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.win", fmt->fmt.win);
7948 break;
7949 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
7950 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
7951 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.pix_mp", fmt->fmt.pix_mp);
7952 break;
7953 case VKI_V4L2_BUF_TYPE_SDR_CAPTURE:
7954 PRE_FIELD_READ("ioctl(VKI_V4L2_CREATE_BUFS).format.sdr", fmt->fmt.sdr);
7955 break;
7957 break;
7959 case VKI_V4L2_PREPARE_BUF: {
7960 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
7961 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).index", data->index);
7962 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).type", data->type);
7963 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).memory", data->memory);
7964 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).reserved", data->reserved);
7965 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).reserved2", data->reserved2);
7966 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
7967 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
7968 unsigned i;
7970 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).length", data->length);
7971 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).m.planes", data->m.planes);
7972 for (i = 0; i < data->length; i++) {
7973 PRE_FIELD_READ("ioctl(VKI_V4L2_PREPARE_BUF).m.planes[].reserved", data->m.planes[i].reserved);
7976 break;
7978 case VKI_V4L2_G_SELECTION: {
7979 struct vki_v4l2_selection *data = (struct vki_v4l2_selection *)ARG3;
7980 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SELECTION).type", data->type);
7981 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SELECTION).target", data->target);
7982 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SELECTION).flags", data->flags);
7983 PRE_FIELD_READ("ioctl(VKI_V4L2_G_SELECTION).reserved", data->reserved);
7984 PRE_FIELD_WRITE("ioctl(VKI_V4L2_G_SELECTION).r", data->r);
7985 break;
7987 case VKI_V4L2_S_SELECTION: {
7988 struct vki_v4l2_selection *data = (struct vki_v4l2_selection *)ARG3;
7989 PRE_MEM_READ("ioctl(VKI_V4L2_S_SELECTION)", (Addr)data, sizeof(*data));
7990 break;
7992 case VKI_V4L2_DECODER_CMD: {
7993 struct vki_v4l2_decoder_cmd *data = (struct vki_v4l2_decoder_cmd *)ARG3;
7994 PRE_MEM_READ("ioctl(VKI_V4L2_DECODER_CMD)", (Addr)data, sizeof(*data));
7995 break;
7997 case VKI_V4L2_TRY_DECODER_CMD: {
7998 struct vki_v4l2_decoder_cmd *data = (struct vki_v4l2_decoder_cmd *)ARG3;
7999 PRE_MEM_READ("ioctl(VKI_V4L2_TRY_DECODER_CMD)", (Addr)data, sizeof(*data));
8000 break;
8002 case VKI_V4L2_ENUM_DV_TIMINGS: {
8003 struct vki_v4l2_enum_dv_timings *data = (struct vki_v4l2_enum_dv_timings *)ARG3;
8004 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_DV_TIMINGS).index", data->index);
8005 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_DV_TIMINGS).pad", data->pad);
8006 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_DV_TIMINGS).reserved", data->reserved);
8007 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_DV_TIMINGS).timings", data->timings);
8008 break;
8010 case VKI_V4L2_QUERY_DV_TIMINGS: {
8011 struct vki_v4l2_dv_timings *data = (struct vki_v4l2_dv_timings *)ARG3;
8012 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERY_DV_TIMINGS)", (Addr)data, sizeof(*data));
8013 break;
8015 case VKI_V4L2_DV_TIMINGS_CAP: {
8016 struct vki_v4l2_dv_timings_cap *data = (struct vki_v4l2_dv_timings_cap *)ARG3;
8017 PRE_MEM_WRITE("ioctl(VKI_V4L2_DV_TIMINGS_CAP)", (Addr)data, sizeof(*data));
8018 break;
8020 case VKI_V4L2_ENUM_FREQ_BANDS: {
8021 struct vki_v4l2_frequency_band *data = (struct vki_v4l2_frequency_band *)ARG3;
8022 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).tuner", data->tuner);
8023 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).type", data->type);
8024 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).index", data->index);
8025 PRE_FIELD_READ("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).reserved", data->reserved);
8026 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).capability", data->capability);
8027 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).rangelow", data->rangelow);
8028 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).rangehigh", data->rangehigh);
8029 PRE_FIELD_WRITE("ioctl(VKI_V4L2_ENUM_FREQ_BANDS).modulation", data->modulation);
8030 break;
8032 case VKI_V4L2_DBG_G_CHIP_INFO: {
8033 struct vki_v4l2_dbg_chip_info *data = (struct vki_v4l2_dbg_chip_info *)ARG3;
8034 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_CHIP_INFO).match.type", data->match.type);
8035 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_CHIP_INFO).match.addr", data->match.addr);
8036 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DBG_G_CHIP_INFO).name", data->name);
8037 PRE_FIELD_WRITE("ioctl(VKI_V4L2_DBG_G_CHIP_INFO).flags", data->flags);
8038 PRE_FIELD_READ("ioctl(VKI_V4L2_DBG_G_CHIP_INFO).reserved", data->reserved);
8039 break;
8041 case VKI_V4L2_QUERY_EXT_CTRL: {
8042 struct vki_v4l2_query_ext_ctrl *data = (struct vki_v4l2_query_ext_ctrl *)ARG3;
8043 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERY_EXT_CTRL).id", data->id);
8044 PRE_FIELD_READ("ioctl(VKI_V4L2_QUERY_EXT_CTRL).reserved", data->reserved);
8045 PRE_MEM_WRITE("ioctl(VKI_V4L2_QUERY_EXT_CTRL)", (Addr)&data->type,
8046 sizeof(*data) - sizeof(data->id) - sizeof(data->reserved));
8047 break;
8049 case VKI_V4L2_SUBDEV_G_FMT: {
8050 struct vki_v4l2_subdev_format *data = (struct vki_v4l2_subdev_format *)ARG3;
8051 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_FMT).pad", data->pad);
8052 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_FMT).which", data->which);
8053 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_FMT).reserved", data->reserved);
8054 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_G_FMT).format", data->format);
8055 break;
8057 case VKI_V4L2_SUBDEV_S_FMT: {
8058 struct vki_v4l2_subdev_format *data = (struct vki_v4l2_subdev_format *)ARG3;
8059 PRE_MEM_READ("ioctl(VKI_V4L2_SUBDEV_S_FMT)", (Addr)data, sizeof(*data));
8060 break;
8062 case VKI_V4L2_SUBDEV_G_FRAME_INTERVAL: {
8063 struct vki_v4l2_subdev_frame_interval *data = (struct vki_v4l2_subdev_frame_interval *)ARG3;
8064 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_FRAME_SIZE).pad", data->pad);
8065 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_FRAME_SIZE).reserved", data->reserved);
8066 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_G_FRAME_SIZE).interval", data->interval);
8067 break;
8069 case VKI_V4L2_SUBDEV_S_FRAME_INTERVAL: {
8070 struct vki_v4l2_subdev_frame_interval *data = (struct vki_v4l2_subdev_frame_interval *)ARG3;
8071 PRE_MEM_READ("ioctl(VKI_V4L2_SUBDEV_S_FRAME_INTERVAL)", (Addr)data, sizeof(*data));
8072 break;
8074 case VKI_V4L2_SUBDEV_ENUM_MBUS_CODE: {
8075 struct vki_v4l2_subdev_mbus_code_enum *data = (struct vki_v4l2_subdev_mbus_code_enum *)ARG3;
8076 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_MBUS_CODE).index", data->index);
8077 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_MBUS_CODE).pad", data->pad);
8078 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_MBUS_CODE).code", data->code);
8079 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_MBUS_CODE).reserved", data->reserved);
8080 break;
8082 case VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE: {
8083 struct vki_v4l2_subdev_frame_size_enum *data = (struct vki_v4l2_subdev_frame_size_enum *)ARG3;
8084 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).index", data->index);
8085 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).pad", data->pad);
8086 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).code", data->code);
8087 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).reserved", data->reserved);
8088 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).min_width", data->min_width);
8089 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).min_height", data->min_height);
8090 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).max_width", data->max_width);
8091 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE).max_height", data->max_height);
8092 break;
8094 case VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL: {
8095 struct vki_v4l2_subdev_frame_interval_enum *data = (struct vki_v4l2_subdev_frame_interval_enum *)ARG3;
8096 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).index", data->index);
8097 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).pad", data->pad);
8098 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).code", data->code);
8099 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).width", data->width);
8100 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).height", data->height);
8101 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).reserved", data->reserved);
8102 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL).interval", data->interval);
8103 break;
8105 case VKI_V4L2_SUBDEV_G_CROP: {
8106 struct vki_v4l2_subdev_crop *data = (struct vki_v4l2_subdev_crop *)ARG3;
8107 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_CROP).pad", data->pad);
8108 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_CROP).which", data->which);
8109 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_CROP).reserved", data->reserved);
8110 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_G_CROP).rect", data->rect);
8111 break;
8113 case VKI_V4L2_SUBDEV_S_CROP: {
8114 struct vki_v4l2_subdev_crop *data = (struct vki_v4l2_subdev_crop *)ARG3;
8115 PRE_MEM_READ("ioctl(VKI_V4L2_SUBDEV_S_CROP)", (Addr)data, sizeof(*data));
8116 break;
8118 case VKI_V4L2_SUBDEV_G_SELECTION: {
8119 struct vki_v4l2_subdev_selection *data = (struct vki_v4l2_subdev_selection *)ARG3;
8120 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).pad", data->pad);
8121 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).which", data->which);
8122 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).target", data->target);
8123 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).flags", data->flags);
8124 PRE_FIELD_READ("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).reserved", data->reserved);
8125 PRE_FIELD_WRITE("ioctl(VKI_V4L2_SUBDEV_G_SELECTION).r", data->r);
8126 break;
8128 case VKI_V4L2_SUBDEV_S_SELECTION: {
8129 struct vki_v4l2_subdev_selection *data = (struct vki_v4l2_subdev_selection *)ARG3;
8130 PRE_MEM_READ("ioctl(VKI_V4L2_SUBDEV_S_SELECTION)", (Addr)data, sizeof(*data));
8131 break;
8133 case VKI_MEDIA_IOC_DEVICE_INFO: {
8134 struct vki_media_device_info *data = (struct vki_media_device_info *)ARG3;
8135 PRE_FIELD_READ("ioctl(VKI_MEDIA_IOC_DEVICE_INFO).reserved", data->reserved);
8136 PRE_MEM_WRITE("ioctl(VKI_MEDIA_IOC_DEVICE_INFO)",
8137 (Addr)data, sizeof(*data) - sizeof(data->reserved));
8138 break;
8140 case VKI_MEDIA_IOC_ENUM_ENTITIES: {
8141 struct vki_media_entity_desc *data = (struct vki_media_entity_desc *)ARG3;
8142 PRE_FIELD_READ("ioctl(VKI_MEDIA_IOC_ENUM_ENTITIES).id", data->id);
8143 PRE_MEM_WRITE("ioctl(VKI_MEDIA_IOC_ENUM_ENTITIES)",
8144 (Addr)data->name, sizeof(*data) - sizeof(data->id));
8145 break;
8147 case VKI_MEDIA_IOC_ENUM_LINKS: {
8148 struct vki_media_links_enum *data = (struct vki_media_links_enum *)ARG3;
8149 PRE_MEM_READ("ioctl(VKI_MEDIA_IOC_ENUM_LINKS)", (Addr)data, sizeof(*data));
8150 break;
8152 case VKI_MEDIA_IOC_SETUP_LINK: {
8153 struct vki_media_link_desc *data = (struct vki_media_link_desc *)ARG3;
8154 PRE_MEM_READ("ioctl(VKI_MEDIA_IOC_SETUP_LINK)", (Addr)data, sizeof(*data));
8155 break;
8158 default:
8159 /* EVIOC* are variable length and return size written on success */
8160 switch (ARG2 & ~(_VKI_IOC_SIZEMASK << _VKI_IOC_SIZESHIFT)) {
8161 case VKI_EVIOCGNAME(0):
8162 case VKI_EVIOCGPHYS(0):
8163 case VKI_EVIOCGUNIQ(0):
8164 case VKI_EVIOCGKEY(0):
8165 case VKI_EVIOCGLED(0):
8166 case VKI_EVIOCGSND(0):
8167 case VKI_EVIOCGSW(0):
8168 case VKI_EVIOCGBIT(VKI_EV_SYN,0):
8169 case VKI_EVIOCGBIT(VKI_EV_KEY,0):
8170 case VKI_EVIOCGBIT(VKI_EV_REL,0):
8171 case VKI_EVIOCGBIT(VKI_EV_ABS,0):
8172 case VKI_EVIOCGBIT(VKI_EV_MSC,0):
8173 case VKI_EVIOCGBIT(VKI_EV_SW,0):
8174 case VKI_EVIOCGBIT(VKI_EV_LED,0):
8175 case VKI_EVIOCGBIT(VKI_EV_SND,0):
8176 case VKI_EVIOCGBIT(VKI_EV_REP,0):
8177 case VKI_EVIOCGBIT(VKI_EV_FF,0):
8178 case VKI_EVIOCGBIT(VKI_EV_PWR,0):
8179 case VKI_EVIOCGBIT(VKI_EV_FF_STATUS,0):
8180 PRE_MEM_WRITE("ioctl(EVIO*)", ARG3, _VKI_IOC_SIZE(ARG2));
8181 break;
8182 default:
8183 ML_(PRE_unknown_ioctl)(tid, ARG2, ARG3);
8184 break;
8186 break;
8190 POST(sys_ioctl)
8192 vg_assert(SUCCESS);
8194 ARG2 = (UInt)ARG2;
8196 /* --- BEGIN special IOCTL handlers for specific Android hardware --- */
8198 /* BEGIN undocumented ioctls for PowerVR SGX 540 (the GPU on Nexus S) */
8199 if (KernelVariantiS(KernelVariant_android_gpu_sgx5xx,
8200 VG_(clo_kernel_variant))) {
8202 if (ARG2 >= 0xC01C6700 && ARG2 <= 0xC01C67FF && ARG3 >= 0x1000) {
8203 /* What's going on here: there appear to be a bunch of ioctls
8204 of the form 0xC01C67xx which are undocumented, and if
8205 unhandled give rise to a vast number of false positives in
8206 Memcheck.
8208 The "normal" interpretation of an ioctl of this form would
8209 be that the 3rd arg is a pointer to an area of size 0x1C
8210 (28 bytes) which is filled in by the kernel. Hence you
8211 might think that "POST_MEM_WRITE(ARG3, 28)" would fix it.
8212 But it doesn't.
8214 It requires POST_MEM_WRITE(ARG3, 256) to silence them.
8215 One interpretation of this is that ARG3 really does point
8216 to a 28 byte struct, but inside that are pointers to other
8217 areas also filled in by the kernel. If these happen to be
8218 allocated just back up the stack then the 256 byte paint
8219 might cover them too, somewhat indiscriminately.
8221 By printing out ARG3 and also the 28 bytes that it points
8222 at, it's possible to guess that the 7 word structure has
8223 this form
8225 0 1 2 3 4 5 6
8226 ioctl-number 0x1C ptr1 ptr1size ptr2 ptr2size aBitMask
8228 Unfortunately that doesn't seem to work for some reason,
8229 so stay with the blunt-instrument approach for the time
8230 being.
8232 if (1) {
8233 /* blunt-instrument approach */
8234 POST_MEM_WRITE(ARG3, 256);
8235 } else {
8236 /* be a bit more sophisticated */
8237 POST_MEM_WRITE(ARG3, 28);
8238 UInt* word = (UInt*)ARG3;
8239 if (word && word[2] && word[3] < 0x200/*stay sane*/)
8240 POST_MEM_WRITE(word[2], word[3]); // "ptr1"
8241 if (word && word[4] && word[5] < 0x200/*stay sane*/)
8242 POST_MEM_WRITE(word[4], word[5]); // "ptr2"
8244 goto post_sys_ioctl__out;
8247 /* END undocumented ioctls for PowerVR SGX 540 (the GPU on Nexus S) */
8249 /* BEGIN undocumented ioctls for Qualcomm Adreno 3xx */
8250 if (KernelVariantiS(KernelVariant_android_gpu_sgx5xx,
8251 VG_(clo_kernel_variant))) {
8252 if (ARG2 == 0xC00C0902) {
8253 POST_MEM_WRITE(ARG3, 24); // 16 is not enough
8254 goto post_sys_ioctl__out;
8257 /* END undocumented ioctls for Qualcomm Adreno 3xx */
8259 /* --- END special IOCTL handlers for specific Android hardware --- */
8261 /* --- normal handling --- */
8262 switch (ARG2 /* request */) {
8264 /* The Linux kernel "ion" memory allocator, used on Android. Note:
8265 this is pretty poor given that there's no pre-handling to check
8266 that writable areas are addressable. */
8267 case VKI_ION_IOC_ALLOC:
8268 POST_MEM_WRITE(ARG3, sizeof(struct vki_ion_allocation_data));
8269 break;
8270 case VKI_ION_IOC_MAP:
8271 POST_MEM_WRITE(ARG3, sizeof(struct vki_ion_fd_data));
8272 break;
8273 case VKI_ION_IOC_FREE: // is this necessary?
8274 POST_MEM_WRITE(ARG3, sizeof(struct vki_ion_handle_data));
8275 break;
8276 case VKI_ION_IOC_SHARE:
8277 break;
8278 case VKI_ION_IOC_IMPORT: // is this necessary?
8279 POST_MEM_WRITE(ARG3, sizeof(struct vki_ion_fd_data));
8280 break;
8281 case VKI_ION_IOC_SYNC:
8282 break;
8283 case VKI_ION_IOC_CUSTOM: // is this necessary?
8284 POST_MEM_WRITE(ARG3, sizeof(struct vki_ion_custom_data));
8285 break;
8287 case VKI_TCSETS:
8288 case VKI_TCSETSW:
8289 case VKI_TCSETSF:
8290 case VKI_IB_USER_MAD_ENABLE_PKEY:
8291 break;
8292 case VKI_TCGETS:
8293 POST_MEM_WRITE( ARG3, sizeof(struct vki_termios) );
8294 break;
8295 case VKI_TCSETA:
8296 case VKI_TCSETAW:
8297 case VKI_TCSETAF:
8298 break;
8299 case VKI_TCGETA:
8300 POST_MEM_WRITE( ARG3, sizeof(struct vki_termio) );
8301 break;
8302 case VKI_TCSBRK:
8303 case VKI_TCXONC:
8304 case VKI_TCSBRKP:
8305 case VKI_TCFLSH:
8306 case VKI_TIOCSIG:
8307 break;
8308 case VKI_TIOCGWINSZ:
8309 POST_MEM_WRITE( ARG3, sizeof(struct vki_winsize) );
8310 break;
8311 case VKI_TIOCSWINSZ:
8312 case VKI_TIOCMBIS:
8313 case VKI_TIOCMBIC:
8314 case VKI_TIOCMSET:
8315 break;
8316 case VKI_TIOCMGET:
8317 POST_MEM_WRITE( ARG3, sizeof(unsigned int) );
8318 break;
8319 case VKI_TIOCLINUX:
8320 POST_MEM_WRITE( ARG3, sizeof(char *) );
8321 break;
8322 case VKI_TIOCGPGRP:
8323 /* Get process group ID for foreground processing group. */
8324 POST_MEM_WRITE( ARG3, sizeof(vki_pid_t) );
8325 break;
8326 case VKI_TIOCSPGRP:
8327 /* Set a process group ID? */
8328 POST_MEM_WRITE( ARG3, sizeof(vki_pid_t) );
8329 break;
8330 case VKI_TIOCGPTN: /* Get Pty Number (of pty-mux device) */
8331 POST_MEM_WRITE( ARG3, sizeof(int));
8332 break;
8333 case VKI_TIOCSCTTY:
8334 break;
8335 case VKI_TIOCSPTLCK: /* Lock/unlock Pty */
8336 break;
8337 case VKI_FIONBIO:
8338 break;
8339 case VKI_FIONCLEX:
8340 break;
8341 case VKI_FIOCLEX:
8342 break;
8343 case VKI_TIOCNOTTY:
8344 break;
8345 case VKI_FIOASYNC:
8346 break;
8347 case VKI_FIONREAD: /* identical to SIOCINQ */
8348 POST_MEM_WRITE( ARG3, sizeof(int) );
8349 break;
8350 case VKI_FIOQSIZE:
8351 POST_MEM_WRITE( ARG3, sizeof(vki_loff_t) );
8352 break;
8354 case VKI_TIOCSERGETLSR:
8355 POST_MEM_WRITE( ARG3, sizeof(int) );
8356 break;
8357 case VKI_TIOCGICOUNT:
8358 POST_MEM_WRITE( ARG3, sizeof(struct vki_serial_icounter_struct) );
8359 break;
8361 case VKI_SG_SET_COMMAND_Q:
8362 break;
8363 case VKI_SG_IO:
8365 vki_sg_io_hdr_t *sgio = (vki_sg_io_hdr_t*)ARG3;
8366 if ( sgio->sbp ) {
8367 POST_MEM_WRITE( (Addr)sgio->sbp, sgio->sb_len_wr );
8369 if ( sgio->dxfer_direction == VKI_SG_DXFER_FROM_DEV ||
8370 sgio->dxfer_direction == VKI_SG_DXFER_TO_FROM_DEV ) {
8371 int transferred = sgio->dxfer_len - sgio->resid;
8372 POST_MEM_WRITE( (Addr)sgio->dxferp, transferred );
8375 break;
8376 case VKI_SG_GET_SCSI_ID:
8377 POST_MEM_WRITE(ARG3, sizeof(vki_sg_scsi_id_t));
8378 break;
8379 case VKI_SG_SET_RESERVED_SIZE:
8380 break;
8381 case VKI_SG_SET_TIMEOUT:
8382 break;
8383 case VKI_SG_GET_RESERVED_SIZE:
8384 POST_MEM_WRITE(ARG3, sizeof(int));
8385 break;
8386 case VKI_SG_GET_TIMEOUT:
8387 break;
8388 case VKI_SG_GET_VERSION_NUM:
8389 POST_MEM_WRITE(ARG3, sizeof(int));
8390 break;
8391 case VKI_SG_EMULATED_HOST:
8392 POST_MEM_WRITE(ARG3, sizeof(int));
8393 break;
8394 case VKI_SG_GET_SG_TABLESIZE:
8395 POST_MEM_WRITE(ARG3, sizeof(int));
8396 break;
8398 case VKI_IIOCGETCPS:
8399 POST_MEM_WRITE( ARG3, VKI_ISDN_MAX_CHANNELS * 2 * sizeof(unsigned long) );
8400 break;
8401 case VKI_IIOCNETGPN:
8402 POST_MEM_WRITE( ARG3, sizeof(vki_isdn_net_ioctl_phone) );
8403 break;
8405 /* These all use struct ifreq AFAIK */
8406 case VKI_SIOCGIFINDEX: /* get iface index */
8407 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_ifindex,
8408 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_ifindex) );
8409 break;
8410 case VKI_SIOCGIFFLAGS: /* get flags */
8411 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
8412 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
8413 break;
8414 case VKI_SIOCGIFHWADDR: /* Get hardware address */
8415 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->ifr_hwaddr,
8416 sizeof(((struct vki_ifreq *)ARG3)->ifr_hwaddr) );
8417 break;
8418 case VKI_SIOCGIFMTU: /* get MTU size */
8419 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_mtu,
8420 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_mtu) );
8421 break;
8422 case VKI_SIOCGIFADDR: /* get PA address */
8423 case VKI_SIOCGIFDSTADDR: /* get remote PA address */
8424 case VKI_SIOCGIFBRDADDR: /* get broadcast PA address */
8425 case VKI_SIOCGIFNETMASK: /* get network PA mask */
8426 POST_MEM_WRITE(
8427 (Addr)&((struct vki_ifreq *)ARG3)->ifr_addr,
8428 sizeof(((struct vki_ifreq *)ARG3)->ifr_addr) );
8429 break;
8430 case VKI_SIOCGIFMETRIC: /* get metric */
8431 POST_MEM_WRITE(
8432 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_metric,
8433 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_metric) );
8434 break;
8435 case VKI_SIOCGIFMAP: /* Get device parameters */
8436 POST_MEM_WRITE(
8437 (Addr)&((struct vki_ifreq *)ARG3)->ifr_map,
8438 sizeof(((struct vki_ifreq *)ARG3)->ifr_map) );
8439 break;
8440 break;
8441 case VKI_SIOCGIFTXQLEN: /* Get the tx queue length */
8442 POST_MEM_WRITE(
8443 (Addr)&((struct vki_ifreq *)ARG3)->ifr_qlen,
8444 sizeof(((struct vki_ifreq *)ARG3)->ifr_qlen) );
8445 break;
8446 case VKI_SIOCGIFNAME: /* get iface name */
8447 POST_MEM_WRITE(
8448 (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_name,
8449 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_name) );
8450 break;
8451 case VKI_SIOCETHTOOL: { /* ethtool(8) interface */
8452 struct vki_ifreq *ir = (struct vki_ifreq *)ARG3;
8453 switch ( *(vki_u32 *)ir->vki_ifr_data ) {
8454 case VKI_ETHTOOL_GSET:
8455 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_cmd));
8456 break;
8457 case VKI_ETHTOOL_SSET:
8458 break;
8459 case VKI_ETHTOOL_GDRVINFO:
8460 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_drvinfo) );
8461 break;
8462 case VKI_ETHTOOL_GREGS:
8463 POST_MEM_WRITE( (Addr)((struct vki_ethtool_regs *)ir->vki_ifr_data)->data,
8464 ((struct vki_ethtool_regs *)ir->vki_ifr_data)->len );
8465 break;
8466 case VKI_ETHTOOL_GWOL:
8467 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_wolinfo) );
8468 break;
8469 case VKI_ETHTOOL_SWOL:
8470 break;
8471 case VKI_ETHTOOL_GMSGLVL:
8472 case VKI_ETHTOOL_GLINK:
8473 case VKI_ETHTOOL_GRXCSUM:
8474 case VKI_ETHTOOL_GSG:
8475 case VKI_ETHTOOL_GTSO:
8476 case VKI_ETHTOOL_GUFO:
8477 case VKI_ETHTOOL_GGSO:
8478 case VKI_ETHTOOL_GFLAGS:
8479 case VKI_ETHTOOL_GGRO:
8480 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_value));
8481 break;
8482 case VKI_ETHTOOL_SMSGLVL:
8483 case VKI_ETHTOOL_SRXCSUM:
8484 case VKI_ETHTOOL_SSG:
8485 case VKI_ETHTOOL_STSO:
8486 case VKI_ETHTOOL_SUFO:
8487 case VKI_ETHTOOL_SGSO:
8488 case VKI_ETHTOOL_SFLAGS:
8489 case VKI_ETHTOOL_SGRO:
8490 break;
8491 case VKI_ETHTOOL_NWAY_RST:
8492 break;
8493 case VKI_ETHTOOL_GRINGPARAM:
8494 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_ringparam));
8495 break;
8496 case VKI_ETHTOOL_SRINGPARAM:
8497 break;
8498 case VKI_ETHTOOL_TEST:
8499 POST_MEM_WRITE( (Addr)((struct vki_ethtool_test *)ir->vki_ifr_data)->data,
8500 ((struct vki_ethtool_test *)ir->vki_ifr_data)->len * sizeof(__vki_u64) );
8501 break;
8502 case VKI_ETHTOOL_PHYS_ID:
8503 break;
8504 case VKI_ETHTOOL_GPERMADDR:
8505 POST_MEM_WRITE( (Addr)((struct vki_ethtool_perm_addr *)ir->vki_ifr_data)->data,
8506 ((struct vki_ethtool_perm_addr *)ir->vki_ifr_data)->size );
8507 break;
8508 case VKI_ETHTOOL_RESET:
8509 break;
8510 case VKI_ETHTOOL_GSSET_INFO:
8511 POST_MEM_WRITE( (Addr)((struct vki_ethtool_sset_info *)ir->vki_ifr_data)->data,
8512 __builtin_popcountll(((struct vki_ethtool_sset_info *)ir->vki_ifr_data)->sset_mask) * sizeof(__vki_u32) );
8513 break;
8514 case VKI_ETHTOOL_GFEATURES:
8515 POST_MEM_WRITE( (Addr)((struct vki_ethtool_gfeatures *)ir->vki_ifr_data)->features,
8516 ((struct vki_ethtool_gfeatures *)ir->vki_ifr_data)->size * sizeof(struct vki_ethtool_get_features_block) );
8517 break;
8518 case VKI_ETHTOOL_SFEATURES:
8519 break;
8520 case VKI_ETHTOOL_GCHANNELS:
8521 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_channels) );
8522 break;
8523 case VKI_ETHTOOL_SCHANNELS:
8524 break;
8525 case VKI_ETHTOOL_GET_TS_INFO:
8526 POST_MEM_WRITE( (Addr)ir->vki_ifr_data, sizeof(struct vki_ethtool_ts_info) );
8527 break;
8529 break;
8531 case VKI_SIOCGMIIPHY: /* get hardware entry */
8532 POST_MEM_WRITE(
8533 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id,
8534 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->phy_id) );
8535 break;
8536 case VKI_SIOCGMIIREG: /* get hardware entry registers */
8537 POST_MEM_WRITE(
8538 (Addr)&((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_out,
8539 sizeof(((struct vki_mii_ioctl_data *)&((struct vki_ifreq *)ARG3)->vki_ifr_data)->val_out) );
8540 break;
8542 /* tun/tap related ioctls */
8543 case VKI_TUNSETIFF:
8544 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_name,
8545 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_name) );
8546 break;
8547 case VKI_TUNGETFEATURES:
8548 POST_MEM_WRITE( ARG3, sizeof(unsigned int) );
8549 break;
8550 case VKI_TUNGETIFF:
8551 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_name,
8552 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_name) );
8553 POST_MEM_WRITE( (Addr)&((struct vki_ifreq *)ARG3)->vki_ifr_flags,
8554 sizeof(((struct vki_ifreq *)ARG3)->vki_ifr_flags) );
8555 break;
8556 case VKI_TUNGETSNDBUF:
8557 POST_MEM_WRITE( ARG3, sizeof(int) );
8558 break;
8559 case VKI_TUNGETVNETHDRSZ:
8560 POST_MEM_WRITE( ARG3, sizeof(int) );
8561 break;
8563 case VKI_SIOCGIFCONF: /* get iface list */
8564 /* WAS:
8565 PRE_MEM_WRITE("ioctl(SIOCGIFCONF)", ARG3, sizeof(struct ifconf));
8566 KERNEL_DO_SYSCALL(tid,RES);
8567 if (!VG_(is_kerror)(RES) && RES == 0)
8568 POST_MEM_WRITE(ARG3, sizeof(struct ifconf));
8570 if (RES == 0 && ARG3 ) {
8571 struct vki_ifconf *ifc = (struct vki_ifconf *) ARG3;
8572 if (ifc->vki_ifc_buf != NULL)
8573 POST_MEM_WRITE( (Addr)(ifc->vki_ifc_buf), ifc->ifc_len );
8575 break;
8576 case VKI_SIOCGSTAMP:
8577 POST_MEM_WRITE( ARG3, sizeof(struct vki_timeval) );
8578 break;
8579 case VKI_SIOCGSTAMPNS:
8580 POST_MEM_WRITE( ARG3, sizeof(struct vki_timespec) );
8581 break;
8582 /* SIOCOUTQ is an ioctl that, when called on a socket, returns
8583 the number of bytes currently in that socket's send buffer.
8584 It writes this value as an int to the memory location
8585 indicated by the third argument of ioctl(2). */
8586 case VKI_SIOCOUTQ:
8587 POST_MEM_WRITE(ARG3, sizeof(int));
8588 break;
8589 case VKI_SIOCGRARP: /* get RARP table entry */
8590 case VKI_SIOCGARP: /* get ARP table entry */
8591 POST_MEM_WRITE(ARG3, sizeof(struct vki_arpreq));
8592 break;
8594 case VKI_SIOCSIFFLAGS: /* set flags */
8595 case VKI_SIOCSIFMAP: /* Set device parameters */
8596 case VKI_SIOCSHWTSTAMP: /* Set hardware time stamping */
8597 case VKI_SIOCSIFTXQLEN: /* Set the tx queue length */
8598 case VKI_SIOCSIFDSTADDR: /* set remote PA address */
8599 case VKI_SIOCSIFBRDADDR: /* set broadcast PA address */
8600 case VKI_SIOCSIFNETMASK: /* set network PA mask */
8601 case VKI_SIOCSIFMETRIC: /* set metric */
8602 case VKI_SIOCSIFADDR: /* set PA address */
8603 case VKI_SIOCSIFMTU: /* set MTU size */
8604 case VKI_SIOCSIFHWADDR: /* set hardware address */
8605 case VKI_SIOCSMIIREG: /* set hardware entry registers */
8606 break;
8607 /* Routing table calls. */
8608 case VKI_SIOCADDRT: /* add routing table entry */
8609 case VKI_SIOCDELRT: /* delete routing table entry */
8610 break;
8612 /* RARP cache control calls. */
8613 case VKI_SIOCDRARP: /* delete RARP table entry */
8614 case VKI_SIOCSRARP: /* set RARP table entry */
8615 /* ARP cache control calls. */
8616 case VKI_SIOCSARP: /* set ARP table entry */
8617 case VKI_SIOCDARP: /* delete ARP table entry */
8618 break;
8620 case VKI_SIOCGPGRP:
8621 POST_MEM_WRITE(ARG3, sizeof(int));
8622 break;
8623 case VKI_SIOCSPGRP:
8624 break;
8626 case VKI_SIOCATMARK:
8627 POST_MEM_WRITE(ARG3, sizeof(int));
8628 break;
8630 /* linux/soundcard interface (OSS) */
8631 case VKI_SNDCTL_SEQ_GETOUTCOUNT:
8632 case VKI_SNDCTL_SEQ_GETINCOUNT:
8633 case VKI_SNDCTL_SEQ_PERCMODE:
8634 case VKI_SNDCTL_SEQ_TESTMIDI:
8635 case VKI_SNDCTL_SEQ_RESETSAMPLES:
8636 case VKI_SNDCTL_SEQ_NRSYNTHS:
8637 case VKI_SNDCTL_SEQ_NRMIDIS:
8638 case VKI_SNDCTL_SEQ_GETTIME:
8639 case VKI_SNDCTL_DSP_GETBLKSIZE:
8640 case VKI_SNDCTL_DSP_GETFMTS:
8641 case VKI_SNDCTL_DSP_SETFMT:
8642 case VKI_SNDCTL_DSP_GETTRIGGER:
8643 case VKI_SNDCTL_DSP_GETODELAY:
8644 case VKI_SNDCTL_DSP_GETSPDIF:
8645 case VKI_SNDCTL_DSP_GETCAPS:
8646 case VKI_SOUND_PCM_READ_RATE:
8647 case VKI_SOUND_PCM_READ_CHANNELS:
8648 case VKI_SOUND_PCM_READ_BITS:
8649 case VKI_SOUND_PCM_READ_FILTER:
8650 POST_MEM_WRITE(ARG3, sizeof(int));
8651 break;
8652 case VKI_SNDCTL_SEQ_CTRLRATE:
8653 case VKI_SNDCTL_DSP_SPEED:
8654 case VKI_SNDCTL_DSP_STEREO:
8655 case VKI_SNDCTL_DSP_CHANNELS:
8656 case VKI_SOUND_PCM_WRITE_FILTER:
8657 case VKI_SNDCTL_DSP_SUBDIVIDE:
8658 case VKI_SNDCTL_DSP_SETFRAGMENT:
8659 case VKI_SNDCTL_DSP_GETCHANNELMASK:
8660 case VKI_SNDCTL_DSP_BIND_CHANNEL:
8661 case VKI_SNDCTL_TMR_TIMEBASE:
8662 case VKI_SNDCTL_TMR_TEMPO:
8663 case VKI_SNDCTL_TMR_SOURCE:
8664 case VKI_SNDCTL_MIDI_PRETIME:
8665 case VKI_SNDCTL_MIDI_MPUMODE:
8666 break;
8667 case VKI_SNDCTL_DSP_GETOSPACE:
8668 case VKI_SNDCTL_DSP_GETISPACE:
8669 POST_MEM_WRITE(ARG3, sizeof(vki_audio_buf_info));
8670 break;
8671 case VKI_SNDCTL_DSP_NONBLOCK:
8672 break;
8673 case VKI_SNDCTL_DSP_SETTRIGGER:
8674 break;
8676 case VKI_SNDCTL_DSP_POST:
8677 case VKI_SNDCTL_DSP_RESET:
8678 case VKI_SNDCTL_DSP_SYNC:
8679 case VKI_SNDCTL_DSP_SETSYNCRO:
8680 case VKI_SNDCTL_DSP_SETDUPLEX:
8681 break;
8683 /* linux/soundcard interface (ALSA) */
8684 case VKI_SNDRV_PCM_IOCTL_HW_FREE:
8685 case VKI_SNDRV_PCM_IOCTL_HWSYNC:
8686 case VKI_SNDRV_PCM_IOCTL_PREPARE:
8687 case VKI_SNDRV_PCM_IOCTL_RESET:
8688 case VKI_SNDRV_PCM_IOCTL_START:
8689 case VKI_SNDRV_PCM_IOCTL_DROP:
8690 case VKI_SNDRV_PCM_IOCTL_DRAIN:
8691 case VKI_SNDRV_PCM_IOCTL_RESUME:
8692 case VKI_SNDRV_PCM_IOCTL_XRUN:
8693 case VKI_SNDRV_PCM_IOCTL_UNLINK:
8694 case VKI_SNDRV_TIMER_IOCTL_START:
8695 case VKI_SNDRV_TIMER_IOCTL_STOP:
8696 case VKI_SNDRV_TIMER_IOCTL_CONTINUE:
8697 case VKI_SNDRV_TIMER_IOCTL_PAUSE:
8698 case VKI_SNDRV_CTL_IOCTL_PVERSION: {
8699 POST_MEM_WRITE( (Addr)ARG3, sizeof(int) );
8700 break;
8702 case VKI_SNDRV_CTL_IOCTL_CARD_INFO:
8703 POST_MEM_WRITE( (Addr)ARG3, sizeof(struct vki_snd_ctl_card_info) );
8704 break;
8705 case VKI_SNDRV_CTL_IOCTL_ELEM_LIST: {
8706 struct vki_snd_ctl_elem_list *data = (struct vki_snd_ctl_elem_list *)ARG3;
8707 POST_MEM_WRITE( (Addr)&data->used, sizeof(data->used) );
8708 POST_MEM_WRITE( (Addr)&data->count, sizeof(data->count) );
8709 if (data->pids) {
8710 POST_MEM_WRITE( (Addr)data->pids, sizeof(struct vki_snd_ctl_elem_id) * data->used );
8712 break;
8714 case VKI_SNDRV_CTL_IOCTL_TLV_READ: {
8715 struct vki_snd_ctl_tlv *data = (struct vki_snd_ctl_tlv *)ARG3;
8716 POST_MEM_WRITE( (Addr)data->tlv, data->length );
8717 break;
8719 case VKI_SNDRV_CTL_IOCTL_TLV_WRITE:
8720 case VKI_SNDRV_CTL_IOCTL_TLV_COMMAND:
8721 break;
8723 /* SCSI no operand */
8724 case VKI_SCSI_IOCTL_DOORLOCK:
8725 case VKI_SCSI_IOCTL_DOORUNLOCK:
8726 break;
8728 /* Real Time Clock (/dev/rtc) ioctls */
8729 case VKI_RTC_UIE_ON:
8730 case VKI_RTC_UIE_OFF:
8731 case VKI_RTC_AIE_ON:
8732 case VKI_RTC_AIE_OFF:
8733 case VKI_RTC_PIE_ON:
8734 case VKI_RTC_PIE_OFF:
8735 case VKI_RTC_IRQP_SET:
8736 break;
8737 case VKI_RTC_RD_TIME:
8738 case VKI_RTC_ALM_READ:
8739 POST_MEM_WRITE(ARG3, sizeof(struct vki_rtc_time));
8740 break;
8741 case VKI_RTC_ALM_SET:
8742 break;
8743 case VKI_RTC_IRQP_READ:
8744 POST_MEM_WRITE(ARG3, sizeof(unsigned long));
8745 break;
8747 /* Block devices */
8748 case VKI_BLKROSET:
8749 break;
8750 case VKI_BLKROGET:
8751 POST_MEM_WRITE(ARG3, sizeof(int));
8752 break;
8753 case VKI_BLKGETSIZE:
8754 POST_MEM_WRITE(ARG3, sizeof(unsigned long));
8755 break;
8756 case VKI_BLKRASET:
8757 break;
8758 case VKI_BLKRAGET:
8759 POST_MEM_WRITE(ARG3, sizeof(long));
8760 break;
8761 case VKI_BLKFRASET:
8762 break;
8763 case VKI_BLKFRAGET:
8764 POST_MEM_WRITE(ARG3, sizeof(long));
8765 break;
8766 case VKI_BLKSECTGET:
8767 POST_MEM_WRITE(ARG3, sizeof(unsigned short));
8768 break;
8769 case VKI_BLKSSZGET:
8770 POST_MEM_WRITE(ARG3, sizeof(int));
8771 break;
8772 case VKI_BLKBSZGET:
8773 POST_MEM_WRITE(ARG3, sizeof(int));
8774 break;
8775 case VKI_BLKBSZSET:
8776 break;
8777 case VKI_BLKGETSIZE64:
8778 POST_MEM_WRITE(ARG3, sizeof(unsigned long long));
8779 break;
8780 case VKI_BLKPBSZGET:
8781 POST_MEM_WRITE(ARG3, sizeof(int));
8782 break;
8783 case VKI_BLKDISCARDZEROES:
8784 POST_MEM_WRITE(ARG3, sizeof(vki_uint));
8785 break;
8787 /* Hard disks */
8788 case VKI_HDIO_GETGEO: /* 0x0301 */
8789 POST_MEM_WRITE(ARG3, sizeof(struct vki_hd_geometry));
8790 break;
8791 case VKI_HDIO_GET_DMA: /* 0x030b */
8792 POST_MEM_WRITE(ARG3, sizeof(long));
8793 break;
8794 case VKI_HDIO_GET_IDENTITY: /* 0x030d */
8795 POST_MEM_WRITE(ARG3, VKI_SIZEOF_STRUCT_HD_DRIVEID );
8796 break;
8798 /* SCSI */
8799 case VKI_SCSI_IOCTL_GET_IDLUN: /* 0x5382 */
8800 POST_MEM_WRITE(ARG3, sizeof(struct vki_scsi_idlun));
8801 break;
8802 case VKI_SCSI_IOCTL_GET_BUS_NUMBER: /* 0x5386 */
8803 POST_MEM_WRITE(ARG3, sizeof(int));
8804 break;
8806 /* CD ROM stuff (??) */
8807 case VKI_CDROM_DISC_STATUS:
8808 break;
8809 case VKI_CDROMSUBCHNL:
8810 POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_subchnl));
8811 break;
8812 case VKI_CDROMREADTOCHDR:
8813 POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_tochdr));
8814 break;
8815 case VKI_CDROMREADTOCENTRY:
8816 POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_tocentry));
8817 break;
8818 case VKI_CDROMMULTISESSION:
8819 POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_multisession));
8820 break;
8821 case VKI_CDROMVOLREAD:
8822 POST_MEM_WRITE(ARG3, sizeof(struct vki_cdrom_volctrl));
8823 break;
8824 case VKI_CDROMREADRAW:
8825 POST_MEM_WRITE(ARG3, VKI_CD_FRAMESIZE_RAW);
8826 break;
8827 case VKI_CDROMREADAUDIO:
8829 struct vki_cdrom_read_audio *cra = (struct vki_cdrom_read_audio *) ARG3;
8830 POST_MEM_WRITE( (Addr)(cra->buf), cra->nframes * VKI_CD_FRAMESIZE_RAW);
8831 break;
8834 case VKI_CDROMPLAYMSF:
8835 break;
8836 /* The following two are probably bogus (should check args
8837 for readability). JRS 20021117 */
8838 case VKI_CDROM_DRIVE_STATUS: /* 0x5326 */
8839 case VKI_CDROM_CLEAR_OPTIONS: /* 0x5321 */
8840 break;
8841 case VKI_CDROM_GET_CAPABILITY: /* 0x5331 */
8842 break;
8844 case VKI_FIGETBSZ:
8845 POST_MEM_WRITE(ARG3, sizeof(unsigned long));
8846 break;
8847 case VKI_FIBMAP:
8848 POST_MEM_WRITE(ARG3, sizeof(int));
8849 break;
8851 case VKI_FBIOGET_VSCREENINFO: //0x4600
8852 POST_MEM_WRITE(ARG3, sizeof(struct vki_fb_var_screeninfo));
8853 break;
8854 case VKI_FBIOGET_FSCREENINFO: //0x4602
8855 POST_MEM_WRITE(ARG3, sizeof(struct vki_fb_fix_screeninfo));
8856 break;
8858 case VKI_PPCLAIM:
8859 case VKI_PPEXCL:
8860 case VKI_PPYIELD:
8861 case VKI_PPRELEASE:
8862 case VKI_PPSETMODE:
8863 case VKI_PPSETPHASE:
8864 case VKI_PPSETFLAGS:
8865 case VKI_PPWDATA:
8866 case VKI_PPWCONTROL:
8867 case VKI_PPFCONTROL:
8868 case VKI_PPDATADIR:
8869 case VKI_PPNEGOT:
8870 case VKI_PPWCTLONIRQ:
8871 case VKI_PPSETTIME:
8872 break;
8873 case VKI_PPGETMODE:
8874 POST_MEM_WRITE( ARG3, sizeof(int) );
8875 break;
8876 case VKI_PPGETPHASE:
8877 POST_MEM_WRITE( ARG3, sizeof(int) );
8878 break;
8879 case VKI_PPGETMODES:
8880 POST_MEM_WRITE( ARG3, sizeof(unsigned int) );
8881 break;
8882 case VKI_PPGETFLAGS:
8883 POST_MEM_WRITE( ARG3, sizeof(int) );
8884 break;
8885 case VKI_PPRSTATUS:
8886 POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
8887 break;
8888 case VKI_PPRDATA:
8889 POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
8890 break;
8891 case VKI_PPRCONTROL:
8892 POST_MEM_WRITE( ARG3, sizeof(unsigned char) );
8893 break;
8894 case VKI_PPCLRIRQ:
8895 POST_MEM_WRITE( ARG3, sizeof(int) );
8896 break;
8897 case VKI_PPGETTIME:
8898 POST_MEM_WRITE( ARG3, sizeof(struct vki_timeval) );
8899 break;
8901 case VKI_GIO_FONT:
8902 POST_MEM_WRITE( ARG3, 32 * 256 );
8903 break;
8904 case VKI_PIO_FONT:
8905 break;
8907 case VKI_GIO_FONTX:
8908 POST_MEM_WRITE( (Addr)((struct vki_consolefontdesc *)ARG3)->chardata,
8909 32 * ((struct vki_consolefontdesc *)ARG3)->charcount );
8910 break;
8911 case VKI_PIO_FONTX:
8912 break;
8914 case VKI_PIO_FONTRESET:
8915 break;
8917 case VKI_GIO_CMAP:
8918 POST_MEM_WRITE( ARG3, 16 * 3 );
8919 break;
8920 case VKI_PIO_CMAP:
8921 break;
8923 case VKI_KIOCSOUND:
8924 case VKI_KDMKTONE:
8925 break;
8927 case VKI_KDGETLED:
8928 POST_MEM_WRITE( ARG3, sizeof(char) );
8929 break;
8930 case VKI_KDSETLED:
8931 break;
8933 case VKI_KDGKBTYPE:
8934 POST_MEM_WRITE( ARG3, sizeof(char) );
8935 break;
8937 case VKI_KDADDIO:
8938 case VKI_KDDELIO:
8939 case VKI_KDENABIO:
8940 case VKI_KDDISABIO:
8941 break;
8943 case VKI_KDSETMODE:
8944 break;
8945 case VKI_KDGETMODE:
8946 POST_MEM_WRITE( ARG3, sizeof(int) );
8947 break;
8949 case VKI_KDMAPDISP:
8950 case VKI_KDUNMAPDISP:
8951 break;
8953 case VKI_GIO_SCRNMAP:
8954 POST_MEM_WRITE( ARG3, VKI_E_TABSZ );
8955 break;
8956 case VKI_PIO_SCRNMAP:
8957 break;
8958 case VKI_GIO_UNISCRNMAP:
8959 POST_MEM_WRITE( ARG3, VKI_E_TABSZ * sizeof(unsigned short) );
8960 break;
8961 case VKI_PIO_UNISCRNMAP:
8962 break;
8964 case VKI_GIO_UNIMAP:
8965 if ( ARG3 ) {
8966 struct vki_unimapdesc *desc = (struct vki_unimapdesc *) ARG3;
8967 POST_MEM_WRITE( (Addr)&desc->entry_ct, sizeof(desc->entry_ct));
8968 POST_MEM_WRITE( (Addr)desc->entries,
8969 desc->entry_ct * sizeof(struct vki_unipair) );
8971 break;
8972 case VKI_PIO_UNIMAP:
8973 break;
8974 case VKI_PIO_UNIMAPCLR:
8975 break;
8977 case VKI_KDGKBMODE:
8978 POST_MEM_WRITE( ARG3, sizeof(int) );
8979 break;
8980 case VKI_KDSKBMODE:
8981 break;
8983 case VKI_KDGKBMETA:
8984 POST_MEM_WRITE( ARG3, sizeof(int) );
8985 break;
8986 case VKI_KDSKBMETA:
8987 break;
8989 case VKI_KDGKBLED:
8990 POST_MEM_WRITE( ARG3, sizeof(char) );
8991 break;
8992 case VKI_KDSKBLED:
8993 break;
8995 case VKI_KDGKBENT:
8996 POST_MEM_WRITE( (Addr)&((struct vki_kbentry *)ARG3)->kb_value,
8997 sizeof(((struct vki_kbentry *)ARG3)->kb_value) );
8998 break;
8999 case VKI_KDSKBENT:
9000 break;
9002 case VKI_KDGKBSENT:
9003 POST_MEM_WRITE( (Addr)((struct vki_kbsentry *)ARG3)->kb_string,
9004 sizeof(((struct vki_kbsentry *)ARG3)->kb_string) );
9005 break;
9006 case VKI_KDSKBSENT:
9007 break;
9009 case VKI_KDGKBDIACR:
9010 POST_MEM_WRITE( ARG3, sizeof(struct vki_kbdiacrs) );
9011 break;
9012 case VKI_KDSKBDIACR:
9013 break;
9015 case VKI_KDGETKEYCODE:
9016 POST_MEM_WRITE( (Addr)((struct vki_kbkeycode *)ARG3)->keycode,
9017 sizeof(((struct vki_kbkeycode *)ARG3)->keycode) );
9018 break;
9019 case VKI_KDSETKEYCODE:
9020 break;
9022 case VKI_KDSIGACCEPT:
9023 break;
9025 case VKI_KDKBDREP:
9026 break;
9028 case VKI_KDFONTOP:
9029 if ( ARG3 ) {
9030 struct vki_console_font_op *op = (struct vki_console_font_op *) ARG3;
9031 switch ( op->op ) {
9032 case VKI_KD_FONT_OP_SET:
9033 break;
9034 case VKI_KD_FONT_OP_GET:
9035 if ( op->data )
9036 POST_MEM_WRITE( (Addr) op->data,
9037 (op->width + 7) / 8 * 32 * op->charcount );
9038 break;
9039 case VKI_KD_FONT_OP_SET_DEFAULT:
9040 break;
9041 case VKI_KD_FONT_OP_COPY:
9042 break;
9044 POST_MEM_WRITE( (Addr) op, sizeof(*op));
9046 break;
9048 case VKI_VT_OPENQRY:
9049 POST_MEM_WRITE( ARG3, sizeof(int) );
9050 break;
9051 case VKI_VT_GETMODE:
9052 POST_MEM_WRITE( ARG3, sizeof(struct vki_vt_mode) );
9053 break;
9054 case VKI_VT_SETMODE:
9055 break;
9056 case VKI_VT_GETSTATE:
9057 POST_MEM_WRITE( (Addr) &(((struct vki_vt_stat*) ARG3)->v_active),
9058 sizeof(((struct vki_vt_stat*) ARG3)->v_active) );
9059 POST_MEM_WRITE( (Addr) &(((struct vki_vt_stat*) ARG3)->v_state),
9060 sizeof(((struct vki_vt_stat*) ARG3)->v_state) );
9061 break;
9062 case VKI_VT_RELDISP:
9063 case VKI_VT_ACTIVATE:
9064 case VKI_VT_WAITACTIVE:
9065 case VKI_VT_DISALLOCATE:
9066 break;
9067 case VKI_VT_RESIZE:
9068 break;
9069 case VKI_VT_RESIZEX:
9070 break;
9071 case VKI_VT_LOCKSWITCH:
9072 case VKI_VT_UNLOCKSWITCH:
9073 break;
9075 case VKI_USBDEVFS_CONTROL:
9076 if ( ARG3 ) {
9077 struct vki_usbdevfs_ctrltransfer *vkuc = (struct vki_usbdevfs_ctrltransfer *)ARG3;
9078 if (vkuc->bRequestType & 0x80)
9079 POST_MEM_WRITE((Addr)vkuc->data, RES);
9081 break;
9082 case VKI_USBDEVFS_BULK:
9083 if ( ARG3 ) {
9084 struct vki_usbdevfs_bulktransfer *vkub = (struct vki_usbdevfs_bulktransfer *)ARG3;
9085 if (vkub->ep & 0x80)
9086 POST_MEM_WRITE((Addr)vkub->data, RES);
9088 break;
9089 case VKI_USBDEVFS_GETDRIVER:
9090 if ( ARG3 ) {
9091 struct vki_usbdevfs_getdriver *vkugd = (struct vki_usbdevfs_getdriver *)ARG3;
9092 POST_MEM_WRITE((Addr)&vkugd->driver, sizeof(vkugd->driver));
9094 break;
9095 case VKI_USBDEVFS_REAPURB:
9096 case VKI_USBDEVFS_REAPURBNDELAY:
9097 if ( ARG3 ) {
9098 struct vki_usbdevfs_urb **vkuu = (struct vki_usbdevfs_urb**)ARG3;
9099 POST_MEM_WRITE((Addr)vkuu, sizeof(*vkuu));
9100 if (!*vkuu)
9101 break;
9102 POST_MEM_WRITE((Addr) &((*vkuu)->status),sizeof((*vkuu)->status));
9103 if ((*vkuu)->type == VKI_USBDEVFS_URB_TYPE_CONTROL) {
9104 struct vki_usbdevfs_setuppacket *vkusp = (struct vki_usbdevfs_setuppacket *)(*vkuu)->buffer;
9105 if (vkusp->bRequestType & 0x80)
9106 POST_MEM_WRITE((Addr)(vkusp+1), (*vkuu)->buffer_length - sizeof(*vkusp));
9107 POST_MEM_WRITE((Addr)&(*vkuu)->actual_length, sizeof((*vkuu)->actual_length));
9108 } else if ((*vkuu)->type == VKI_USBDEVFS_URB_TYPE_ISO) {
9109 char *bp = (*vkuu)->buffer;
9110 int i;
9111 for(i=0; i<(*vkuu)->number_of_packets; i++) {
9112 POST_MEM_WRITE((Addr)&(*vkuu)->iso_frame_desc[i].actual_length, sizeof((*vkuu)->iso_frame_desc[i].actual_length));
9113 POST_MEM_WRITE((Addr)&(*vkuu)->iso_frame_desc[i].status, sizeof((*vkuu)->iso_frame_desc[i].status));
9114 if ((*vkuu)->endpoint & 0x80)
9115 POST_MEM_WRITE((Addr)bp, (*vkuu)->iso_frame_desc[i].actual_length);
9116 bp += (*vkuu)->iso_frame_desc[i].length; // FIXME: or actual_length??
9118 POST_MEM_WRITE((Addr)&(*vkuu)->error_count, sizeof((*vkuu)->error_count));
9119 } else {
9120 if ((*vkuu)->endpoint & 0x80)
9121 POST_MEM_WRITE((Addr)(*vkuu)->buffer, (*vkuu)->actual_length);
9122 POST_MEM_WRITE((Addr)&(*vkuu)->actual_length, sizeof((*vkuu)->actual_length));
9125 break;
9126 case VKI_USBDEVFS_CONNECTINFO:
9127 POST_MEM_WRITE(ARG3, sizeof(struct vki_usbdevfs_connectinfo));
9128 break;
9129 case VKI_USBDEVFS_IOCTL:
9130 if ( ARG3 ) {
9131 struct vki_usbdevfs_ioctl *vkui = (struct vki_usbdevfs_ioctl *)ARG3;
9132 UInt dir2, size2;
9133 dir2 = _VKI_IOC_DIR(vkui->ioctl_code);
9134 size2 = _VKI_IOC_SIZE(vkui->ioctl_code);
9135 if (size2 > 0) {
9136 if (dir2 & _VKI_IOC_READ)
9137 POST_MEM_WRITE((Addr)vkui->data, size2);
9140 break;
9142 /* I2C (/dev/i2c-*) ioctls */
9143 case VKI_I2C_SLAVE:
9144 case VKI_I2C_SLAVE_FORCE:
9145 case VKI_I2C_TENBIT:
9146 case VKI_I2C_PEC:
9147 break;
9148 case VKI_I2C_FUNCS:
9149 POST_MEM_WRITE( ARG3, sizeof(unsigned long) );
9150 break;
9151 case VKI_I2C_RDWR:
9152 if ( ARG3 ) {
9153 struct vki_i2c_rdwr_ioctl_data *vkui = (struct vki_i2c_rdwr_ioctl_data *)ARG3;
9154 UInt i;
9155 for (i=0; i < vkui->nmsgs; i++) {
9156 struct vki_i2c_msg *msg = vkui->msgs + i;
9157 if (msg->flags & VKI_I2C_M_RD)
9158 POST_MEM_WRITE((Addr)msg->buf, msg->len);
9161 break;
9163 /* Wireless extensions ioctls */
9164 case VKI_SIOCSIWCOMMIT:
9165 case VKI_SIOCSIWNWID:
9166 case VKI_SIOCSIWFREQ:
9167 case VKI_SIOCSIWMODE:
9168 case VKI_SIOCSIWSENS:
9169 case VKI_SIOCSIWRANGE:
9170 case VKI_SIOCSIWPRIV:
9171 case VKI_SIOCSIWSTATS:
9172 case VKI_SIOCSIWSPY:
9173 case VKI_SIOCSIWTHRSPY:
9174 case VKI_SIOCSIWAP:
9175 case VKI_SIOCSIWSCAN:
9176 case VKI_SIOCSIWESSID:
9177 case VKI_SIOCSIWRATE:
9178 case VKI_SIOCSIWNICKN:
9179 case VKI_SIOCSIWRTS:
9180 case VKI_SIOCSIWFRAG:
9181 case VKI_SIOCSIWTXPOW:
9182 case VKI_SIOCSIWRETRY:
9183 case VKI_SIOCSIWENCODE:
9184 case VKI_SIOCSIWPOWER:
9185 case VKI_SIOCSIWGENIE:
9186 case VKI_SIOCSIWMLME:
9187 case VKI_SIOCSIWAUTH:
9188 case VKI_SIOCSIWENCODEEXT:
9189 case VKI_SIOCSIWPMKSA:
9190 break;
9191 case VKI_SIOCGIWNAME:
9192 if (ARG3) {
9193 POST_MEM_WRITE((Addr)((struct vki_iwreq *)ARG3)->u.name,
9194 sizeof(((struct vki_iwreq *)ARG3)->u.name));
9196 break;
9197 case VKI_SIOCGIWNWID:
9198 case VKI_SIOCGIWSENS:
9199 case VKI_SIOCGIWRATE:
9200 case VKI_SIOCGIWRTS:
9201 case VKI_SIOCGIWFRAG:
9202 case VKI_SIOCGIWTXPOW:
9203 case VKI_SIOCGIWRETRY:
9204 case VKI_SIOCGIWPOWER:
9205 case VKI_SIOCGIWAUTH:
9206 if (ARG3) {
9207 POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.param,
9208 sizeof(struct vki_iw_param));
9210 break;
9211 case VKI_SIOCGIWFREQ:
9212 if (ARG3) {
9213 POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.freq,
9214 sizeof(struct vki_iw_freq));
9216 break;
9217 case VKI_SIOCGIWMODE:
9218 if (ARG3) {
9219 POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.mode,
9220 sizeof(__vki_u32));
9222 break;
9223 case VKI_SIOCGIWRANGE:
9224 case VKI_SIOCGIWPRIV:
9225 case VKI_SIOCGIWSTATS:
9226 case VKI_SIOCGIWSPY:
9227 case VKI_SIOCGIWTHRSPY:
9228 case VKI_SIOCGIWAPLIST:
9229 case VKI_SIOCGIWSCAN:
9230 case VKI_SIOCGIWESSID:
9231 case VKI_SIOCGIWNICKN:
9232 case VKI_SIOCGIWENCODE:
9233 case VKI_SIOCGIWGENIE:
9234 case VKI_SIOCGIWENCODEEXT:
9235 if (ARG3) {
9236 struct vki_iw_point* point;
9237 point = &((struct vki_iwreq *)ARG3)->u.data;
9238 POST_MEM_WRITE((Addr)point->pointer, point->length);
9240 break;
9241 case VKI_SIOCGIWAP:
9242 if (ARG3) {
9243 POST_MEM_WRITE((Addr)&((struct vki_iwreq *)ARG3)->u.ap_addr,
9244 sizeof(struct vki_sockaddr));
9246 break;
9248 # if defined(VGPV_arm_linux_android) || defined(VGPV_x86_linux_android) \
9249 || defined(VGPV_mips32_linux_android)
9250 /* ashmem */
9251 case VKI_ASHMEM_GET_SIZE:
9252 case VKI_ASHMEM_SET_SIZE:
9253 case VKI_ASHMEM_GET_PROT_MASK:
9254 case VKI_ASHMEM_SET_PROT_MASK:
9255 case VKI_ASHMEM_GET_PIN_STATUS:
9256 case VKI_ASHMEM_PURGE_ALL_CACHES:
9257 case VKI_ASHMEM_SET_NAME:
9258 case VKI_ASHMEM_PIN:
9259 case VKI_ASHMEM_UNPIN:
9260 break;
9261 case VKI_ASHMEM_GET_NAME:
9262 POST_MEM_WRITE( ARG3, VKI_ASHMEM_NAME_LEN );
9263 break;
9265 /* binder */
9266 case VKI_BINDER_WRITE_READ:
9267 if (ARG3) {
9268 struct vki_binder_write_read* bwr
9269 = (struct vki_binder_write_read*)ARG3;
9270 POST_FIELD_WRITE(bwr->write_consumed);
9271 POST_FIELD_WRITE(bwr->read_consumed);
9273 if (bwr->read_size)
9274 POST_MEM_WRITE((Addr)bwr->read_buffer, bwr->read_consumed);
9276 break;
9278 case VKI_BINDER_SET_IDLE_TIMEOUT:
9279 case VKI_BINDER_SET_MAX_THREADS:
9280 case VKI_BINDER_SET_IDLE_PRIORITY:
9281 case VKI_BINDER_SET_CONTEXT_MGR:
9282 case VKI_BINDER_THREAD_EXIT:
9283 break;
9284 case VKI_BINDER_VERSION:
9285 if (ARG3) {
9286 struct vki_binder_version* bv = (struct vki_binder_version*)ARG3;
9287 POST_FIELD_WRITE(bv->protocol_version);
9289 break;
9290 # endif /* defined(VGPV_*_linux_android) */
9292 case VKI_HCIGETDEVLIST:
9293 if (ARG3) {
9294 struct vki_hci_dev_list_req* dlr = (struct vki_hci_dev_list_req*)ARG3;
9295 POST_MEM_WRITE((Addr)ARG3 + sizeof(struct vki_hci_dev_list_req),
9296 dlr->dev_num * sizeof(struct vki_hci_dev_req));
9298 break;
9300 case VKI_HCIINQUIRY:
9301 if (ARG3) {
9302 struct vki_hci_inquiry_req* ir = (struct vki_hci_inquiry_req*)ARG3;
9303 POST_MEM_WRITE((Addr)ARG3 + sizeof(struct vki_hci_inquiry_req),
9304 ir->num_rsp * sizeof(struct vki_inquiry_info));
9306 break;
9308 case VKI_DRM_IOCTL_VERSION:
9309 if (ARG3) {
9310 struct vki_drm_version *data = (struct vki_drm_version *)ARG3;
9311 POST_MEM_WRITE((Addr)&data->version_major, sizeof(data->version_major));
9312 POST_MEM_WRITE((Addr)&data->version_minor, sizeof(data->version_minor));
9313 POST_MEM_WRITE((Addr)&data->version_patchlevel, sizeof(data->version_patchlevel));
9314 POST_MEM_WRITE((Addr)&data->name_len, sizeof(data->name_len));
9315 POST_MEM_WRITE((Addr)data->name, data->name_len);
9316 POST_MEM_WRITE((Addr)&data->date_len, sizeof(data->date_len));
9317 POST_MEM_WRITE((Addr)data->date, data->date_len);
9318 POST_MEM_WRITE((Addr)&data->desc_len, sizeof(data->desc_len));
9319 POST_MEM_WRITE((Addr)data->desc, data->desc_len);
9321 break;
9322 case VKI_DRM_IOCTL_GET_UNIQUE:
9323 if (ARG3) {
9324 struct vki_drm_unique *data = (struct vki_drm_unique *)ARG3;
9325 POST_MEM_WRITE((Addr)data->unique, sizeof(data->unique_len));
9327 break;
9328 case VKI_DRM_IOCTL_GET_MAGIC:
9329 if (ARG3) {
9330 struct vki_drm_auth *data = (struct vki_drm_auth *)ARG3;
9331 POST_MEM_WRITE((Addr)&data->magic, sizeof(data->magic));
9333 break;
9334 case VKI_DRM_IOCTL_WAIT_VBLANK:
9335 if (ARG3) {
9336 union vki_drm_wait_vblank *data = (union vki_drm_wait_vblank *)ARG3;
9337 POST_MEM_WRITE((Addr)&data->reply, sizeof(data->reply));
9339 break;
9340 case VKI_DRM_IOCTL_GEM_FLINK:
9341 if (ARG3) {
9342 struct vki_drm_gem_flink *data = (struct vki_drm_gem_flink *)ARG3;
9343 POST_MEM_WRITE((Addr)&data->name, sizeof(data->name));
9345 break;
9346 case VKI_DRM_IOCTL_GEM_OPEN:
9347 if (ARG3) {
9348 struct vki_drm_gem_open *data = (struct vki_drm_gem_open *)ARG3;
9349 POST_MEM_WRITE((Addr)&data->handle, sizeof(data->handle));
9350 POST_MEM_WRITE((Addr)&data->size, sizeof(data->size));
9352 break;
9353 case VKI_DRM_IOCTL_I915_GETPARAM:
9354 if (ARG3) {
9355 vki_drm_i915_getparam_t *data = (vki_drm_i915_getparam_t *)ARG3;
9356 POST_MEM_WRITE((Addr)data->value, sizeof(int));
9358 break;
9359 case VKI_DRM_IOCTL_I915_GEM_BUSY:
9360 if (ARG3) {
9361 struct vki_drm_i915_gem_busy *data = (struct vki_drm_i915_gem_busy *)ARG3;
9362 POST_MEM_WRITE((Addr)&data->busy, sizeof(data->busy));
9364 break;
9365 case VKI_DRM_IOCTL_I915_GEM_CREATE:
9366 if (ARG3) {
9367 struct vki_drm_i915_gem_create *data = (struct vki_drm_i915_gem_create *)ARG3;
9368 POST_MEM_WRITE((Addr)&data->handle, sizeof(data->handle));
9370 break;
9371 case VKI_DRM_IOCTL_I915_GEM_PREAD:
9372 if (ARG3) {
9373 struct vki_drm_i915_gem_pread *data = (struct vki_drm_i915_gem_pread *)ARG3;
9374 POST_MEM_WRITE((Addr)data->data_ptr, data->size);
9376 break;
9377 case VKI_DRM_IOCTL_I915_GEM_MMAP_GTT:
9378 if (ARG3) {
9379 struct vki_drm_i915_gem_mmap_gtt *data = (struct vki_drm_i915_gem_mmap_gtt *)ARG3;
9380 POST_MEM_WRITE((Addr)&data->offset, sizeof(data->offset));
9382 break;
9383 case VKI_DRM_IOCTL_I915_GEM_SET_TILING:
9384 if (ARG3) {
9385 struct vki_drm_i915_gem_set_tiling *data = (struct vki_drm_i915_gem_set_tiling *)ARG3;
9386 POST_MEM_WRITE((Addr)&data->tiling_mode, sizeof(data->tiling_mode));
9387 POST_MEM_WRITE((Addr)&data->stride, sizeof(data->stride));
9388 POST_MEM_WRITE((Addr)&data->swizzle_mode, sizeof(data->swizzle_mode));
9390 break;
9391 case VKI_DRM_IOCTL_I915_GEM_GET_TILING:
9392 if (ARG3) {
9393 struct vki_drm_i915_gem_get_tiling *data = (struct vki_drm_i915_gem_get_tiling *)ARG3;
9394 POST_MEM_WRITE((Addr)&data->tiling_mode, sizeof(data->tiling_mode));
9395 POST_MEM_WRITE((Addr)&data->swizzle_mode, sizeof(data->swizzle_mode));
9397 break;
9398 case VKI_DRM_IOCTL_I915_GEM_GET_APERTURE:
9399 if (ARG3) {
9400 struct vki_drm_i915_gem_get_aperture *data = (struct vki_drm_i915_gem_get_aperture *)ARG3;
9401 POST_MEM_WRITE((Addr)&data->aper_size, sizeof(data->aper_size));
9402 POST_MEM_WRITE((Addr)&data->aper_available_size, sizeof(data->aper_available_size));
9404 break;
9406 /* KVM ioctls that only write the system call return value */
9407 case VKI_KVM_GET_API_VERSION:
9408 case VKI_KVM_CREATE_VM:
9409 case VKI_KVM_CHECK_EXTENSION:
9410 case VKI_KVM_GET_VCPU_MMAP_SIZE:
9411 case VKI_KVM_S390_ENABLE_SIE:
9412 case VKI_KVM_CREATE_VCPU:
9413 case VKI_KVM_SET_TSS_ADDR:
9414 case VKI_KVM_CREATE_IRQCHIP:
9415 case VKI_KVM_RUN:
9416 case VKI_KVM_S390_INITIAL_RESET:
9417 case VKI_KVM_KVMCLOCK_CTRL:
9418 break;
9420 #ifdef ENABLE_XEN
9421 case VKI_XEN_IOCTL_PRIVCMD_HYPERCALL: {
9422 SyscallArgs harrghs;
9423 struct vki_xen_privcmd_hypercall *args =
9424 (struct vki_xen_privcmd_hypercall *)(ARG3);
9426 if (!args)
9427 break;
9429 VG_(memset)(&harrghs, 0, sizeof(harrghs));
9430 harrghs.sysno = args->op;
9431 harrghs.arg1 = args->arg[0];
9432 harrghs.arg2 = args->arg[1];
9433 harrghs.arg3 = args->arg[2];
9434 harrghs.arg4 = args->arg[3];
9435 harrghs.arg5 = args->arg[4];
9436 harrghs.arg6 = harrghs.arg7 = harrghs.arg8 = 0;
9438 WRAPPER_POST_NAME(xen, hypercall) (tid, &harrghs, status);
9440 break;
9442 case VKI_XEN_IOCTL_PRIVCMD_MMAP:
9443 break;
9444 case VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH: {
9445 struct vki_xen_privcmd_mmapbatch *args =
9446 (struct vki_xen_privcmd_mmapbatch *)(ARG3);
9447 POST_MEM_WRITE((Addr)args->arr, sizeof(*(args->arr)) * args->num);
9449 break;
9450 case VKI_XEN_IOCTL_PRIVCMD_MMAPBATCH_V2: {
9451 struct vki_xen_privcmd_mmapbatch_v2 *args =
9452 (struct vki_xen_privcmd_mmapbatch_v2 *)(ARG3);
9453 POST_MEM_WRITE((Addr)args->err, sizeof(*(args->err)) * args->num);
9455 break;
9457 case VKI_XEN_IOCTL_EVTCHN_BIND_VIRQ:
9458 case VKI_XEN_IOCTL_EVTCHN_BIND_INTERDOMAIN:
9459 case VKI_XEN_IOCTL_EVTCHN_BIND_UNBOUND_PORT:
9460 case VKI_XEN_IOCTL_EVTCHN_UNBIND:
9461 case VKI_XEN_IOCTL_EVTCHN_NOTIFY:
9462 case VKI_XEN_IOCTL_EVTCHN_RESET:
9463 /* No output */
9464 break;
9465 #endif
9467 /* To do: figure out which software layer extends the sign of 'request' */
9468 case VKI_OBD_IOC_FID2PATH: {
9469 struct vki_getinfo_fid2path *args = (void *)(ARG3);
9470 POST_MEM_WRITE((Addr)args->gf_path, args->gf_pathlen);
9472 break;
9474 /* V4L2 */
9475 case VKI_V4L2_S_FMT:
9476 case VKI_V4L2_TRY_FMT:
9477 case VKI_V4L2_REQBUFS:
9478 case VKI_V4L2_OVERLAY:
9479 case VKI_V4L2_STREAMON:
9480 case VKI_V4L2_STREAMOFF:
9481 case VKI_V4L2_S_PARM:
9482 case VKI_V4L2_S_STD:
9483 case VKI_V4L2_S_FREQUENCY:
9484 case VKI_V4L2_S_CTRL:
9485 case VKI_V4L2_S_TUNER:
9486 case VKI_V4L2_S_AUDIO:
9487 case VKI_V4L2_S_INPUT:
9488 case VKI_V4L2_S_EDID:
9489 case VKI_V4L2_S_OUTPUT:
9490 case VKI_V4L2_S_AUDOUT:
9491 case VKI_V4L2_S_MODULATOR:
9492 case VKI_V4L2_S_JPEGCOMP:
9493 case VKI_V4L2_S_CROP:
9494 case VKI_V4L2_S_PRIORITY:
9495 case VKI_V4L2_G_ENC_INDEX:
9496 case VKI_V4L2_S_HW_FREQ_SEEK:
9497 case VKI_V4L2_S_DV_TIMINGS:
9498 case VKI_V4L2_SUBSCRIBE_EVENT:
9499 case VKI_V4L2_UNSUBSCRIBE_EVENT:
9500 case VKI_V4L2_PREPARE_BUF:
9501 break;
9502 case VKI_V4L2_QUERYCAP: {
9503 struct vki_v4l2_capability *data = (struct vki_v4l2_capability *)ARG3;
9504 POST_MEM_WRITE((Addr)data, sizeof(*data));
9505 break;
9507 case VKI_V4L2_ENUM_FMT: {
9508 struct vki_v4l2_fmtdesc *data = (struct vki_v4l2_fmtdesc *)ARG3;
9509 POST_FIELD_WRITE(data->flags);
9510 POST_FIELD_WRITE(data->description);
9511 POST_FIELD_WRITE(data->pixelformat);
9512 POST_FIELD_WRITE(data->reserved);
9513 break;
9515 case VKI_V4L2_G_FMT: {
9516 struct vki_v4l2_format *data = (struct vki_v4l2_format *)ARG3;
9517 switch (data->type) {
9518 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE:
9519 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT:
9520 POST_FIELD_WRITE(data->fmt.pix);
9521 break;
9522 case VKI_V4L2_BUF_TYPE_VBI_CAPTURE:
9523 case VKI_V4L2_BUF_TYPE_VBI_OUTPUT:
9524 POST_FIELD_WRITE(data->fmt.vbi);
9525 break;
9526 case VKI_V4L2_BUF_TYPE_SLICED_VBI_CAPTURE:
9527 case VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT:
9528 POST_FIELD_WRITE(data->fmt.sliced);
9529 break;
9530 case VKI_V4L2_BUF_TYPE_VIDEO_OVERLAY:
9531 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_OVERLAY:
9532 POST_FIELD_WRITE(data->fmt.win);
9533 break;
9534 case VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
9535 case VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
9536 POST_FIELD_WRITE(data->fmt.pix_mp);
9537 break;
9538 case VKI_V4L2_BUF_TYPE_SDR_CAPTURE:
9539 POST_FIELD_WRITE(data->fmt.sdr);
9540 break;
9542 break;
9544 case VKI_V4L2_QUERYBUF: {
9545 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
9546 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
9547 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
9548 unsigned i;
9550 for (i = 0; i < data->length; i++) {
9551 POST_FIELD_WRITE(data->m.planes[i].bytesused);
9552 POST_FIELD_WRITE(data->m.planes[i].length);
9553 POST_FIELD_WRITE(data->m.planes[i].m);
9554 POST_FIELD_WRITE(data->m.planes[i].data_offset);
9555 POST_FIELD_WRITE(data->m.planes[i].reserved);
9557 } else {
9558 POST_FIELD_WRITE(data->m);
9559 POST_FIELD_WRITE(data->length);
9561 POST_FIELD_WRITE(data->bytesused);
9562 POST_FIELD_WRITE(data->flags);
9563 POST_FIELD_WRITE(data->field);
9564 POST_FIELD_WRITE(data->timestamp);
9565 POST_FIELD_WRITE(data->timecode);
9566 POST_FIELD_WRITE(data->sequence);
9567 POST_FIELD_WRITE(data->memory);
9568 POST_FIELD_WRITE(data->sequence);
9569 break;
9571 case VKI_V4L2_G_FBUF: {
9572 struct vki_v4l2_framebuffer *data = (struct vki_v4l2_framebuffer *)ARG3;
9573 POST_MEM_WRITE((Addr)data, sizeof(*data));
9574 break;
9576 case VKI_V4L2_S_FBUF: {
9577 struct vki_v4l2_framebuffer *data = (struct vki_v4l2_framebuffer *)ARG3;
9578 POST_FIELD_WRITE(data->capability);
9579 POST_FIELD_WRITE(data->flags);
9580 POST_FIELD_WRITE(data->fmt);
9581 break;
9583 case VKI_V4L2_QBUF: {
9584 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
9586 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
9587 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
9588 unsigned i;
9590 for (i = 0; i < data->length; i++) {
9591 POST_FIELD_WRITE(data->m.planes[i].length);
9592 if (data->memory == VKI_V4L2_MEMORY_MMAP)
9593 POST_FIELD_WRITE(data->m.planes[i].m);
9595 } else {
9596 if (data->memory == VKI_V4L2_MEMORY_MMAP)
9597 POST_FIELD_WRITE(data->m);
9598 POST_FIELD_WRITE(data->length);
9600 break;
9602 case VKI_V4L2_EXPBUF: {
9603 struct vki_v4l2_exportbuffer *data = (struct vki_v4l2_exportbuffer *)ARG3;
9604 POST_FIELD_WRITE(data->fd);
9605 break;
9607 case VKI_V4L2_DQBUF: {
9608 struct vki_v4l2_buffer *data = (struct vki_v4l2_buffer *)ARG3;
9609 POST_FIELD_WRITE(data->index);
9610 POST_FIELD_WRITE(data->bytesused);
9611 POST_FIELD_WRITE(data->field);
9612 if (data->type == VKI_V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE ||
9613 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) {
9614 unsigned i;
9616 for (i = 0; i < data->length; i++) {
9617 POST_FIELD_WRITE(data->m.planes[i].bytesused);
9618 POST_FIELD_WRITE(data->m.planes[i].data_offset);
9619 POST_FIELD_WRITE(data->m.planes[i].length);
9620 POST_FIELD_WRITE(data->m.planes[i].m);
9622 } else {
9623 POST_FIELD_WRITE(data->m);
9624 POST_FIELD_WRITE(data->length);
9625 POST_FIELD_WRITE(data->bytesused);
9626 POST_FIELD_WRITE(data->field);
9628 POST_FIELD_WRITE(data->timestamp);
9629 POST_FIELD_WRITE(data->timecode);
9630 POST_FIELD_WRITE(data->sequence);
9631 break;
9633 case VKI_V4L2_G_PARM: {
9634 struct vki_v4l2_streamparm *data = (struct vki_v4l2_streamparm *)ARG3;
9635 int is_output = data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT ||
9636 data->type == VKI_V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE ||
9637 data->type == VKI_V4L2_BUF_TYPE_VBI_OUTPUT ||
9638 data->type == VKI_V4L2_BUF_TYPE_SLICED_VBI_OUTPUT;
9640 if (is_output)
9641 POST_MEM_WRITE((Addr)&data->parm.output,
9642 sizeof(data->parm.output) - sizeof(data->parm.output.reserved));
9643 else
9644 POST_MEM_WRITE((Addr)&data->parm.capture,
9645 sizeof(data->parm.capture) - sizeof(data->parm.capture.reserved));
9646 break;
9648 case VKI_V4L2_G_STD: {
9649 vki_v4l2_std_id *data = (vki_v4l2_std_id *)ARG3;
9650 POST_MEM_WRITE((Addr)data, sizeof(*data));
9651 break;
9653 case VKI_V4L2_ENUMSTD: {
9654 struct vki_v4l2_standard *data = (struct vki_v4l2_standard *)ARG3;
9655 POST_MEM_WRITE((Addr)&data->id, sizeof(*data) - sizeof(data->index));
9656 break;
9658 case VKI_V4L2_ENUMINPUT: {
9659 struct vki_v4l2_input *data = (struct vki_v4l2_input *)ARG3;
9660 POST_MEM_WRITE((Addr)data->name, sizeof(*data) - sizeof(data->index));
9661 break;
9663 case VKI_V4L2_G_CTRL: {
9664 struct vki_v4l2_control *data = (struct vki_v4l2_control *)ARG3;
9665 POST_FIELD_WRITE(data->value);
9666 break;
9668 case VKI_V4L2_G_TUNER: {
9669 struct vki_v4l2_tuner *data = (struct vki_v4l2_tuner *)ARG3;
9670 POST_MEM_WRITE((Addr)data->name,
9671 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9672 break;
9674 case VKI_V4L2_G_AUDIO: {
9675 struct vki_v4l2_audio *data = (struct vki_v4l2_audio *)ARG3;
9676 POST_MEM_WRITE((Addr)data->name,
9677 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9678 break;
9680 case VKI_V4L2_QUERYCTRL: {
9681 struct vki_v4l2_queryctrl *data = (struct vki_v4l2_queryctrl *)ARG3;
9682 POST_MEM_WRITE((Addr)&data->type,
9683 sizeof(*data) - sizeof(data->id));
9684 break;
9686 case VKI_V4L2_QUERYMENU: {
9687 struct vki_v4l2_querymenu *data = (struct vki_v4l2_querymenu *)ARG3;
9688 POST_MEM_WRITE((Addr)data->name,
9689 sizeof(*data) - sizeof(data->id) - sizeof(data->index));
9690 break;
9692 case VKI_V4L2_G_INPUT: {
9693 int *data = (int *)ARG3;
9694 POST_MEM_WRITE((Addr)data, sizeof(*data));
9695 break;
9697 case VKI_V4L2_G_EDID: {
9698 struct vki_v4l2_edid *data = (struct vki_v4l2_edid *)ARG3;
9699 if (data->blocks && data->edid)
9700 POST_MEM_WRITE((Addr)data->edid, data->blocks * 128);
9701 break;
9703 case VKI_V4L2_G_OUTPUT: {
9704 int *data = (int *)ARG3;
9705 POST_MEM_WRITE((Addr)data, sizeof(*data));
9706 break;
9708 case VKI_V4L2_ENUMOUTPUT: {
9709 struct vki_v4l2_output *data = (struct vki_v4l2_output *)ARG3;
9710 POST_MEM_WRITE((Addr)data->name, sizeof(*data) - sizeof(data->index));
9711 break;
9713 case VKI_V4L2_G_AUDOUT: {
9714 struct vki_v4l2_audioout *data = (struct vki_v4l2_audioout *)ARG3;
9715 POST_MEM_WRITE((Addr)data->name,
9716 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9717 break;
9719 case VKI_V4L2_G_MODULATOR: {
9720 struct vki_v4l2_modulator *data = (struct vki_v4l2_modulator *)ARG3;
9721 POST_MEM_WRITE((Addr)data->name,
9722 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9723 break;
9725 case VKI_V4L2_G_FREQUENCY: {
9726 struct vki_v4l2_frequency *data = (struct vki_v4l2_frequency *)ARG3;
9727 POST_FIELD_WRITE(data->type);
9728 POST_FIELD_WRITE(data->frequency);
9729 break;
9731 case VKI_V4L2_CROPCAP: {
9732 struct vki_v4l2_cropcap *data = (struct vki_v4l2_cropcap *)ARG3;
9733 POST_MEM_WRITE((Addr)&data->bounds, sizeof(*data) - sizeof(data->type));
9734 break;
9736 case VKI_V4L2_G_CROP: {
9737 struct vki_v4l2_crop *data = (struct vki_v4l2_crop *)ARG3;
9738 POST_FIELD_WRITE(data->c);
9739 break;
9741 case VKI_V4L2_G_JPEGCOMP: {
9742 struct vki_v4l2_jpegcompression *data = (struct vki_v4l2_jpegcompression *)ARG3;
9743 POST_MEM_WRITE((Addr)data, sizeof(*data));
9744 break;
9746 case VKI_V4L2_QUERYSTD: {
9747 vki_v4l2_std_id *data = (vki_v4l2_std_id *)ARG3;
9748 POST_MEM_WRITE((Addr)data, sizeof(*data));
9749 break;
9751 case VKI_V4L2_ENUMAUDIO: {
9752 struct vki_v4l2_audio *data = (struct vki_v4l2_audio *)ARG3;
9753 POST_MEM_WRITE((Addr)data->name,
9754 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9755 break;
9757 case VKI_V4L2_ENUMAUDOUT: {
9758 struct vki_v4l2_audioout *data = (struct vki_v4l2_audioout *)ARG3;
9759 POST_MEM_WRITE((Addr)data->name,
9760 sizeof(*data) - sizeof(data->index) - sizeof(data->reserved));
9761 break;
9763 case VKI_V4L2_G_PRIORITY: {
9764 __vki_u32 *data = (__vki_u32 *)ARG3;
9765 POST_MEM_WRITE((Addr)data, sizeof(*data));
9766 break;
9768 case VKI_V4L2_G_SLICED_VBI_CAP: {
9769 struct vki_v4l2_sliced_vbi_cap *data = (struct vki_v4l2_sliced_vbi_cap *)ARG3;
9770 POST_MEM_WRITE((Addr)data,
9771 sizeof(*data) - sizeof(data->type) - sizeof(data->reserved));
9772 break;
9774 case VKI_V4L2_G_EXT_CTRLS: {
9775 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
9776 if (data->count) {
9777 unsigned i;
9779 for (i = 0; i < data->count; i++) {
9780 if (data->controls[i].size)
9781 POST_MEM_WRITE((Addr)data->controls[i].ptr, data->controls[i].size);
9782 else
9783 POST_FIELD_WRITE(data->controls[i].value64);
9786 POST_FIELD_WRITE(data->error_idx);
9787 break;
9789 case VKI_V4L2_S_EXT_CTRLS: {
9790 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
9791 POST_FIELD_WRITE(data->error_idx);
9792 break;
9794 case VKI_V4L2_TRY_EXT_CTRLS: {
9795 struct vki_v4l2_ext_controls *data = (struct vki_v4l2_ext_controls *)ARG3;
9796 POST_FIELD_WRITE(data->error_idx);
9797 break;
9799 case VKI_V4L2_ENUM_FRAMESIZES: {
9800 struct vki_v4l2_frmsizeenum *data = (struct vki_v4l2_frmsizeenum *)ARG3;
9801 POST_FIELD_WRITE(data->type);
9802 POST_FIELD_WRITE(data->stepwise);
9803 break;
9805 case VKI_V4L2_ENUM_FRAMEINTERVALS: {
9806 struct vki_v4l2_frmivalenum *data = (struct vki_v4l2_frmivalenum *)ARG3;
9807 POST_FIELD_WRITE(data->type);
9808 POST_FIELD_WRITE(data->stepwise);
9809 break;
9811 case VKI_V4L2_ENCODER_CMD: {
9812 struct vki_v4l2_encoder_cmd *data = (struct vki_v4l2_encoder_cmd *)ARG3;
9813 POST_FIELD_WRITE(data->flags);
9814 break;
9816 case VKI_V4L2_TRY_ENCODER_CMD: {
9817 struct vki_v4l2_encoder_cmd *data = (struct vki_v4l2_encoder_cmd *)ARG3;
9818 POST_FIELD_WRITE(data->flags);
9819 break;
9821 case VKI_V4L2_DBG_S_REGISTER: {
9822 struct vki_v4l2_dbg_register *data = (struct vki_v4l2_dbg_register *)ARG3;
9823 POST_FIELD_WRITE(data->size);
9824 break;
9826 case VKI_V4L2_DBG_G_REGISTER: {
9827 struct vki_v4l2_dbg_register *data = (struct vki_v4l2_dbg_register *)ARG3;
9828 POST_FIELD_WRITE(data->val);
9829 POST_FIELD_WRITE(data->size);
9830 break;
9832 case VKI_V4L2_G_DV_TIMINGS: {
9833 struct vki_v4l2_dv_timings *data = (struct vki_v4l2_dv_timings *)ARG3;
9834 POST_MEM_WRITE((Addr)data, sizeof(*data));
9835 break;
9837 case VKI_V4L2_DQEVENT: {
9838 struct vki_v4l2_event *data = (struct vki_v4l2_event *)ARG3;
9839 POST_MEM_WRITE((Addr)data, sizeof(*data));
9840 break;
9842 case VKI_V4L2_CREATE_BUFS: {
9843 struct vki_v4l2_create_buffers *data = (struct vki_v4l2_create_buffers *)ARG3;
9844 POST_FIELD_WRITE(data->index);
9845 break;
9847 case VKI_V4L2_G_SELECTION: {
9848 struct vki_v4l2_selection *data = (struct vki_v4l2_selection *)ARG3;
9849 POST_FIELD_WRITE(data->r);
9850 break;
9852 case VKI_V4L2_S_SELECTION: {
9853 struct vki_v4l2_selection *data = (struct vki_v4l2_selection *)ARG3;
9854 POST_FIELD_WRITE(data->r);
9855 break;
9857 case VKI_V4L2_DECODER_CMD: {
9858 struct vki_v4l2_decoder_cmd *data = (struct vki_v4l2_decoder_cmd *)ARG3;
9859 POST_FIELD_WRITE(data->flags);
9860 break;
9862 case VKI_V4L2_TRY_DECODER_CMD: {
9863 struct vki_v4l2_decoder_cmd *data = (struct vki_v4l2_decoder_cmd *)ARG3;
9864 POST_FIELD_WRITE(data->flags);
9865 break;
9867 case VKI_V4L2_ENUM_DV_TIMINGS: {
9868 struct vki_v4l2_enum_dv_timings *data = (struct vki_v4l2_enum_dv_timings *)ARG3;
9869 POST_FIELD_WRITE(data->timings);
9870 break;
9872 case VKI_V4L2_QUERY_DV_TIMINGS: {
9873 struct vki_v4l2_dv_timings *data = (struct vki_v4l2_dv_timings *)ARG3;
9874 POST_MEM_WRITE((Addr)data, sizeof(*data));
9875 break;
9877 case VKI_V4L2_DV_TIMINGS_CAP: {
9878 struct vki_v4l2_dv_timings_cap *data = (struct vki_v4l2_dv_timings_cap *)ARG3;
9879 POST_MEM_WRITE((Addr)data, sizeof(*data));
9880 break;
9882 case VKI_V4L2_ENUM_FREQ_BANDS: {
9883 struct vki_v4l2_frequency_band *data = (struct vki_v4l2_frequency_band *)ARG3;
9884 POST_FIELD_WRITE(data->capability);
9885 POST_FIELD_WRITE(data->rangelow);
9886 POST_FIELD_WRITE(data->rangehigh);
9887 POST_FIELD_WRITE(data->modulation);
9888 break;
9890 case VKI_V4L2_DBG_G_CHIP_INFO: {
9891 struct vki_v4l2_dbg_chip_info *data = (struct vki_v4l2_dbg_chip_info *)ARG3;
9892 POST_FIELD_WRITE(data->name);
9893 POST_FIELD_WRITE(data->flags);
9894 break;
9896 case VKI_V4L2_QUERY_EXT_CTRL: {
9897 struct vki_v4l2_query_ext_ctrl *data = (struct vki_v4l2_query_ext_ctrl *)ARG3;
9898 POST_MEM_WRITE((Addr)&data->type,
9899 sizeof(*data) - sizeof(data->id) - sizeof(data->reserved));
9900 break;
9903 case VKI_V4L2_SUBDEV_S_FMT:
9904 case VKI_V4L2_SUBDEV_S_FRAME_INTERVAL:
9905 case VKI_V4L2_SUBDEV_S_CROP:
9906 case VKI_V4L2_SUBDEV_S_SELECTION:
9907 break;
9909 case VKI_V4L2_SUBDEV_G_FMT: {
9910 struct vki_v4l2_subdev_format *data = (struct vki_v4l2_subdev_format *)ARG3;
9911 POST_FIELD_WRITE(data->format);
9912 break;
9914 case VKI_V4L2_SUBDEV_G_FRAME_INTERVAL: {
9915 struct vki_v4l2_subdev_frame_interval *data = (struct vki_v4l2_subdev_frame_interval *)ARG3;
9916 POST_FIELD_WRITE(data->interval);
9917 break;
9919 case VKI_V4L2_SUBDEV_ENUM_MBUS_CODE: {
9920 struct vki_v4l2_subdev_mbus_code_enum *data = (struct vki_v4l2_subdev_mbus_code_enum *)ARG3;
9921 POST_FIELD_WRITE(data->code);
9922 break;
9924 case VKI_V4L2_SUBDEV_ENUM_FRAME_SIZE: {
9925 struct vki_v4l2_subdev_frame_size_enum *data = (struct vki_v4l2_subdev_frame_size_enum *)ARG3;
9926 POST_FIELD_WRITE(data->min_width);
9927 POST_FIELD_WRITE(data->min_height);
9928 POST_FIELD_WRITE(data->max_width);
9929 POST_FIELD_WRITE(data->max_height);
9930 break;
9932 case VKI_V4L2_SUBDEV_ENUM_FRAME_INTERVAL: {
9933 struct vki_v4l2_subdev_frame_interval_enum *data = (struct vki_v4l2_subdev_frame_interval_enum *)ARG3;
9934 POST_FIELD_WRITE(data->interval);
9935 break;
9937 case VKI_V4L2_SUBDEV_G_CROP: {
9938 struct vki_v4l2_subdev_crop *data = (struct vki_v4l2_subdev_crop *)ARG3;
9939 POST_FIELD_WRITE(data->rect);
9940 break;
9942 case VKI_V4L2_SUBDEV_G_SELECTION: {
9943 struct vki_v4l2_subdev_selection *data = (struct vki_v4l2_subdev_selection *)ARG3;
9944 POST_FIELD_WRITE(data->r);
9945 break;
9947 case VKI_MEDIA_IOC_DEVICE_INFO: {
9948 struct vki_media_device_info *data = (struct vki_media_device_info *)ARG3;
9949 POST_MEM_WRITE((Addr)data, sizeof(*data) - sizeof(data->reserved));
9950 break;
9952 case VKI_MEDIA_IOC_ENUM_ENTITIES: {
9953 struct vki_media_entity_desc *data = (struct vki_media_entity_desc *)ARG3;
9954 POST_MEM_WRITE((Addr)data->name, sizeof(*data) - sizeof(data->id));
9955 break;
9957 case VKI_MEDIA_IOC_ENUM_LINKS:
9959 * This ioctl does write to the provided pointers, but it's not
9960 * possible to deduce the size of the array those pointers point to.
9962 break;
9963 case VKI_MEDIA_IOC_SETUP_LINK:
9964 break;
9966 default:
9967 /* EVIOC* are variable length and return size written on success */
9968 switch (ARG2 & ~(_VKI_IOC_SIZEMASK << _VKI_IOC_SIZESHIFT)) {
9969 case VKI_EVIOCGNAME(0):
9970 case VKI_EVIOCGPHYS(0):
9971 case VKI_EVIOCGUNIQ(0):
9972 case VKI_EVIOCGKEY(0):
9973 case VKI_EVIOCGLED(0):
9974 case VKI_EVIOCGSND(0):
9975 case VKI_EVIOCGSW(0):
9976 case VKI_EVIOCGBIT(VKI_EV_SYN,0):
9977 case VKI_EVIOCGBIT(VKI_EV_KEY,0):
9978 case VKI_EVIOCGBIT(VKI_EV_REL,0):
9979 case VKI_EVIOCGBIT(VKI_EV_ABS,0):
9980 case VKI_EVIOCGBIT(VKI_EV_MSC,0):
9981 case VKI_EVIOCGBIT(VKI_EV_SW,0):
9982 case VKI_EVIOCGBIT(VKI_EV_LED,0):
9983 case VKI_EVIOCGBIT(VKI_EV_SND,0):
9984 case VKI_EVIOCGBIT(VKI_EV_REP,0):
9985 case VKI_EVIOCGBIT(VKI_EV_FF,0):
9986 case VKI_EVIOCGBIT(VKI_EV_PWR,0):
9987 case VKI_EVIOCGBIT(VKI_EV_FF_STATUS,0):
9988 if (RES > 0)
9989 POST_MEM_WRITE(ARG3, RES);
9990 break;
9991 default:
9992 ML_(POST_unknown_ioctl)(tid, RES, ARG2, ARG3);
9993 break;
9995 break;
9998 post_sys_ioctl__out:
9999 {} /* keep C compilers happy */
10002 /* ---------------------------------------------------------------------
10003 socketcall wrapper helpers
10004 ------------------------------------------------------------------ */
10006 void
10007 ML_(linux_PRE_sys_getsockopt) ( ThreadId tid,
10008 UWord arg0, UWord arg1, UWord arg2,
10009 UWord arg3, UWord arg4 )
10011 /* int getsockopt(int s, int level, int optname,
10012 void *optval, socklen_t *optlen); */
10013 Addr optval_p = arg3;
10014 Addr optlen_p = arg4;
10015 /* vg_assert(sizeof(socklen_t) == sizeof(UInt)); */
10016 if (optval_p != (Addr)NULL) {
10017 ML_(buf_and_len_pre_check) ( tid, optval_p, optlen_p,
10018 "socketcall.getsockopt(optval)",
10019 "socketcall.getsockopt(optlen)" );
10020 if (arg1 == VKI_SOL_SCTP &&
10021 (arg2 == VKI_SCTP_GET_PEER_ADDRS ||
10022 arg2 == VKI_SCTP_GET_LOCAL_ADDRS))
10024 struct vki_sctp_getaddrs *ga = (struct vki_sctp_getaddrs*)arg3;
10025 int address_bytes = sizeof(struct vki_sockaddr_in6) * ga->addr_num;
10026 PRE_MEM_WRITE( "socketcall.getsockopt(optval.addrs)",
10027 (Addr)ga->addrs, address_bytes );
10032 void
10033 ML_(linux_POST_sys_getsockopt) ( ThreadId tid,
10034 SysRes res,
10035 UWord arg0, UWord arg1, UWord arg2,
10036 UWord arg3, UWord arg4 )
10038 Addr optval_p = arg3;
10039 Addr optlen_p = arg4;
10040 vg_assert(!sr_isError(res)); /* guaranteed by caller */
10041 if (optval_p != (Addr)NULL) {
10042 ML_(buf_and_len_post_check) ( tid, res, optval_p, optlen_p,
10043 "socketcall.getsockopt(optlen_out)" );
10044 if (arg1 == VKI_SOL_SCTP &&
10045 (arg2 == VKI_SCTP_GET_PEER_ADDRS ||
10046 arg2 == VKI_SCTP_GET_LOCAL_ADDRS))
10048 struct vki_sctp_getaddrs *ga = (struct vki_sctp_getaddrs*)arg3;
10049 struct vki_sockaddr *a = ga->addrs;
10050 int i;
10051 for (i = 0; i < ga->addr_num; i++) {
10052 int sl = 0;
10053 if (a->sa_family == VKI_AF_INET)
10054 sl = sizeof(struct vki_sockaddr_in);
10055 else if (a->sa_family == VKI_AF_INET6)
10056 sl = sizeof(struct vki_sockaddr_in6);
10057 else {
10058 VG_(message)(Vg_UserMsg, "Warning: getsockopt: unhandled "
10059 "address type %d\n", a->sa_family);
10061 a = (struct vki_sockaddr*)((char*)a + sl);
10063 POST_MEM_WRITE( (Addr)ga->addrs, (char*)a - (char*)ga->addrs );
10068 void
10069 ML_(linux_PRE_sys_setsockopt) ( ThreadId tid,
10070 UWord arg0, UWord arg1, UWord arg2,
10071 UWord arg3, UWord arg4 )
10073 /* int setsockopt(int s, int level, int optname,
10074 const void *optval, socklen_t optlen); */
10075 Addr optval_p = arg3;
10076 if (optval_p != (Addr)NULL) {
10078 * OK, let's handle at least some setsockopt levels and options
10079 * ourselves, so we don't get false claims of references to
10080 * uninitialized memory (such as padding in structures) and *do*
10081 * check what pointers in the argument point to.
10083 if (arg1 == VKI_SOL_SOCKET && arg2 == VKI_SO_ATTACH_FILTER)
10085 struct vki_sock_fprog *fp = (struct vki_sock_fprog *)optval_p;
10088 * struct sock_fprog has a 16-bit count of instructions,
10089 * followed by a pointer to an array of those instructions.
10090 * There's padding between those two elements.
10092 * So that we don't bogusly complain about the padding bytes,
10093 * we just report that we read len and and filter.
10095 * We then make sure that what filter points to is valid.
10097 PRE_MEM_READ( "setsockopt(SOL_SOCKET, SO_ATTACH_FILTER, &optval.len)",
10098 (Addr)&fp->len, sizeof(fp->len) );
10099 PRE_MEM_READ( "setsockopt(SOL_SOCKET, SO_ATTACH_FILTER, &optval.filter)",
10100 (Addr)&fp->filter, sizeof(fp->filter) );
10102 /* len * sizeof (*filter) */
10103 if (fp->filter != NULL)
10105 PRE_MEM_READ( "setsockopt(SOL_SOCKET, SO_ATTACH_FILTER, optval.filter)",
10106 (Addr)(fp->filter),
10107 fp->len * sizeof(*fp->filter) );
10110 else
10112 PRE_MEM_READ( "socketcall.setsockopt(optval)",
10113 arg3, /* optval */
10114 arg4 /* optlen */ );
10119 /* ---------------------------------------------------------------------
10120 ptrace wrapper helpers
10121 ------------------------------------------------------------------ */
10123 void
10124 ML_(linux_PRE_getregset) ( ThreadId tid, long arg3, long arg4 )
10126 struct vki_iovec *iov = (struct vki_iovec *) arg4;
10128 PRE_MEM_READ("ptrace(getregset iovec->iov_base)",
10129 (unsigned long) &iov->iov_base, sizeof(iov->iov_base));
10130 PRE_MEM_READ("ptrace(getregset iovec->iov_len)",
10131 (unsigned long) &iov->iov_len, sizeof(iov->iov_len));
10132 PRE_MEM_WRITE("ptrace(getregset *(iovec->iov_base))",
10133 (unsigned long) iov->iov_base, iov->iov_len);
10136 void
10137 ML_(linux_PRE_setregset) ( ThreadId tid, long arg3, long arg4 )
10139 struct vki_iovec *iov = (struct vki_iovec *) arg4;
10141 PRE_MEM_READ("ptrace(setregset iovec->iov_base)",
10142 (unsigned long) &iov->iov_base, sizeof(iov->iov_base));
10143 PRE_MEM_READ("ptrace(setregset iovec->iov_len)",
10144 (unsigned long) &iov->iov_len, sizeof(iov->iov_len));
10145 PRE_MEM_READ("ptrace(setregset *(iovec->iov_base))",
10146 (unsigned long) iov->iov_base, iov->iov_len);
10149 void
10150 ML_(linux_POST_getregset) ( ThreadId tid, long arg3, long arg4 )
10152 struct vki_iovec *iov = (struct vki_iovec *) arg4;
10154 /* XXX: The actual amount of data written by the kernel might be
10155 less than iov_len, depending on the regset (arg3). */
10156 POST_MEM_WRITE((unsigned long) iov->iov_base, iov->iov_len);
10159 PRE(sys_kcmp)
10161 PRINT("kcmp ( %ld, %ld, %ld, %lu, %lu )", ARG1, ARG2, ARG3, ARG4, ARG5);
10162 switch (ARG3) {
10163 case VKI_KCMP_VM: case VKI_KCMP_FILES: case VKI_KCMP_FS:
10164 case VKI_KCMP_SIGHAND: case VKI_KCMP_IO: case VKI_KCMP_SYSVSEM:
10165 /* Most of the comparison types don't look at |idx1| or
10166 |idx2|. */
10167 PRE_REG_READ3(long, "kcmp",
10168 vki_pid_t, pid1, vki_pid_t, pid2, int, type);
10169 break;
10170 case VKI_KCMP_FILE:
10171 default:
10172 PRE_REG_READ5(long, "kcmp",
10173 vki_pid_t, pid1, vki_pid_t, pid2, int, type,
10174 unsigned long, idx1, unsigned long, idx2);
10175 break;
10179 #undef PRE
10180 #undef POST
10182 #endif // defined(VGO_linux)
10184 /*--------------------------------------------------------------------*/
10185 /*--- end ---*/
10186 /*--------------------------------------------------------------------*/