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