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