xref: /openbmc/qemu/linux-user/syscall.c (revision dfc080791dfb9dd8907a15e6d45b6cc4969b986f)
1 /*
2  *  Linux syscalls
3  *
4  *  Copyright (c) 2003 Fabrice Bellard
5  *
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 2 of the License, or
9  *  (at your option) any later version.
10  *
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *
16  *  You should have received a copy of the GNU General Public License
17  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
18  */
19 #define _ATFILE_SOURCE
20 #include <stdlib.h>
21 #include <stdio.h>
22 #include <stdarg.h>
23 #include <string.h>
24 #include <elf.h>
25 #include <endian.h>
26 #include <errno.h>
27 #include <unistd.h>
28 #include <fcntl.h>
29 #include <time.h>
30 #include <limits.h>
31 #include <grp.h>
32 #include <sys/types.h>
33 #include <sys/ipc.h>
34 #include <sys/msg.h>
35 #include <sys/wait.h>
36 #include <sys/time.h>
37 #include <sys/stat.h>
38 #include <sys/mount.h>
39 #include <sys/file.h>
40 #include <sys/fsuid.h>
41 #include <sys/personality.h>
42 #include <sys/prctl.h>
43 #include <sys/resource.h>
44 #include <sys/mman.h>
45 #include <sys/swap.h>
46 #include <signal.h>
47 #include <sched.h>
48 #ifdef __ia64__
49 int __clone2(int (*fn)(void *), void *child_stack_base,
50              size_t stack_size, int flags, void *arg, ...);
51 #endif
52 #include <sys/socket.h>
53 #include <sys/un.h>
54 #include <sys/uio.h>
55 #include <sys/poll.h>
56 #include <sys/times.h>
57 #include <sys/shm.h>
58 #include <sys/sem.h>
59 #include <sys/statfs.h>
60 #include <utime.h>
61 #include <sys/sysinfo.h>
62 #include <sys/utsname.h>
63 //#include <sys/user.h>
64 #include <netinet/ip.h>
65 #include <netinet/tcp.h>
66 #include <linux/wireless.h>
67 #include <linux/icmp.h>
68 #include "qemu-common.h"
69 #ifdef TARGET_GPROF
70 #include <sys/gmon.h>
71 #endif
72 #ifdef CONFIG_EVENTFD
73 #include <sys/eventfd.h>
74 #endif
75 #ifdef CONFIG_EPOLL
76 #include <sys/epoll.h>
77 #endif
78 #ifdef CONFIG_ATTR
79 #include "qemu/xattr.h"
80 #endif
81 #ifdef CONFIG_SENDFILE
82 #include <sys/sendfile.h>
83 #endif
84 
85 #define termios host_termios
86 #define winsize host_winsize
87 #define termio host_termio
88 #define sgttyb host_sgttyb /* same as target */
89 #define tchars host_tchars /* same as target */
90 #define ltchars host_ltchars /* same as target */
91 
92 #include <linux/termios.h>
93 #include <linux/unistd.h>
94 #include <linux/utsname.h>
95 #include <linux/cdrom.h>
96 #include <linux/hdreg.h>
97 #include <linux/soundcard.h>
98 #include <linux/kd.h>
99 #include <linux/mtio.h>
100 #include <linux/fs.h>
101 #if defined(CONFIG_FIEMAP)
102 #include <linux/fiemap.h>
103 #endif
104 #include <linux/fb.h>
105 #include <linux/vt.h>
106 #include <linux/dm-ioctl.h>
107 #include <linux/reboot.h>
108 #include "linux_loop.h"
109 #include "cpu-uname.h"
110 
111 #include "qemu.h"
112 
113 #if defined(CONFIG_USE_NPTL)
114 #define CLONE_NPTL_FLAGS2 (CLONE_SETTLS | \
115     CLONE_PARENT_SETTID | CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID)
116 #else
117 /* XXX: Hardcode the above values.  */
118 #define CLONE_NPTL_FLAGS2 0
119 #endif
120 
121 //#define DEBUG
122 
123 //#include <linux/msdos_fs.h>
124 #define	VFAT_IOCTL_READDIR_BOTH		_IOR('r', 1, struct linux_dirent [2])
125 #define	VFAT_IOCTL_READDIR_SHORT	_IOR('r', 2, struct linux_dirent [2])
126 
127 
128 #undef _syscall0
129 #undef _syscall1
130 #undef _syscall2
131 #undef _syscall3
132 #undef _syscall4
133 #undef _syscall5
134 #undef _syscall6
135 
136 #define _syscall0(type,name)		\
137 static type name (void)			\
138 {					\
139 	return syscall(__NR_##name);	\
140 }
141 
142 #define _syscall1(type,name,type1,arg1)		\
143 static type name (type1 arg1)			\
144 {						\
145 	return syscall(__NR_##name, arg1);	\
146 }
147 
148 #define _syscall2(type,name,type1,arg1,type2,arg2)	\
149 static type name (type1 arg1,type2 arg2)		\
150 {							\
151 	return syscall(__NR_##name, arg1, arg2);	\
152 }
153 
154 #define _syscall3(type,name,type1,arg1,type2,arg2,type3,arg3)	\
155 static type name (type1 arg1,type2 arg2,type3 arg3)		\
156 {								\
157 	return syscall(__NR_##name, arg1, arg2, arg3);		\
158 }
159 
160 #define _syscall4(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4)	\
161 static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4)			\
162 {										\
163 	return syscall(__NR_##name, arg1, arg2, arg3, arg4);			\
164 }
165 
166 #define _syscall5(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4,	\
167 		  type5,arg5)							\
168 static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5)	\
169 {										\
170 	return syscall(__NR_##name, arg1, arg2, arg3, arg4, arg5);		\
171 }
172 
173 
174 #define _syscall6(type,name,type1,arg1,type2,arg2,type3,arg3,type4,arg4,	\
175 		  type5,arg5,type6,arg6)					\
176 static type name (type1 arg1,type2 arg2,type3 arg3,type4 arg4,type5 arg5,	\
177                   type6 arg6)							\
178 {										\
179 	return syscall(__NR_##name, arg1, arg2, arg3, arg4, arg5, arg6);	\
180 }
181 
182 
183 #define __NR_sys_uname __NR_uname
184 #define __NR_sys_getcwd1 __NR_getcwd
185 #define __NR_sys_getdents __NR_getdents
186 #define __NR_sys_getdents64 __NR_getdents64
187 #define __NR_sys_getpriority __NR_getpriority
188 #define __NR_sys_rt_sigqueueinfo __NR_rt_sigqueueinfo
189 #define __NR_sys_syslog __NR_syslog
190 #define __NR_sys_tgkill __NR_tgkill
191 #define __NR_sys_tkill __NR_tkill
192 #define __NR_sys_futex __NR_futex
193 #define __NR_sys_inotify_init __NR_inotify_init
194 #define __NR_sys_inotify_add_watch __NR_inotify_add_watch
195 #define __NR_sys_inotify_rm_watch __NR_inotify_rm_watch
196 
197 #if defined(__alpha__) || defined (__ia64__) || defined(__x86_64__) || \
198     defined(__s390x__)
199 #define __NR__llseek __NR_lseek
200 #endif
201 
202 #ifdef __NR_gettid
203 _syscall0(int, gettid)
204 #else
205 /* This is a replacement for the host gettid() and must return a host
206    errno. */
207 static int gettid(void) {
208     return -ENOSYS;
209 }
210 #endif
211 #ifdef __NR_getdents
212 _syscall3(int, sys_getdents, uint, fd, struct linux_dirent *, dirp, uint, count);
213 #endif
214 #if !defined(__NR_getdents) || \
215     (defined(TARGET_NR_getdents64) && defined(__NR_getdents64))
216 _syscall3(int, sys_getdents64, uint, fd, struct linux_dirent64 *, dirp, uint, count);
217 #endif
218 #if defined(TARGET_NR__llseek) && defined(__NR_llseek)
219 _syscall5(int, _llseek,  uint,  fd, ulong, hi, ulong, lo,
220           loff_t *, res, uint, wh);
221 #endif
222 _syscall3(int,sys_rt_sigqueueinfo,int,pid,int,sig,siginfo_t *,uinfo)
223 _syscall3(int,sys_syslog,int,type,char*,bufp,int,len)
224 #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
225 _syscall3(int,sys_tgkill,int,tgid,int,pid,int,sig)
226 #endif
227 #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
228 _syscall2(int,sys_tkill,int,tid,int,sig)
229 #endif
230 #ifdef __NR_exit_group
231 _syscall1(int,exit_group,int,error_code)
232 #endif
233 #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
234 _syscall1(int,set_tid_address,int *,tidptr)
235 #endif
236 #if defined(CONFIG_USE_NPTL)
237 #if defined(TARGET_NR_futex) && defined(__NR_futex)
238 _syscall6(int,sys_futex,int *,uaddr,int,op,int,val,
239           const struct timespec *,timeout,int *,uaddr2,int,val3)
240 #endif
241 #endif
242 #define __NR_sys_sched_getaffinity __NR_sched_getaffinity
243 _syscall3(int, sys_sched_getaffinity, pid_t, pid, unsigned int, len,
244           unsigned long *, user_mask_ptr);
245 #define __NR_sys_sched_setaffinity __NR_sched_setaffinity
246 _syscall3(int, sys_sched_setaffinity, pid_t, pid, unsigned int, len,
247           unsigned long *, user_mask_ptr);
248 _syscall4(int, reboot, int, magic1, int, magic2, unsigned int, cmd,
249           void *, arg);
250 
251 static bitmask_transtbl fcntl_flags_tbl[] = {
252   { TARGET_O_ACCMODE,   TARGET_O_WRONLY,    O_ACCMODE,   O_WRONLY,    },
253   { TARGET_O_ACCMODE,   TARGET_O_RDWR,      O_ACCMODE,   O_RDWR,      },
254   { TARGET_O_CREAT,     TARGET_O_CREAT,     O_CREAT,     O_CREAT,     },
255   { TARGET_O_EXCL,      TARGET_O_EXCL,      O_EXCL,      O_EXCL,      },
256   { TARGET_O_NOCTTY,    TARGET_O_NOCTTY,    O_NOCTTY,    O_NOCTTY,    },
257   { TARGET_O_TRUNC,     TARGET_O_TRUNC,     O_TRUNC,     O_TRUNC,     },
258   { TARGET_O_APPEND,    TARGET_O_APPEND,    O_APPEND,    O_APPEND,    },
259   { TARGET_O_NONBLOCK,  TARGET_O_NONBLOCK,  O_NONBLOCK,  O_NONBLOCK,  },
260   { TARGET_O_SYNC,      TARGET_O_DSYNC,     O_SYNC,      O_DSYNC,     },
261   { TARGET_O_SYNC,      TARGET_O_SYNC,      O_SYNC,      O_SYNC,      },
262   { TARGET_FASYNC,      TARGET_FASYNC,      FASYNC,      FASYNC,      },
263   { TARGET_O_DIRECTORY, TARGET_O_DIRECTORY, O_DIRECTORY, O_DIRECTORY, },
264   { TARGET_O_NOFOLLOW,  TARGET_O_NOFOLLOW,  O_NOFOLLOW,  O_NOFOLLOW,  },
265 #if defined(O_DIRECT)
266   { TARGET_O_DIRECT,    TARGET_O_DIRECT,    O_DIRECT,    O_DIRECT,    },
267 #endif
268 #if defined(O_NOATIME)
269   { TARGET_O_NOATIME,   TARGET_O_NOATIME,   O_NOATIME,   O_NOATIME    },
270 #endif
271 #if defined(O_CLOEXEC)
272   { TARGET_O_CLOEXEC,   TARGET_O_CLOEXEC,   O_CLOEXEC,   O_CLOEXEC    },
273 #endif
274 #if defined(O_PATH)
275   { TARGET_O_PATH,      TARGET_O_PATH,      O_PATH,      O_PATH       },
276 #endif
277   /* Don't terminate the list prematurely on 64-bit host+guest.  */
278 #if TARGET_O_LARGEFILE != 0 || O_LARGEFILE != 0
279   { TARGET_O_LARGEFILE, TARGET_O_LARGEFILE, O_LARGEFILE, O_LARGEFILE, },
280 #endif
281   { 0, 0, 0, 0 }
282 };
283 
284 #define COPY_UTSNAME_FIELD(dest, src) \
285   do { \
286       /* __NEW_UTS_LEN doesn't include terminating null */ \
287       (void) strncpy((dest), (src), __NEW_UTS_LEN); \
288       (dest)[__NEW_UTS_LEN] = '\0'; \
289   } while (0)
290 
291 static int sys_uname(struct new_utsname *buf)
292 {
293   struct utsname uts_buf;
294 
295   if (uname(&uts_buf) < 0)
296       return (-1);
297 
298   /*
299    * Just in case these have some differences, we
300    * translate utsname to new_utsname (which is the
301    * struct linux kernel uses).
302    */
303 
304   memset(buf, 0, sizeof(*buf));
305   COPY_UTSNAME_FIELD(buf->sysname, uts_buf.sysname);
306   COPY_UTSNAME_FIELD(buf->nodename, uts_buf.nodename);
307   COPY_UTSNAME_FIELD(buf->release, uts_buf.release);
308   COPY_UTSNAME_FIELD(buf->version, uts_buf.version);
309   COPY_UTSNAME_FIELD(buf->machine, uts_buf.machine);
310 #ifdef _GNU_SOURCE
311   COPY_UTSNAME_FIELD(buf->domainname, uts_buf.domainname);
312 #endif
313   return (0);
314 
315 #undef COPY_UTSNAME_FIELD
316 }
317 
318 static int sys_getcwd1(char *buf, size_t size)
319 {
320   if (getcwd(buf, size) == NULL) {
321       /* getcwd() sets errno */
322       return (-1);
323   }
324   return strlen(buf)+1;
325 }
326 
327 #ifdef TARGET_NR_openat
328 static int sys_openat(int dirfd, const char *pathname, int flags, mode_t mode)
329 {
330   /*
331    * open(2) has extra parameter 'mode' when called with
332    * flag O_CREAT.
333    */
334   if ((flags & O_CREAT) != 0) {
335       return (openat(dirfd, pathname, flags, mode));
336   }
337   return (openat(dirfd, pathname, flags));
338 }
339 #endif
340 
341 #ifdef CONFIG_UTIMENSAT
342 static int sys_utimensat(int dirfd, const char *pathname,
343     const struct timespec times[2], int flags)
344 {
345     if (pathname == NULL)
346         return futimens(dirfd, times);
347     else
348         return utimensat(dirfd, pathname, times, flags);
349 }
350 #else
351 #if defined(TARGET_NR_utimensat) && defined(__NR_utimensat)
352 _syscall4(int,sys_utimensat,int,dirfd,const char *,pathname,
353           const struct timespec *,tsp,int,flags)
354 #endif
355 #endif /* CONFIG_UTIMENSAT  */
356 
357 #ifdef CONFIG_INOTIFY
358 #include <sys/inotify.h>
359 
360 #if defined(TARGET_NR_inotify_init) && defined(__NR_inotify_init)
361 static int sys_inotify_init(void)
362 {
363   return (inotify_init());
364 }
365 #endif
366 #if defined(TARGET_NR_inotify_add_watch) && defined(__NR_inotify_add_watch)
367 static int sys_inotify_add_watch(int fd,const char *pathname, int32_t mask)
368 {
369   return (inotify_add_watch(fd, pathname, mask));
370 }
371 #endif
372 #if defined(TARGET_NR_inotify_rm_watch) && defined(__NR_inotify_rm_watch)
373 static int sys_inotify_rm_watch(int fd, int32_t wd)
374 {
375   return (inotify_rm_watch(fd, wd));
376 }
377 #endif
378 #ifdef CONFIG_INOTIFY1
379 #if defined(TARGET_NR_inotify_init1) && defined(__NR_inotify_init1)
380 static int sys_inotify_init1(int flags)
381 {
382   return (inotify_init1(flags));
383 }
384 #endif
385 #endif
386 #else
387 /* Userspace can usually survive runtime without inotify */
388 #undef TARGET_NR_inotify_init
389 #undef TARGET_NR_inotify_init1
390 #undef TARGET_NR_inotify_add_watch
391 #undef TARGET_NR_inotify_rm_watch
392 #endif /* CONFIG_INOTIFY  */
393 
394 #if defined(TARGET_NR_ppoll)
395 #ifndef __NR_ppoll
396 # define __NR_ppoll -1
397 #endif
398 #define __NR_sys_ppoll __NR_ppoll
399 _syscall5(int, sys_ppoll, struct pollfd *, fds, nfds_t, nfds,
400           struct timespec *, timeout, const __sigset_t *, sigmask,
401           size_t, sigsetsize)
402 #endif
403 
404 #if defined(TARGET_NR_pselect6)
405 #ifndef __NR_pselect6
406 # define __NR_pselect6 -1
407 #endif
408 #define __NR_sys_pselect6 __NR_pselect6
409 _syscall6(int, sys_pselect6, int, nfds, fd_set *, readfds, fd_set *, writefds,
410           fd_set *, exceptfds, struct timespec *, timeout, void *, sig);
411 #endif
412 
413 #if defined(TARGET_NR_prlimit64)
414 #ifndef __NR_prlimit64
415 # define __NR_prlimit64 -1
416 #endif
417 #define __NR_sys_prlimit64 __NR_prlimit64
418 /* The glibc rlimit structure may not be that used by the underlying syscall */
419 struct host_rlimit64 {
420     uint64_t rlim_cur;
421     uint64_t rlim_max;
422 };
423 _syscall4(int, sys_prlimit64, pid_t, pid, int, resource,
424           const struct host_rlimit64 *, new_limit,
425           struct host_rlimit64 *, old_limit)
426 #endif
427 
428 /* ARM EABI and MIPS expect 64bit types aligned even on pairs or registers */
429 #ifdef TARGET_ARM
430 static inline int regpairs_aligned(void *cpu_env) {
431     return ((((CPUARMState *)cpu_env)->eabi) == 1) ;
432 }
433 #elif defined(TARGET_MIPS)
434 static inline int regpairs_aligned(void *cpu_env) { return 1; }
435 #elif defined(TARGET_PPC) && !defined(TARGET_PPC64)
436 /* SysV AVI for PPC32 expects 64bit parameters to be passed on odd/even pairs
437  * of registers which translates to the same as ARM/MIPS, because we start with
438  * r3 as arg1 */
439 static inline int regpairs_aligned(void *cpu_env) { return 1; }
440 #else
441 static inline int regpairs_aligned(void *cpu_env) { return 0; }
442 #endif
443 
444 #define ERRNO_TABLE_SIZE 1200
445 
446 /* target_to_host_errno_table[] is initialized from
447  * host_to_target_errno_table[] in syscall_init(). */
448 static uint16_t target_to_host_errno_table[ERRNO_TABLE_SIZE] = {
449 };
450 
451 /*
452  * This list is the union of errno values overridden in asm-<arch>/errno.h
453  * minus the errnos that are not actually generic to all archs.
454  */
455 static uint16_t host_to_target_errno_table[ERRNO_TABLE_SIZE] = {
456     [EIDRM]		= TARGET_EIDRM,
457     [ECHRNG]		= TARGET_ECHRNG,
458     [EL2NSYNC]		= TARGET_EL2NSYNC,
459     [EL3HLT]		= TARGET_EL3HLT,
460     [EL3RST]		= TARGET_EL3RST,
461     [ELNRNG]		= TARGET_ELNRNG,
462     [EUNATCH]		= TARGET_EUNATCH,
463     [ENOCSI]		= TARGET_ENOCSI,
464     [EL2HLT]		= TARGET_EL2HLT,
465     [EDEADLK]		= TARGET_EDEADLK,
466     [ENOLCK]		= TARGET_ENOLCK,
467     [EBADE]		= TARGET_EBADE,
468     [EBADR]		= TARGET_EBADR,
469     [EXFULL]		= TARGET_EXFULL,
470     [ENOANO]		= TARGET_ENOANO,
471     [EBADRQC]		= TARGET_EBADRQC,
472     [EBADSLT]		= TARGET_EBADSLT,
473     [EBFONT]		= TARGET_EBFONT,
474     [ENOSTR]		= TARGET_ENOSTR,
475     [ENODATA]		= TARGET_ENODATA,
476     [ETIME]		= TARGET_ETIME,
477     [ENOSR]		= TARGET_ENOSR,
478     [ENONET]		= TARGET_ENONET,
479     [ENOPKG]		= TARGET_ENOPKG,
480     [EREMOTE]		= TARGET_EREMOTE,
481     [ENOLINK]		= TARGET_ENOLINK,
482     [EADV]		= TARGET_EADV,
483     [ESRMNT]		= TARGET_ESRMNT,
484     [ECOMM]		= TARGET_ECOMM,
485     [EPROTO]		= TARGET_EPROTO,
486     [EDOTDOT]		= TARGET_EDOTDOT,
487     [EMULTIHOP]		= TARGET_EMULTIHOP,
488     [EBADMSG]		= TARGET_EBADMSG,
489     [ENAMETOOLONG]	= TARGET_ENAMETOOLONG,
490     [EOVERFLOW]		= TARGET_EOVERFLOW,
491     [ENOTUNIQ]		= TARGET_ENOTUNIQ,
492     [EBADFD]		= TARGET_EBADFD,
493     [EREMCHG]		= TARGET_EREMCHG,
494     [ELIBACC]		= TARGET_ELIBACC,
495     [ELIBBAD]		= TARGET_ELIBBAD,
496     [ELIBSCN]		= TARGET_ELIBSCN,
497     [ELIBMAX]		= TARGET_ELIBMAX,
498     [ELIBEXEC]		= TARGET_ELIBEXEC,
499     [EILSEQ]		= TARGET_EILSEQ,
500     [ENOSYS]		= TARGET_ENOSYS,
501     [ELOOP]		= TARGET_ELOOP,
502     [ERESTART]		= TARGET_ERESTART,
503     [ESTRPIPE]		= TARGET_ESTRPIPE,
504     [ENOTEMPTY]		= TARGET_ENOTEMPTY,
505     [EUSERS]		= TARGET_EUSERS,
506     [ENOTSOCK]		= TARGET_ENOTSOCK,
507     [EDESTADDRREQ]	= TARGET_EDESTADDRREQ,
508     [EMSGSIZE]		= TARGET_EMSGSIZE,
509     [EPROTOTYPE]	= TARGET_EPROTOTYPE,
510     [ENOPROTOOPT]	= TARGET_ENOPROTOOPT,
511     [EPROTONOSUPPORT]	= TARGET_EPROTONOSUPPORT,
512     [ESOCKTNOSUPPORT]	= TARGET_ESOCKTNOSUPPORT,
513     [EOPNOTSUPP]	= TARGET_EOPNOTSUPP,
514     [EPFNOSUPPORT]	= TARGET_EPFNOSUPPORT,
515     [EAFNOSUPPORT]	= TARGET_EAFNOSUPPORT,
516     [EADDRINUSE]	= TARGET_EADDRINUSE,
517     [EADDRNOTAVAIL]	= TARGET_EADDRNOTAVAIL,
518     [ENETDOWN]		= TARGET_ENETDOWN,
519     [ENETUNREACH]	= TARGET_ENETUNREACH,
520     [ENETRESET]		= TARGET_ENETRESET,
521     [ECONNABORTED]	= TARGET_ECONNABORTED,
522     [ECONNRESET]	= TARGET_ECONNRESET,
523     [ENOBUFS]		= TARGET_ENOBUFS,
524     [EISCONN]		= TARGET_EISCONN,
525     [ENOTCONN]		= TARGET_ENOTCONN,
526     [EUCLEAN]		= TARGET_EUCLEAN,
527     [ENOTNAM]		= TARGET_ENOTNAM,
528     [ENAVAIL]		= TARGET_ENAVAIL,
529     [EISNAM]		= TARGET_EISNAM,
530     [EREMOTEIO]		= TARGET_EREMOTEIO,
531     [ESHUTDOWN]		= TARGET_ESHUTDOWN,
532     [ETOOMANYREFS]	= TARGET_ETOOMANYREFS,
533     [ETIMEDOUT]		= TARGET_ETIMEDOUT,
534     [ECONNREFUSED]	= TARGET_ECONNREFUSED,
535     [EHOSTDOWN]		= TARGET_EHOSTDOWN,
536     [EHOSTUNREACH]	= TARGET_EHOSTUNREACH,
537     [EALREADY]		= TARGET_EALREADY,
538     [EINPROGRESS]	= TARGET_EINPROGRESS,
539     [ESTALE]		= TARGET_ESTALE,
540     [ECANCELED]		= TARGET_ECANCELED,
541     [ENOMEDIUM]		= TARGET_ENOMEDIUM,
542     [EMEDIUMTYPE]	= TARGET_EMEDIUMTYPE,
543 #ifdef ENOKEY
544     [ENOKEY]		= TARGET_ENOKEY,
545 #endif
546 #ifdef EKEYEXPIRED
547     [EKEYEXPIRED]	= TARGET_EKEYEXPIRED,
548 #endif
549 #ifdef EKEYREVOKED
550     [EKEYREVOKED]	= TARGET_EKEYREVOKED,
551 #endif
552 #ifdef EKEYREJECTED
553     [EKEYREJECTED]	= TARGET_EKEYREJECTED,
554 #endif
555 #ifdef EOWNERDEAD
556     [EOWNERDEAD]	= TARGET_EOWNERDEAD,
557 #endif
558 #ifdef ENOTRECOVERABLE
559     [ENOTRECOVERABLE]	= TARGET_ENOTRECOVERABLE,
560 #endif
561 };
562 
563 static inline int host_to_target_errno(int err)
564 {
565     if(host_to_target_errno_table[err])
566         return host_to_target_errno_table[err];
567     return err;
568 }
569 
570 static inline int target_to_host_errno(int err)
571 {
572     if (target_to_host_errno_table[err])
573         return target_to_host_errno_table[err];
574     return err;
575 }
576 
577 static inline abi_long get_errno(abi_long ret)
578 {
579     if (ret == -1)
580         return -host_to_target_errno(errno);
581     else
582         return ret;
583 }
584 
585 static inline int is_error(abi_long ret)
586 {
587     return (abi_ulong)ret >= (abi_ulong)(-4096);
588 }
589 
590 char *target_strerror(int err)
591 {
592     if ((err >= ERRNO_TABLE_SIZE) || (err < 0)) {
593         return NULL;
594     }
595     return strerror(target_to_host_errno(err));
596 }
597 
598 static abi_ulong target_brk;
599 static abi_ulong target_original_brk;
600 static abi_ulong brk_page;
601 
602 void target_set_brk(abi_ulong new_brk)
603 {
604     target_original_brk = target_brk = HOST_PAGE_ALIGN(new_brk);
605     brk_page = HOST_PAGE_ALIGN(target_brk);
606 }
607 
608 //#define DEBUGF_BRK(message, args...) do { fprintf(stderr, (message), ## args); } while (0)
609 #define DEBUGF_BRK(message, args...)
610 
611 /* do_brk() must return target values and target errnos. */
612 abi_long do_brk(abi_ulong new_brk)
613 {
614     abi_long mapped_addr;
615     int	new_alloc_size;
616 
617     DEBUGF_BRK("do_brk(" TARGET_ABI_FMT_lx ") -> ", new_brk);
618 
619     if (!new_brk) {
620         DEBUGF_BRK(TARGET_ABI_FMT_lx " (!new_brk)\n", target_brk);
621         return target_brk;
622     }
623     if (new_brk < target_original_brk) {
624         DEBUGF_BRK(TARGET_ABI_FMT_lx " (new_brk < target_original_brk)\n",
625                    target_brk);
626         return target_brk;
627     }
628 
629     /* If the new brk is less than the highest page reserved to the
630      * target heap allocation, set it and we're almost done...  */
631     if (new_brk <= brk_page) {
632         /* Heap contents are initialized to zero, as for anonymous
633          * mapped pages.  */
634         if (new_brk > target_brk) {
635             memset(g2h(target_brk), 0, new_brk - target_brk);
636         }
637 	target_brk = new_brk;
638         DEBUGF_BRK(TARGET_ABI_FMT_lx " (new_brk <= brk_page)\n", target_brk);
639     	return target_brk;
640     }
641 
642     /* We need to allocate more memory after the brk... Note that
643      * we don't use MAP_FIXED because that will map over the top of
644      * any existing mapping (like the one with the host libc or qemu
645      * itself); instead we treat "mapped but at wrong address" as
646      * a failure and unmap again.
647      */
648     new_alloc_size = HOST_PAGE_ALIGN(new_brk - brk_page);
649     mapped_addr = get_errno(target_mmap(brk_page, new_alloc_size,
650                                         PROT_READ|PROT_WRITE,
651                                         MAP_ANON|MAP_PRIVATE, 0, 0));
652 
653     if (mapped_addr == brk_page) {
654         /* Heap contents are initialized to zero, as for anonymous
655          * mapped pages.  Technically the new pages are already
656          * initialized to zero since they *are* anonymous mapped
657          * pages, however we have to take care with the contents that
658          * come from the remaining part of the previous page: it may
659          * contains garbage data due to a previous heap usage (grown
660          * then shrunken).  */
661         memset(g2h(target_brk), 0, brk_page - target_brk);
662 
663         target_brk = new_brk;
664         brk_page = HOST_PAGE_ALIGN(target_brk);
665         DEBUGF_BRK(TARGET_ABI_FMT_lx " (mapped_addr == brk_page)\n",
666             target_brk);
667         return target_brk;
668     } else if (mapped_addr != -1) {
669         /* Mapped but at wrong address, meaning there wasn't actually
670          * enough space for this brk.
671          */
672         target_munmap(mapped_addr, new_alloc_size);
673         mapped_addr = -1;
674         DEBUGF_BRK(TARGET_ABI_FMT_lx " (mapped_addr != -1)\n", target_brk);
675     }
676     else {
677         DEBUGF_BRK(TARGET_ABI_FMT_lx " (otherwise)\n", target_brk);
678     }
679 
680 #if defined(TARGET_ALPHA)
681     /* We (partially) emulate OSF/1 on Alpha, which requires we
682        return a proper errno, not an unchanged brk value.  */
683     return -TARGET_ENOMEM;
684 #endif
685     /* For everything else, return the previous break. */
686     return target_brk;
687 }
688 
689 static inline abi_long copy_from_user_fdset(fd_set *fds,
690                                             abi_ulong target_fds_addr,
691                                             int n)
692 {
693     int i, nw, j, k;
694     abi_ulong b, *target_fds;
695 
696     nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
697     if (!(target_fds = lock_user(VERIFY_READ,
698                                  target_fds_addr,
699                                  sizeof(abi_ulong) * nw,
700                                  1)))
701         return -TARGET_EFAULT;
702 
703     FD_ZERO(fds);
704     k = 0;
705     for (i = 0; i < nw; i++) {
706         /* grab the abi_ulong */
707         __get_user(b, &target_fds[i]);
708         for (j = 0; j < TARGET_ABI_BITS; j++) {
709             /* check the bit inside the abi_ulong */
710             if ((b >> j) & 1)
711                 FD_SET(k, fds);
712             k++;
713         }
714     }
715 
716     unlock_user(target_fds, target_fds_addr, 0);
717 
718     return 0;
719 }
720 
721 static inline abi_ulong copy_from_user_fdset_ptr(fd_set *fds, fd_set **fds_ptr,
722                                                  abi_ulong target_fds_addr,
723                                                  int n)
724 {
725     if (target_fds_addr) {
726         if (copy_from_user_fdset(fds, target_fds_addr, n))
727             return -TARGET_EFAULT;
728         *fds_ptr = fds;
729     } else {
730         *fds_ptr = NULL;
731     }
732     return 0;
733 }
734 
735 static inline abi_long copy_to_user_fdset(abi_ulong target_fds_addr,
736                                           const fd_set *fds,
737                                           int n)
738 {
739     int i, nw, j, k;
740     abi_long v;
741     abi_ulong *target_fds;
742 
743     nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
744     if (!(target_fds = lock_user(VERIFY_WRITE,
745                                  target_fds_addr,
746                                  sizeof(abi_ulong) * nw,
747                                  0)))
748         return -TARGET_EFAULT;
749 
750     k = 0;
751     for (i = 0; i < nw; i++) {
752         v = 0;
753         for (j = 0; j < TARGET_ABI_BITS; j++) {
754             v |= ((abi_ulong)(FD_ISSET(k, fds) != 0) << j);
755             k++;
756         }
757         __put_user(v, &target_fds[i]);
758     }
759 
760     unlock_user(target_fds, target_fds_addr, sizeof(abi_ulong) * nw);
761 
762     return 0;
763 }
764 
765 #if defined(__alpha__)
766 #define HOST_HZ 1024
767 #else
768 #define HOST_HZ 100
769 #endif
770 
771 static inline abi_long host_to_target_clock_t(long ticks)
772 {
773 #if HOST_HZ == TARGET_HZ
774     return ticks;
775 #else
776     return ((int64_t)ticks * TARGET_HZ) / HOST_HZ;
777 #endif
778 }
779 
780 static inline abi_long host_to_target_rusage(abi_ulong target_addr,
781                                              const struct rusage *rusage)
782 {
783     struct target_rusage *target_rusage;
784 
785     if (!lock_user_struct(VERIFY_WRITE, target_rusage, target_addr, 0))
786         return -TARGET_EFAULT;
787     target_rusage->ru_utime.tv_sec = tswapal(rusage->ru_utime.tv_sec);
788     target_rusage->ru_utime.tv_usec = tswapal(rusage->ru_utime.tv_usec);
789     target_rusage->ru_stime.tv_sec = tswapal(rusage->ru_stime.tv_sec);
790     target_rusage->ru_stime.tv_usec = tswapal(rusage->ru_stime.tv_usec);
791     target_rusage->ru_maxrss = tswapal(rusage->ru_maxrss);
792     target_rusage->ru_ixrss = tswapal(rusage->ru_ixrss);
793     target_rusage->ru_idrss = tswapal(rusage->ru_idrss);
794     target_rusage->ru_isrss = tswapal(rusage->ru_isrss);
795     target_rusage->ru_minflt = tswapal(rusage->ru_minflt);
796     target_rusage->ru_majflt = tswapal(rusage->ru_majflt);
797     target_rusage->ru_nswap = tswapal(rusage->ru_nswap);
798     target_rusage->ru_inblock = tswapal(rusage->ru_inblock);
799     target_rusage->ru_oublock = tswapal(rusage->ru_oublock);
800     target_rusage->ru_msgsnd = tswapal(rusage->ru_msgsnd);
801     target_rusage->ru_msgrcv = tswapal(rusage->ru_msgrcv);
802     target_rusage->ru_nsignals = tswapal(rusage->ru_nsignals);
803     target_rusage->ru_nvcsw = tswapal(rusage->ru_nvcsw);
804     target_rusage->ru_nivcsw = tswapal(rusage->ru_nivcsw);
805     unlock_user_struct(target_rusage, target_addr, 1);
806 
807     return 0;
808 }
809 
810 static inline rlim_t target_to_host_rlim(abi_ulong target_rlim)
811 {
812     abi_ulong target_rlim_swap;
813     rlim_t result;
814 
815     target_rlim_swap = tswapal(target_rlim);
816     if (target_rlim_swap == TARGET_RLIM_INFINITY)
817         return RLIM_INFINITY;
818 
819     result = target_rlim_swap;
820     if (target_rlim_swap != (rlim_t)result)
821         return RLIM_INFINITY;
822 
823     return result;
824 }
825 
826 static inline abi_ulong host_to_target_rlim(rlim_t rlim)
827 {
828     abi_ulong target_rlim_swap;
829     abi_ulong result;
830 
831     if (rlim == RLIM_INFINITY || rlim != (abi_long)rlim)
832         target_rlim_swap = TARGET_RLIM_INFINITY;
833     else
834         target_rlim_swap = rlim;
835     result = tswapal(target_rlim_swap);
836 
837     return result;
838 }
839 
840 static inline int target_to_host_resource(int code)
841 {
842     switch (code) {
843     case TARGET_RLIMIT_AS:
844         return RLIMIT_AS;
845     case TARGET_RLIMIT_CORE:
846         return RLIMIT_CORE;
847     case TARGET_RLIMIT_CPU:
848         return RLIMIT_CPU;
849     case TARGET_RLIMIT_DATA:
850         return RLIMIT_DATA;
851     case TARGET_RLIMIT_FSIZE:
852         return RLIMIT_FSIZE;
853     case TARGET_RLIMIT_LOCKS:
854         return RLIMIT_LOCKS;
855     case TARGET_RLIMIT_MEMLOCK:
856         return RLIMIT_MEMLOCK;
857     case TARGET_RLIMIT_MSGQUEUE:
858         return RLIMIT_MSGQUEUE;
859     case TARGET_RLIMIT_NICE:
860         return RLIMIT_NICE;
861     case TARGET_RLIMIT_NOFILE:
862         return RLIMIT_NOFILE;
863     case TARGET_RLIMIT_NPROC:
864         return RLIMIT_NPROC;
865     case TARGET_RLIMIT_RSS:
866         return RLIMIT_RSS;
867     case TARGET_RLIMIT_RTPRIO:
868         return RLIMIT_RTPRIO;
869     case TARGET_RLIMIT_SIGPENDING:
870         return RLIMIT_SIGPENDING;
871     case TARGET_RLIMIT_STACK:
872         return RLIMIT_STACK;
873     default:
874         return code;
875     }
876 }
877 
878 static inline abi_long copy_from_user_timeval(struct timeval *tv,
879                                               abi_ulong target_tv_addr)
880 {
881     struct target_timeval *target_tv;
882 
883     if (!lock_user_struct(VERIFY_READ, target_tv, target_tv_addr, 1))
884         return -TARGET_EFAULT;
885 
886     __get_user(tv->tv_sec, &target_tv->tv_sec);
887     __get_user(tv->tv_usec, &target_tv->tv_usec);
888 
889     unlock_user_struct(target_tv, target_tv_addr, 0);
890 
891     return 0;
892 }
893 
894 static inline abi_long copy_to_user_timeval(abi_ulong target_tv_addr,
895                                             const struct timeval *tv)
896 {
897     struct target_timeval *target_tv;
898 
899     if (!lock_user_struct(VERIFY_WRITE, target_tv, target_tv_addr, 0))
900         return -TARGET_EFAULT;
901 
902     __put_user(tv->tv_sec, &target_tv->tv_sec);
903     __put_user(tv->tv_usec, &target_tv->tv_usec);
904 
905     unlock_user_struct(target_tv, target_tv_addr, 1);
906 
907     return 0;
908 }
909 
910 #if defined(TARGET_NR_mq_open) && defined(__NR_mq_open)
911 #include <mqueue.h>
912 
913 static inline abi_long copy_from_user_mq_attr(struct mq_attr *attr,
914                                               abi_ulong target_mq_attr_addr)
915 {
916     struct target_mq_attr *target_mq_attr;
917 
918     if (!lock_user_struct(VERIFY_READ, target_mq_attr,
919                           target_mq_attr_addr, 1))
920         return -TARGET_EFAULT;
921 
922     __get_user(attr->mq_flags, &target_mq_attr->mq_flags);
923     __get_user(attr->mq_maxmsg, &target_mq_attr->mq_maxmsg);
924     __get_user(attr->mq_msgsize, &target_mq_attr->mq_msgsize);
925     __get_user(attr->mq_curmsgs, &target_mq_attr->mq_curmsgs);
926 
927     unlock_user_struct(target_mq_attr, target_mq_attr_addr, 0);
928 
929     return 0;
930 }
931 
932 static inline abi_long copy_to_user_mq_attr(abi_ulong target_mq_attr_addr,
933                                             const struct mq_attr *attr)
934 {
935     struct target_mq_attr *target_mq_attr;
936 
937     if (!lock_user_struct(VERIFY_WRITE, target_mq_attr,
938                           target_mq_attr_addr, 0))
939         return -TARGET_EFAULT;
940 
941     __put_user(attr->mq_flags, &target_mq_attr->mq_flags);
942     __put_user(attr->mq_maxmsg, &target_mq_attr->mq_maxmsg);
943     __put_user(attr->mq_msgsize, &target_mq_attr->mq_msgsize);
944     __put_user(attr->mq_curmsgs, &target_mq_attr->mq_curmsgs);
945 
946     unlock_user_struct(target_mq_attr, target_mq_attr_addr, 1);
947 
948     return 0;
949 }
950 #endif
951 
952 #if defined(TARGET_NR_select) || defined(TARGET_NR__newselect)
953 /* do_select() must return target values and target errnos. */
954 static abi_long do_select(int n,
955                           abi_ulong rfd_addr, abi_ulong wfd_addr,
956                           abi_ulong efd_addr, abi_ulong target_tv_addr)
957 {
958     fd_set rfds, wfds, efds;
959     fd_set *rfds_ptr, *wfds_ptr, *efds_ptr;
960     struct timeval tv, *tv_ptr;
961     abi_long ret;
962 
963     ret = copy_from_user_fdset_ptr(&rfds, &rfds_ptr, rfd_addr, n);
964     if (ret) {
965         return ret;
966     }
967     ret = copy_from_user_fdset_ptr(&wfds, &wfds_ptr, wfd_addr, n);
968     if (ret) {
969         return ret;
970     }
971     ret = copy_from_user_fdset_ptr(&efds, &efds_ptr, efd_addr, n);
972     if (ret) {
973         return ret;
974     }
975 
976     if (target_tv_addr) {
977         if (copy_from_user_timeval(&tv, target_tv_addr))
978             return -TARGET_EFAULT;
979         tv_ptr = &tv;
980     } else {
981         tv_ptr = NULL;
982     }
983 
984     ret = get_errno(select(n, rfds_ptr, wfds_ptr, efds_ptr, tv_ptr));
985 
986     if (!is_error(ret)) {
987         if (rfd_addr && copy_to_user_fdset(rfd_addr, &rfds, n))
988             return -TARGET_EFAULT;
989         if (wfd_addr && copy_to_user_fdset(wfd_addr, &wfds, n))
990             return -TARGET_EFAULT;
991         if (efd_addr && copy_to_user_fdset(efd_addr, &efds, n))
992             return -TARGET_EFAULT;
993 
994         if (target_tv_addr && copy_to_user_timeval(target_tv_addr, &tv))
995             return -TARGET_EFAULT;
996     }
997 
998     return ret;
999 }
1000 #endif
1001 
1002 static abi_long do_pipe2(int host_pipe[], int flags)
1003 {
1004 #ifdef CONFIG_PIPE2
1005     return pipe2(host_pipe, flags);
1006 #else
1007     return -ENOSYS;
1008 #endif
1009 }
1010 
1011 static abi_long do_pipe(void *cpu_env, abi_ulong pipedes,
1012                         int flags, int is_pipe2)
1013 {
1014     int host_pipe[2];
1015     abi_long ret;
1016     ret = flags ? do_pipe2(host_pipe, flags) : pipe(host_pipe);
1017 
1018     if (is_error(ret))
1019         return get_errno(ret);
1020 
1021     /* Several targets have special calling conventions for the original
1022        pipe syscall, but didn't replicate this into the pipe2 syscall.  */
1023     if (!is_pipe2) {
1024 #if defined(TARGET_ALPHA)
1025         ((CPUAlphaState *)cpu_env)->ir[IR_A4] = host_pipe[1];
1026         return host_pipe[0];
1027 #elif defined(TARGET_MIPS)
1028         ((CPUMIPSState*)cpu_env)->active_tc.gpr[3] = host_pipe[1];
1029         return host_pipe[0];
1030 #elif defined(TARGET_SH4)
1031         ((CPUSH4State*)cpu_env)->gregs[1] = host_pipe[1];
1032         return host_pipe[0];
1033 #endif
1034     }
1035 
1036     if (put_user_s32(host_pipe[0], pipedes)
1037         || put_user_s32(host_pipe[1], pipedes + sizeof(host_pipe[0])))
1038         return -TARGET_EFAULT;
1039     return get_errno(ret);
1040 }
1041 
1042 static inline abi_long target_to_host_ip_mreq(struct ip_mreqn *mreqn,
1043                                               abi_ulong target_addr,
1044                                               socklen_t len)
1045 {
1046     struct target_ip_mreqn *target_smreqn;
1047 
1048     target_smreqn = lock_user(VERIFY_READ, target_addr, len, 1);
1049     if (!target_smreqn)
1050         return -TARGET_EFAULT;
1051     mreqn->imr_multiaddr.s_addr = target_smreqn->imr_multiaddr.s_addr;
1052     mreqn->imr_address.s_addr = target_smreqn->imr_address.s_addr;
1053     if (len == sizeof(struct target_ip_mreqn))
1054         mreqn->imr_ifindex = tswapal(target_smreqn->imr_ifindex);
1055     unlock_user(target_smreqn, target_addr, 0);
1056 
1057     return 0;
1058 }
1059 
1060 static inline abi_long target_to_host_sockaddr(struct sockaddr *addr,
1061                                                abi_ulong target_addr,
1062                                                socklen_t len)
1063 {
1064     const socklen_t unix_maxlen = sizeof (struct sockaddr_un);
1065     sa_family_t sa_family;
1066     struct target_sockaddr *target_saddr;
1067 
1068     target_saddr = lock_user(VERIFY_READ, target_addr, len, 1);
1069     if (!target_saddr)
1070         return -TARGET_EFAULT;
1071 
1072     sa_family = tswap16(target_saddr->sa_family);
1073 
1074     /* Oops. The caller might send a incomplete sun_path; sun_path
1075      * must be terminated by \0 (see the manual page), but
1076      * unfortunately it is quite common to specify sockaddr_un
1077      * length as "strlen(x->sun_path)" while it should be
1078      * "strlen(...) + 1". We'll fix that here if needed.
1079      * Linux kernel has a similar feature.
1080      */
1081 
1082     if (sa_family == AF_UNIX) {
1083         if (len < unix_maxlen && len > 0) {
1084             char *cp = (char*)target_saddr;
1085 
1086             if ( cp[len-1] && !cp[len] )
1087                 len++;
1088         }
1089         if (len > unix_maxlen)
1090             len = unix_maxlen;
1091     }
1092 
1093     memcpy(addr, target_saddr, len);
1094     addr->sa_family = sa_family;
1095     unlock_user(target_saddr, target_addr, 0);
1096 
1097     return 0;
1098 }
1099 
1100 static inline abi_long host_to_target_sockaddr(abi_ulong target_addr,
1101                                                struct sockaddr *addr,
1102                                                socklen_t len)
1103 {
1104     struct target_sockaddr *target_saddr;
1105 
1106     target_saddr = lock_user(VERIFY_WRITE, target_addr, len, 0);
1107     if (!target_saddr)
1108         return -TARGET_EFAULT;
1109     memcpy(target_saddr, addr, len);
1110     target_saddr->sa_family = tswap16(addr->sa_family);
1111     unlock_user(target_saddr, target_addr, len);
1112 
1113     return 0;
1114 }
1115 
1116 static inline abi_long target_to_host_cmsg(struct msghdr *msgh,
1117                                            struct target_msghdr *target_msgh)
1118 {
1119     struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
1120     abi_long msg_controllen;
1121     abi_ulong target_cmsg_addr;
1122     struct target_cmsghdr *target_cmsg;
1123     socklen_t space = 0;
1124 
1125     msg_controllen = tswapal(target_msgh->msg_controllen);
1126     if (msg_controllen < sizeof (struct target_cmsghdr))
1127         goto the_end;
1128     target_cmsg_addr = tswapal(target_msgh->msg_control);
1129     target_cmsg = lock_user(VERIFY_READ, target_cmsg_addr, msg_controllen, 1);
1130     if (!target_cmsg)
1131         return -TARGET_EFAULT;
1132 
1133     while (cmsg && target_cmsg) {
1134         void *data = CMSG_DATA(cmsg);
1135         void *target_data = TARGET_CMSG_DATA(target_cmsg);
1136 
1137         int len = tswapal(target_cmsg->cmsg_len)
1138                   - TARGET_CMSG_ALIGN(sizeof (struct target_cmsghdr));
1139 
1140         space += CMSG_SPACE(len);
1141         if (space > msgh->msg_controllen) {
1142             space -= CMSG_SPACE(len);
1143             gemu_log("Host cmsg overflow\n");
1144             break;
1145         }
1146 
1147         cmsg->cmsg_level = tswap32(target_cmsg->cmsg_level);
1148         cmsg->cmsg_type = tswap32(target_cmsg->cmsg_type);
1149         cmsg->cmsg_len = CMSG_LEN(len);
1150 
1151         if (cmsg->cmsg_level != TARGET_SOL_SOCKET || cmsg->cmsg_type != SCM_RIGHTS) {
1152             gemu_log("Unsupported ancillary data: %d/%d\n", cmsg->cmsg_level, cmsg->cmsg_type);
1153             memcpy(data, target_data, len);
1154         } else {
1155             int *fd = (int *)data;
1156             int *target_fd = (int *)target_data;
1157             int i, numfds = len / sizeof(int);
1158 
1159             for (i = 0; i < numfds; i++)
1160                 fd[i] = tswap32(target_fd[i]);
1161         }
1162 
1163         cmsg = CMSG_NXTHDR(msgh, cmsg);
1164         target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
1165     }
1166     unlock_user(target_cmsg, target_cmsg_addr, 0);
1167  the_end:
1168     msgh->msg_controllen = space;
1169     return 0;
1170 }
1171 
1172 static inline abi_long host_to_target_cmsg(struct target_msghdr *target_msgh,
1173                                            struct msghdr *msgh)
1174 {
1175     struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
1176     abi_long msg_controllen;
1177     abi_ulong target_cmsg_addr;
1178     struct target_cmsghdr *target_cmsg;
1179     socklen_t space = 0;
1180 
1181     msg_controllen = tswapal(target_msgh->msg_controllen);
1182     if (msg_controllen < sizeof (struct target_cmsghdr))
1183         goto the_end;
1184     target_cmsg_addr = tswapal(target_msgh->msg_control);
1185     target_cmsg = lock_user(VERIFY_WRITE, target_cmsg_addr, msg_controllen, 0);
1186     if (!target_cmsg)
1187         return -TARGET_EFAULT;
1188 
1189     while (cmsg && target_cmsg) {
1190         void *data = CMSG_DATA(cmsg);
1191         void *target_data = TARGET_CMSG_DATA(target_cmsg);
1192 
1193         int len = cmsg->cmsg_len - CMSG_ALIGN(sizeof (struct cmsghdr));
1194 
1195         space += TARGET_CMSG_SPACE(len);
1196         if (space > msg_controllen) {
1197             space -= TARGET_CMSG_SPACE(len);
1198             gemu_log("Target cmsg overflow\n");
1199             break;
1200         }
1201 
1202         target_cmsg->cmsg_level = tswap32(cmsg->cmsg_level);
1203         target_cmsg->cmsg_type = tswap32(cmsg->cmsg_type);
1204         target_cmsg->cmsg_len = tswapal(TARGET_CMSG_LEN(len));
1205 
1206         if ((cmsg->cmsg_level == TARGET_SOL_SOCKET) &&
1207                                 (cmsg->cmsg_type == SCM_RIGHTS)) {
1208             int *fd = (int *)data;
1209             int *target_fd = (int *)target_data;
1210             int i, numfds = len / sizeof(int);
1211 
1212             for (i = 0; i < numfds; i++)
1213                 target_fd[i] = tswap32(fd[i]);
1214         } else if ((cmsg->cmsg_level == TARGET_SOL_SOCKET) &&
1215                                 (cmsg->cmsg_type == SO_TIMESTAMP) &&
1216                                 (len == sizeof(struct timeval))) {
1217             /* copy struct timeval to target */
1218             struct timeval *tv = (struct timeval *)data;
1219             struct target_timeval *target_tv =
1220                                         (struct target_timeval *)target_data;
1221 
1222             target_tv->tv_sec = tswapal(tv->tv_sec);
1223             target_tv->tv_usec = tswapal(tv->tv_usec);
1224         } else {
1225             gemu_log("Unsupported ancillary data: %d/%d\n",
1226                                         cmsg->cmsg_level, cmsg->cmsg_type);
1227             memcpy(target_data, data, len);
1228         }
1229 
1230         cmsg = CMSG_NXTHDR(msgh, cmsg);
1231         target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
1232     }
1233     unlock_user(target_cmsg, target_cmsg_addr, space);
1234  the_end:
1235     target_msgh->msg_controllen = tswapal(space);
1236     return 0;
1237 }
1238 
1239 /* do_setsockopt() Must return target values and target errnos. */
1240 static abi_long do_setsockopt(int sockfd, int level, int optname,
1241                               abi_ulong optval_addr, socklen_t optlen)
1242 {
1243     abi_long ret;
1244     int val;
1245     struct ip_mreqn *ip_mreq;
1246     struct ip_mreq_source *ip_mreq_source;
1247 
1248     switch(level) {
1249     case SOL_TCP:
1250         /* TCP options all take an 'int' value.  */
1251         if (optlen < sizeof(uint32_t))
1252             return -TARGET_EINVAL;
1253 
1254         if (get_user_u32(val, optval_addr))
1255             return -TARGET_EFAULT;
1256         ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
1257         break;
1258     case SOL_IP:
1259         switch(optname) {
1260         case IP_TOS:
1261         case IP_TTL:
1262         case IP_HDRINCL:
1263         case IP_ROUTER_ALERT:
1264         case IP_RECVOPTS:
1265         case IP_RETOPTS:
1266         case IP_PKTINFO:
1267         case IP_MTU_DISCOVER:
1268         case IP_RECVERR:
1269         case IP_RECVTOS:
1270 #ifdef IP_FREEBIND
1271         case IP_FREEBIND:
1272 #endif
1273         case IP_MULTICAST_TTL:
1274         case IP_MULTICAST_LOOP:
1275             val = 0;
1276             if (optlen >= sizeof(uint32_t)) {
1277                 if (get_user_u32(val, optval_addr))
1278                     return -TARGET_EFAULT;
1279             } else if (optlen >= 1) {
1280                 if (get_user_u8(val, optval_addr))
1281                     return -TARGET_EFAULT;
1282             }
1283             ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
1284             break;
1285         case IP_ADD_MEMBERSHIP:
1286         case IP_DROP_MEMBERSHIP:
1287             if (optlen < sizeof (struct target_ip_mreq) ||
1288                 optlen > sizeof (struct target_ip_mreqn))
1289                 return -TARGET_EINVAL;
1290 
1291             ip_mreq = (struct ip_mreqn *) alloca(optlen);
1292             target_to_host_ip_mreq(ip_mreq, optval_addr, optlen);
1293             ret = get_errno(setsockopt(sockfd, level, optname, ip_mreq, optlen));
1294             break;
1295 
1296         case IP_BLOCK_SOURCE:
1297         case IP_UNBLOCK_SOURCE:
1298         case IP_ADD_SOURCE_MEMBERSHIP:
1299         case IP_DROP_SOURCE_MEMBERSHIP:
1300             if (optlen != sizeof (struct target_ip_mreq_source))
1301                 return -TARGET_EINVAL;
1302 
1303             ip_mreq_source = lock_user(VERIFY_READ, optval_addr, optlen, 1);
1304             ret = get_errno(setsockopt(sockfd, level, optname, ip_mreq_source, optlen));
1305             unlock_user (ip_mreq_source, optval_addr, 0);
1306             break;
1307 
1308         default:
1309             goto unimplemented;
1310         }
1311         break;
1312     case SOL_RAW:
1313         switch (optname) {
1314         case ICMP_FILTER:
1315             /* struct icmp_filter takes an u32 value */
1316             if (optlen < sizeof(uint32_t)) {
1317                 return -TARGET_EINVAL;
1318             }
1319 
1320             if (get_user_u32(val, optval_addr)) {
1321                 return -TARGET_EFAULT;
1322             }
1323             ret = get_errno(setsockopt(sockfd, level, optname,
1324                                        &val, sizeof(val)));
1325             break;
1326 
1327         default:
1328             goto unimplemented;
1329         }
1330         break;
1331     case TARGET_SOL_SOCKET:
1332         switch (optname) {
1333         case TARGET_SO_RCVTIMEO:
1334         {
1335                 struct timeval tv;
1336 
1337                 optname = SO_RCVTIMEO;
1338 
1339 set_timeout:
1340                 if (optlen != sizeof(struct target_timeval)) {
1341                     return -TARGET_EINVAL;
1342                 }
1343 
1344                 if (copy_from_user_timeval(&tv, optval_addr)) {
1345                     return -TARGET_EFAULT;
1346                 }
1347 
1348                 ret = get_errno(setsockopt(sockfd, SOL_SOCKET, optname,
1349                                 &tv, sizeof(tv)));
1350                 return ret;
1351         }
1352         case TARGET_SO_SNDTIMEO:
1353                 optname = SO_SNDTIMEO;
1354                 goto set_timeout;
1355             /* Options with 'int' argument.  */
1356         case TARGET_SO_DEBUG:
1357 		optname = SO_DEBUG;
1358 		break;
1359         case TARGET_SO_REUSEADDR:
1360 		optname = SO_REUSEADDR;
1361 		break;
1362         case TARGET_SO_TYPE:
1363 		optname = SO_TYPE;
1364 		break;
1365         case TARGET_SO_ERROR:
1366 		optname = SO_ERROR;
1367 		break;
1368         case TARGET_SO_DONTROUTE:
1369 		optname = SO_DONTROUTE;
1370 		break;
1371         case TARGET_SO_BROADCAST:
1372 		optname = SO_BROADCAST;
1373 		break;
1374         case TARGET_SO_SNDBUF:
1375 		optname = SO_SNDBUF;
1376 		break;
1377         case TARGET_SO_RCVBUF:
1378 		optname = SO_RCVBUF;
1379 		break;
1380         case TARGET_SO_KEEPALIVE:
1381 		optname = SO_KEEPALIVE;
1382 		break;
1383         case TARGET_SO_OOBINLINE:
1384 		optname = SO_OOBINLINE;
1385 		break;
1386         case TARGET_SO_NO_CHECK:
1387 		optname = SO_NO_CHECK;
1388 		break;
1389         case TARGET_SO_PRIORITY:
1390 		optname = SO_PRIORITY;
1391 		break;
1392 #ifdef SO_BSDCOMPAT
1393         case TARGET_SO_BSDCOMPAT:
1394 		optname = SO_BSDCOMPAT;
1395 		break;
1396 #endif
1397         case TARGET_SO_PASSCRED:
1398 		optname = SO_PASSCRED;
1399 		break;
1400         case TARGET_SO_TIMESTAMP:
1401 		optname = SO_TIMESTAMP;
1402 		break;
1403         case TARGET_SO_RCVLOWAT:
1404 		optname = SO_RCVLOWAT;
1405 		break;
1406             break;
1407         default:
1408             goto unimplemented;
1409         }
1410 	if (optlen < sizeof(uint32_t))
1411             return -TARGET_EINVAL;
1412 
1413 	if (get_user_u32(val, optval_addr))
1414             return -TARGET_EFAULT;
1415 	ret = get_errno(setsockopt(sockfd, SOL_SOCKET, optname, &val, sizeof(val)));
1416         break;
1417     default:
1418     unimplemented:
1419         gemu_log("Unsupported setsockopt level=%d optname=%d\n", level, optname);
1420         ret = -TARGET_ENOPROTOOPT;
1421     }
1422     return ret;
1423 }
1424 
1425 /* do_getsockopt() Must return target values and target errnos. */
1426 static abi_long do_getsockopt(int sockfd, int level, int optname,
1427                               abi_ulong optval_addr, abi_ulong optlen)
1428 {
1429     abi_long ret;
1430     int len, val;
1431     socklen_t lv;
1432 
1433     switch(level) {
1434     case TARGET_SOL_SOCKET:
1435         level = SOL_SOCKET;
1436         switch (optname) {
1437         /* These don't just return a single integer */
1438         case TARGET_SO_LINGER:
1439         case TARGET_SO_RCVTIMEO:
1440         case TARGET_SO_SNDTIMEO:
1441         case TARGET_SO_PEERNAME:
1442             goto unimplemented;
1443         case TARGET_SO_PEERCRED: {
1444             struct ucred cr;
1445             socklen_t crlen;
1446             struct target_ucred *tcr;
1447 
1448             if (get_user_u32(len, optlen)) {
1449                 return -TARGET_EFAULT;
1450             }
1451             if (len < 0) {
1452                 return -TARGET_EINVAL;
1453             }
1454 
1455             crlen = sizeof(cr);
1456             ret = get_errno(getsockopt(sockfd, level, SO_PEERCRED,
1457                                        &cr, &crlen));
1458             if (ret < 0) {
1459                 return ret;
1460             }
1461             if (len > crlen) {
1462                 len = crlen;
1463             }
1464             if (!lock_user_struct(VERIFY_WRITE, tcr, optval_addr, 0)) {
1465                 return -TARGET_EFAULT;
1466             }
1467             __put_user(cr.pid, &tcr->pid);
1468             __put_user(cr.uid, &tcr->uid);
1469             __put_user(cr.gid, &tcr->gid);
1470             unlock_user_struct(tcr, optval_addr, 1);
1471             if (put_user_u32(len, optlen)) {
1472                 return -TARGET_EFAULT;
1473             }
1474             break;
1475         }
1476         /* Options with 'int' argument.  */
1477         case TARGET_SO_DEBUG:
1478             optname = SO_DEBUG;
1479             goto int_case;
1480         case TARGET_SO_REUSEADDR:
1481             optname = SO_REUSEADDR;
1482             goto int_case;
1483         case TARGET_SO_TYPE:
1484             optname = SO_TYPE;
1485             goto int_case;
1486         case TARGET_SO_ERROR:
1487             optname = SO_ERROR;
1488             goto int_case;
1489         case TARGET_SO_DONTROUTE:
1490             optname = SO_DONTROUTE;
1491             goto int_case;
1492         case TARGET_SO_BROADCAST:
1493             optname = SO_BROADCAST;
1494             goto int_case;
1495         case TARGET_SO_SNDBUF:
1496             optname = SO_SNDBUF;
1497             goto int_case;
1498         case TARGET_SO_RCVBUF:
1499             optname = SO_RCVBUF;
1500             goto int_case;
1501         case TARGET_SO_KEEPALIVE:
1502             optname = SO_KEEPALIVE;
1503             goto int_case;
1504         case TARGET_SO_OOBINLINE:
1505             optname = SO_OOBINLINE;
1506             goto int_case;
1507         case TARGET_SO_NO_CHECK:
1508             optname = SO_NO_CHECK;
1509             goto int_case;
1510         case TARGET_SO_PRIORITY:
1511             optname = SO_PRIORITY;
1512             goto int_case;
1513 #ifdef SO_BSDCOMPAT
1514         case TARGET_SO_BSDCOMPAT:
1515             optname = SO_BSDCOMPAT;
1516             goto int_case;
1517 #endif
1518         case TARGET_SO_PASSCRED:
1519             optname = SO_PASSCRED;
1520             goto int_case;
1521         case TARGET_SO_TIMESTAMP:
1522             optname = SO_TIMESTAMP;
1523             goto int_case;
1524         case TARGET_SO_RCVLOWAT:
1525             optname = SO_RCVLOWAT;
1526             goto int_case;
1527         default:
1528             goto int_case;
1529         }
1530         break;
1531     case SOL_TCP:
1532         /* TCP options all take an 'int' value.  */
1533     int_case:
1534         if (get_user_u32(len, optlen))
1535             return -TARGET_EFAULT;
1536         if (len < 0)
1537             return -TARGET_EINVAL;
1538         lv = sizeof(lv);
1539         ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
1540         if (ret < 0)
1541             return ret;
1542         if (len > lv)
1543             len = lv;
1544         if (len == 4) {
1545             if (put_user_u32(val, optval_addr))
1546                 return -TARGET_EFAULT;
1547         } else {
1548             if (put_user_u8(val, optval_addr))
1549                 return -TARGET_EFAULT;
1550         }
1551         if (put_user_u32(len, optlen))
1552             return -TARGET_EFAULT;
1553         break;
1554     case SOL_IP:
1555         switch(optname) {
1556         case IP_TOS:
1557         case IP_TTL:
1558         case IP_HDRINCL:
1559         case IP_ROUTER_ALERT:
1560         case IP_RECVOPTS:
1561         case IP_RETOPTS:
1562         case IP_PKTINFO:
1563         case IP_MTU_DISCOVER:
1564         case IP_RECVERR:
1565         case IP_RECVTOS:
1566 #ifdef IP_FREEBIND
1567         case IP_FREEBIND:
1568 #endif
1569         case IP_MULTICAST_TTL:
1570         case IP_MULTICAST_LOOP:
1571             if (get_user_u32(len, optlen))
1572                 return -TARGET_EFAULT;
1573             if (len < 0)
1574                 return -TARGET_EINVAL;
1575             lv = sizeof(lv);
1576             ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
1577             if (ret < 0)
1578                 return ret;
1579             if (len < sizeof(int) && len > 0 && val >= 0 && val < 255) {
1580                 len = 1;
1581                 if (put_user_u32(len, optlen)
1582                     || put_user_u8(val, optval_addr))
1583                     return -TARGET_EFAULT;
1584             } else {
1585                 if (len > sizeof(int))
1586                     len = sizeof(int);
1587                 if (put_user_u32(len, optlen)
1588                     || put_user_u32(val, optval_addr))
1589                     return -TARGET_EFAULT;
1590             }
1591             break;
1592         default:
1593             ret = -TARGET_ENOPROTOOPT;
1594             break;
1595         }
1596         break;
1597     default:
1598     unimplemented:
1599         gemu_log("getsockopt level=%d optname=%d not yet supported\n",
1600                  level, optname);
1601         ret = -TARGET_EOPNOTSUPP;
1602         break;
1603     }
1604     return ret;
1605 }
1606 
1607 static struct iovec *lock_iovec(int type, abi_ulong target_addr,
1608                                 int count, int copy)
1609 {
1610     struct target_iovec *target_vec;
1611     struct iovec *vec;
1612     abi_ulong total_len, max_len;
1613     int i;
1614 
1615     if (count == 0) {
1616         errno = 0;
1617         return NULL;
1618     }
1619     if (count < 0 || count > IOV_MAX) {
1620         errno = EINVAL;
1621         return NULL;
1622     }
1623 
1624     vec = calloc(count, sizeof(struct iovec));
1625     if (vec == NULL) {
1626         errno = ENOMEM;
1627         return NULL;
1628     }
1629 
1630     target_vec = lock_user(VERIFY_READ, target_addr,
1631                            count * sizeof(struct target_iovec), 1);
1632     if (target_vec == NULL) {
1633         errno = EFAULT;
1634         goto fail2;
1635     }
1636 
1637     /* ??? If host page size > target page size, this will result in a
1638        value larger than what we can actually support.  */
1639     max_len = 0x7fffffff & TARGET_PAGE_MASK;
1640     total_len = 0;
1641 
1642     for (i = 0; i < count; i++) {
1643         abi_ulong base = tswapal(target_vec[i].iov_base);
1644         abi_long len = tswapal(target_vec[i].iov_len);
1645 
1646         if (len < 0) {
1647             errno = EINVAL;
1648             goto fail;
1649         } else if (len == 0) {
1650             /* Zero length pointer is ignored.  */
1651             vec[i].iov_base = 0;
1652         } else {
1653             vec[i].iov_base = lock_user(type, base, len, copy);
1654             if (!vec[i].iov_base) {
1655                 errno = EFAULT;
1656                 goto fail;
1657             }
1658             if (len > max_len - total_len) {
1659                 len = max_len - total_len;
1660             }
1661         }
1662         vec[i].iov_len = len;
1663         total_len += len;
1664     }
1665 
1666     unlock_user(target_vec, target_addr, 0);
1667     return vec;
1668 
1669  fail:
1670     free(vec);
1671  fail2:
1672     unlock_user(target_vec, target_addr, 0);
1673     return NULL;
1674 }
1675 
1676 static void unlock_iovec(struct iovec *vec, abi_ulong target_addr,
1677                          int count, int copy)
1678 {
1679     struct target_iovec *target_vec;
1680     int i;
1681 
1682     target_vec = lock_user(VERIFY_READ, target_addr,
1683                            count * sizeof(struct target_iovec), 1);
1684     if (target_vec) {
1685         for (i = 0; i < count; i++) {
1686             abi_ulong base = tswapal(target_vec[i].iov_base);
1687             abi_long len = tswapal(target_vec[i].iov_base);
1688             if (len < 0) {
1689                 break;
1690             }
1691             unlock_user(vec[i].iov_base, base, copy ? vec[i].iov_len : 0);
1692         }
1693         unlock_user(target_vec, target_addr, 0);
1694     }
1695 
1696     free(vec);
1697 }
1698 
1699 /* do_socket() Must return target values and target errnos. */
1700 static abi_long do_socket(int domain, int type, int protocol)
1701 {
1702 #if defined(TARGET_MIPS)
1703     switch(type) {
1704     case TARGET_SOCK_DGRAM:
1705         type = SOCK_DGRAM;
1706         break;
1707     case TARGET_SOCK_STREAM:
1708         type = SOCK_STREAM;
1709         break;
1710     case TARGET_SOCK_RAW:
1711         type = SOCK_RAW;
1712         break;
1713     case TARGET_SOCK_RDM:
1714         type = SOCK_RDM;
1715         break;
1716     case TARGET_SOCK_SEQPACKET:
1717         type = SOCK_SEQPACKET;
1718         break;
1719     case TARGET_SOCK_PACKET:
1720         type = SOCK_PACKET;
1721         break;
1722     }
1723 #endif
1724     if (domain == PF_NETLINK)
1725         return -EAFNOSUPPORT; /* do not NETLINK socket connections possible */
1726     return get_errno(socket(domain, type, protocol));
1727 }
1728 
1729 /* do_bind() Must return target values and target errnos. */
1730 static abi_long do_bind(int sockfd, abi_ulong target_addr,
1731                         socklen_t addrlen)
1732 {
1733     void *addr;
1734     abi_long ret;
1735 
1736     if ((int)addrlen < 0) {
1737         return -TARGET_EINVAL;
1738     }
1739 
1740     addr = alloca(addrlen+1);
1741 
1742     ret = target_to_host_sockaddr(addr, target_addr, addrlen);
1743     if (ret)
1744         return ret;
1745 
1746     return get_errno(bind(sockfd, addr, addrlen));
1747 }
1748 
1749 /* do_connect() Must return target values and target errnos. */
1750 static abi_long do_connect(int sockfd, abi_ulong target_addr,
1751                            socklen_t addrlen)
1752 {
1753     void *addr;
1754     abi_long ret;
1755 
1756     if ((int)addrlen < 0) {
1757         return -TARGET_EINVAL;
1758     }
1759 
1760     addr = alloca(addrlen);
1761 
1762     ret = target_to_host_sockaddr(addr, target_addr, addrlen);
1763     if (ret)
1764         return ret;
1765 
1766     return get_errno(connect(sockfd, addr, addrlen));
1767 }
1768 
1769 /* do_sendrecvmsg() Must return target values and target errnos. */
1770 static abi_long do_sendrecvmsg(int fd, abi_ulong target_msg,
1771                                int flags, int send)
1772 {
1773     abi_long ret, len;
1774     struct target_msghdr *msgp;
1775     struct msghdr msg;
1776     int count;
1777     struct iovec *vec;
1778     abi_ulong target_vec;
1779 
1780     /* FIXME */
1781     if (!lock_user_struct(send ? VERIFY_READ : VERIFY_WRITE,
1782                           msgp,
1783                           target_msg,
1784                           send ? 1 : 0))
1785         return -TARGET_EFAULT;
1786     if (msgp->msg_name) {
1787         msg.msg_namelen = tswap32(msgp->msg_namelen);
1788         msg.msg_name = alloca(msg.msg_namelen);
1789         ret = target_to_host_sockaddr(msg.msg_name, tswapal(msgp->msg_name),
1790                                 msg.msg_namelen);
1791         if (ret) {
1792             goto out2;
1793         }
1794     } else {
1795         msg.msg_name = NULL;
1796         msg.msg_namelen = 0;
1797     }
1798     msg.msg_controllen = 2 * tswapal(msgp->msg_controllen);
1799     msg.msg_control = alloca(msg.msg_controllen);
1800     msg.msg_flags = tswap32(msgp->msg_flags);
1801 
1802     count = tswapal(msgp->msg_iovlen);
1803     target_vec = tswapal(msgp->msg_iov);
1804     vec = lock_iovec(send ? VERIFY_READ : VERIFY_WRITE,
1805                      target_vec, count, send);
1806     if (vec == NULL) {
1807         ret = -host_to_target_errno(errno);
1808         goto out2;
1809     }
1810     msg.msg_iovlen = count;
1811     msg.msg_iov = vec;
1812 
1813     if (send) {
1814         ret = target_to_host_cmsg(&msg, msgp);
1815         if (ret == 0)
1816             ret = get_errno(sendmsg(fd, &msg, flags));
1817     } else {
1818         ret = get_errno(recvmsg(fd, &msg, flags));
1819         if (!is_error(ret)) {
1820             len = ret;
1821             ret = host_to_target_cmsg(msgp, &msg);
1822             if (!is_error(ret)) {
1823                 msgp->msg_namelen = tswap32(msg.msg_namelen);
1824                 if (msg.msg_name != NULL) {
1825                     ret = host_to_target_sockaddr(tswapal(msgp->msg_name),
1826                                     msg.msg_name, msg.msg_namelen);
1827                     if (ret) {
1828                         goto out;
1829                     }
1830                 }
1831 
1832                 ret = len;
1833             }
1834         }
1835     }
1836 
1837 out:
1838     unlock_iovec(vec, target_vec, count, !send);
1839 out2:
1840     unlock_user_struct(msgp, target_msg, send ? 0 : 1);
1841     return ret;
1842 }
1843 
1844 /* If we don't have a system accept4() then just call accept.
1845  * The callsites to do_accept4() will ensure that they don't
1846  * pass a non-zero flags argument in this config.
1847  */
1848 #ifndef CONFIG_ACCEPT4
1849 static inline int accept4(int sockfd, struct sockaddr *addr,
1850                           socklen_t *addrlen, int flags)
1851 {
1852     assert(flags == 0);
1853     return accept(sockfd, addr, addrlen);
1854 }
1855 #endif
1856 
1857 /* do_accept4() Must return target values and target errnos. */
1858 static abi_long do_accept4(int fd, abi_ulong target_addr,
1859                            abi_ulong target_addrlen_addr, int flags)
1860 {
1861     socklen_t addrlen;
1862     void *addr;
1863     abi_long ret;
1864 
1865     if (target_addr == 0) {
1866         return get_errno(accept4(fd, NULL, NULL, flags));
1867     }
1868 
1869     /* linux returns EINVAL if addrlen pointer is invalid */
1870     if (get_user_u32(addrlen, target_addrlen_addr))
1871         return -TARGET_EINVAL;
1872 
1873     if ((int)addrlen < 0) {
1874         return -TARGET_EINVAL;
1875     }
1876 
1877     if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
1878         return -TARGET_EINVAL;
1879 
1880     addr = alloca(addrlen);
1881 
1882     ret = get_errno(accept4(fd, addr, &addrlen, flags));
1883     if (!is_error(ret)) {
1884         host_to_target_sockaddr(target_addr, addr, addrlen);
1885         if (put_user_u32(addrlen, target_addrlen_addr))
1886             ret = -TARGET_EFAULT;
1887     }
1888     return ret;
1889 }
1890 
1891 /* do_getpeername() Must return target values and target errnos. */
1892 static abi_long do_getpeername(int fd, abi_ulong target_addr,
1893                                abi_ulong target_addrlen_addr)
1894 {
1895     socklen_t addrlen;
1896     void *addr;
1897     abi_long ret;
1898 
1899     if (get_user_u32(addrlen, target_addrlen_addr))
1900         return -TARGET_EFAULT;
1901 
1902     if ((int)addrlen < 0) {
1903         return -TARGET_EINVAL;
1904     }
1905 
1906     if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
1907         return -TARGET_EFAULT;
1908 
1909     addr = alloca(addrlen);
1910 
1911     ret = get_errno(getpeername(fd, addr, &addrlen));
1912     if (!is_error(ret)) {
1913         host_to_target_sockaddr(target_addr, addr, addrlen);
1914         if (put_user_u32(addrlen, target_addrlen_addr))
1915             ret = -TARGET_EFAULT;
1916     }
1917     return ret;
1918 }
1919 
1920 /* do_getsockname() Must return target values and target errnos. */
1921 static abi_long do_getsockname(int fd, abi_ulong target_addr,
1922                                abi_ulong target_addrlen_addr)
1923 {
1924     socklen_t addrlen;
1925     void *addr;
1926     abi_long ret;
1927 
1928     if (get_user_u32(addrlen, target_addrlen_addr))
1929         return -TARGET_EFAULT;
1930 
1931     if ((int)addrlen < 0) {
1932         return -TARGET_EINVAL;
1933     }
1934 
1935     if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
1936         return -TARGET_EFAULT;
1937 
1938     addr = alloca(addrlen);
1939 
1940     ret = get_errno(getsockname(fd, addr, &addrlen));
1941     if (!is_error(ret)) {
1942         host_to_target_sockaddr(target_addr, addr, addrlen);
1943         if (put_user_u32(addrlen, target_addrlen_addr))
1944             ret = -TARGET_EFAULT;
1945     }
1946     return ret;
1947 }
1948 
1949 /* do_socketpair() Must return target values and target errnos. */
1950 static abi_long do_socketpair(int domain, int type, int protocol,
1951                               abi_ulong target_tab_addr)
1952 {
1953     int tab[2];
1954     abi_long ret;
1955 
1956     ret = get_errno(socketpair(domain, type, protocol, tab));
1957     if (!is_error(ret)) {
1958         if (put_user_s32(tab[0], target_tab_addr)
1959             || put_user_s32(tab[1], target_tab_addr + sizeof(tab[0])))
1960             ret = -TARGET_EFAULT;
1961     }
1962     return ret;
1963 }
1964 
1965 /* do_sendto() Must return target values and target errnos. */
1966 static abi_long do_sendto(int fd, abi_ulong msg, size_t len, int flags,
1967                           abi_ulong target_addr, socklen_t addrlen)
1968 {
1969     void *addr;
1970     void *host_msg;
1971     abi_long ret;
1972 
1973     if ((int)addrlen < 0) {
1974         return -TARGET_EINVAL;
1975     }
1976 
1977     host_msg = lock_user(VERIFY_READ, msg, len, 1);
1978     if (!host_msg)
1979         return -TARGET_EFAULT;
1980     if (target_addr) {
1981         addr = alloca(addrlen);
1982         ret = target_to_host_sockaddr(addr, target_addr, addrlen);
1983         if (ret) {
1984             unlock_user(host_msg, msg, 0);
1985             return ret;
1986         }
1987         ret = get_errno(sendto(fd, host_msg, len, flags, addr, addrlen));
1988     } else {
1989         ret = get_errno(send(fd, host_msg, len, flags));
1990     }
1991     unlock_user(host_msg, msg, 0);
1992     return ret;
1993 }
1994 
1995 /* do_recvfrom() Must return target values and target errnos. */
1996 static abi_long do_recvfrom(int fd, abi_ulong msg, size_t len, int flags,
1997                             abi_ulong target_addr,
1998                             abi_ulong target_addrlen)
1999 {
2000     socklen_t addrlen;
2001     void *addr;
2002     void *host_msg;
2003     abi_long ret;
2004 
2005     host_msg = lock_user(VERIFY_WRITE, msg, len, 0);
2006     if (!host_msg)
2007         return -TARGET_EFAULT;
2008     if (target_addr) {
2009         if (get_user_u32(addrlen, target_addrlen)) {
2010             ret = -TARGET_EFAULT;
2011             goto fail;
2012         }
2013         if ((int)addrlen < 0) {
2014             ret = -TARGET_EINVAL;
2015             goto fail;
2016         }
2017         addr = alloca(addrlen);
2018         ret = get_errno(recvfrom(fd, host_msg, len, flags, addr, &addrlen));
2019     } else {
2020         addr = NULL; /* To keep compiler quiet.  */
2021         ret = get_errno(qemu_recv(fd, host_msg, len, flags));
2022     }
2023     if (!is_error(ret)) {
2024         if (target_addr) {
2025             host_to_target_sockaddr(target_addr, addr, addrlen);
2026             if (put_user_u32(addrlen, target_addrlen)) {
2027                 ret = -TARGET_EFAULT;
2028                 goto fail;
2029             }
2030         }
2031         unlock_user(host_msg, msg, len);
2032     } else {
2033 fail:
2034         unlock_user(host_msg, msg, 0);
2035     }
2036     return ret;
2037 }
2038 
2039 #ifdef TARGET_NR_socketcall
2040 /* do_socketcall() Must return target values and target errnos. */
2041 static abi_long do_socketcall(int num, abi_ulong vptr)
2042 {
2043     abi_long ret;
2044     const int n = sizeof(abi_ulong);
2045 
2046     switch(num) {
2047     case SOCKOP_socket:
2048 	{
2049             abi_ulong domain, type, protocol;
2050 
2051             if (get_user_ual(domain, vptr)
2052                 || get_user_ual(type, vptr + n)
2053                 || get_user_ual(protocol, vptr + 2 * n))
2054                 return -TARGET_EFAULT;
2055 
2056             ret = do_socket(domain, type, protocol);
2057 	}
2058         break;
2059     case SOCKOP_bind:
2060 	{
2061             abi_ulong sockfd;
2062             abi_ulong target_addr;
2063             socklen_t addrlen;
2064 
2065             if (get_user_ual(sockfd, vptr)
2066                 || get_user_ual(target_addr, vptr + n)
2067                 || get_user_ual(addrlen, vptr + 2 * n))
2068                 return -TARGET_EFAULT;
2069 
2070             ret = do_bind(sockfd, target_addr, addrlen);
2071         }
2072         break;
2073     case SOCKOP_connect:
2074         {
2075             abi_ulong sockfd;
2076             abi_ulong target_addr;
2077             socklen_t addrlen;
2078 
2079             if (get_user_ual(sockfd, vptr)
2080                 || get_user_ual(target_addr, vptr + n)
2081                 || get_user_ual(addrlen, vptr + 2 * n))
2082                 return -TARGET_EFAULT;
2083 
2084             ret = do_connect(sockfd, target_addr, addrlen);
2085         }
2086         break;
2087     case SOCKOP_listen:
2088         {
2089             abi_ulong sockfd, backlog;
2090 
2091             if (get_user_ual(sockfd, vptr)
2092                 || get_user_ual(backlog, vptr + n))
2093                 return -TARGET_EFAULT;
2094 
2095             ret = get_errno(listen(sockfd, backlog));
2096         }
2097         break;
2098     case SOCKOP_accept:
2099         {
2100             abi_ulong sockfd;
2101             abi_ulong target_addr, target_addrlen;
2102 
2103             if (get_user_ual(sockfd, vptr)
2104                 || get_user_ual(target_addr, vptr + n)
2105                 || get_user_ual(target_addrlen, vptr + 2 * n))
2106                 return -TARGET_EFAULT;
2107 
2108             ret = do_accept4(sockfd, target_addr, target_addrlen, 0);
2109         }
2110         break;
2111     case SOCKOP_getsockname:
2112         {
2113             abi_ulong sockfd;
2114             abi_ulong target_addr, target_addrlen;
2115 
2116             if (get_user_ual(sockfd, vptr)
2117                 || get_user_ual(target_addr, vptr + n)
2118                 || get_user_ual(target_addrlen, vptr + 2 * n))
2119                 return -TARGET_EFAULT;
2120 
2121             ret = do_getsockname(sockfd, target_addr, target_addrlen);
2122         }
2123         break;
2124     case SOCKOP_getpeername:
2125         {
2126             abi_ulong sockfd;
2127             abi_ulong target_addr, target_addrlen;
2128 
2129             if (get_user_ual(sockfd, vptr)
2130                 || get_user_ual(target_addr, vptr + n)
2131                 || get_user_ual(target_addrlen, vptr + 2 * n))
2132                 return -TARGET_EFAULT;
2133 
2134             ret = do_getpeername(sockfd, target_addr, target_addrlen);
2135         }
2136         break;
2137     case SOCKOP_socketpair:
2138         {
2139             abi_ulong domain, type, protocol;
2140             abi_ulong tab;
2141 
2142             if (get_user_ual(domain, vptr)
2143                 || get_user_ual(type, vptr + n)
2144                 || get_user_ual(protocol, vptr + 2 * n)
2145                 || get_user_ual(tab, vptr + 3 * n))
2146                 return -TARGET_EFAULT;
2147 
2148             ret = do_socketpair(domain, type, protocol, tab);
2149         }
2150         break;
2151     case SOCKOP_send:
2152         {
2153             abi_ulong sockfd;
2154             abi_ulong msg;
2155             size_t len;
2156             abi_ulong flags;
2157 
2158             if (get_user_ual(sockfd, vptr)
2159                 || get_user_ual(msg, vptr + n)
2160                 || get_user_ual(len, vptr + 2 * n)
2161                 || get_user_ual(flags, vptr + 3 * n))
2162                 return -TARGET_EFAULT;
2163 
2164             ret = do_sendto(sockfd, msg, len, flags, 0, 0);
2165         }
2166         break;
2167     case SOCKOP_recv:
2168         {
2169             abi_ulong sockfd;
2170             abi_ulong msg;
2171             size_t len;
2172             abi_ulong flags;
2173 
2174             if (get_user_ual(sockfd, vptr)
2175                 || get_user_ual(msg, vptr + n)
2176                 || get_user_ual(len, vptr + 2 * n)
2177                 || get_user_ual(flags, vptr + 3 * n))
2178                 return -TARGET_EFAULT;
2179 
2180             ret = do_recvfrom(sockfd, msg, len, flags, 0, 0);
2181         }
2182         break;
2183     case SOCKOP_sendto:
2184         {
2185             abi_ulong sockfd;
2186             abi_ulong msg;
2187             size_t len;
2188             abi_ulong flags;
2189             abi_ulong addr;
2190             socklen_t addrlen;
2191 
2192             if (get_user_ual(sockfd, vptr)
2193                 || get_user_ual(msg, vptr + n)
2194                 || get_user_ual(len, vptr + 2 * n)
2195                 || get_user_ual(flags, vptr + 3 * n)
2196                 || get_user_ual(addr, vptr + 4 * n)
2197                 || get_user_ual(addrlen, vptr + 5 * n))
2198                 return -TARGET_EFAULT;
2199 
2200             ret = do_sendto(sockfd, msg, len, flags, addr, addrlen);
2201         }
2202         break;
2203     case SOCKOP_recvfrom:
2204         {
2205             abi_ulong sockfd;
2206             abi_ulong msg;
2207             size_t len;
2208             abi_ulong flags;
2209             abi_ulong addr;
2210             socklen_t addrlen;
2211 
2212             if (get_user_ual(sockfd, vptr)
2213                 || get_user_ual(msg, vptr + n)
2214                 || get_user_ual(len, vptr + 2 * n)
2215                 || get_user_ual(flags, vptr + 3 * n)
2216                 || get_user_ual(addr, vptr + 4 * n)
2217                 || get_user_ual(addrlen, vptr + 5 * n))
2218                 return -TARGET_EFAULT;
2219 
2220             ret = do_recvfrom(sockfd, msg, len, flags, addr, addrlen);
2221         }
2222         break;
2223     case SOCKOP_shutdown:
2224         {
2225             abi_ulong sockfd, how;
2226 
2227             if (get_user_ual(sockfd, vptr)
2228                 || get_user_ual(how, vptr + n))
2229                 return -TARGET_EFAULT;
2230 
2231             ret = get_errno(shutdown(sockfd, how));
2232         }
2233         break;
2234     case SOCKOP_sendmsg:
2235     case SOCKOP_recvmsg:
2236         {
2237             abi_ulong fd;
2238             abi_ulong target_msg;
2239             abi_ulong flags;
2240 
2241             if (get_user_ual(fd, vptr)
2242                 || get_user_ual(target_msg, vptr + n)
2243                 || get_user_ual(flags, vptr + 2 * n))
2244                 return -TARGET_EFAULT;
2245 
2246             ret = do_sendrecvmsg(fd, target_msg, flags,
2247                                  (num == SOCKOP_sendmsg));
2248         }
2249         break;
2250     case SOCKOP_setsockopt:
2251         {
2252             abi_ulong sockfd;
2253             abi_ulong level;
2254             abi_ulong optname;
2255             abi_ulong optval;
2256             socklen_t optlen;
2257 
2258             if (get_user_ual(sockfd, vptr)
2259                 || get_user_ual(level, vptr + n)
2260                 || get_user_ual(optname, vptr + 2 * n)
2261                 || get_user_ual(optval, vptr + 3 * n)
2262                 || get_user_ual(optlen, vptr + 4 * n))
2263                 return -TARGET_EFAULT;
2264 
2265             ret = do_setsockopt(sockfd, level, optname, optval, optlen);
2266         }
2267         break;
2268     case SOCKOP_getsockopt:
2269         {
2270             abi_ulong sockfd;
2271             abi_ulong level;
2272             abi_ulong optname;
2273             abi_ulong optval;
2274             socklen_t optlen;
2275 
2276             if (get_user_ual(sockfd, vptr)
2277                 || get_user_ual(level, vptr + n)
2278                 || get_user_ual(optname, vptr + 2 * n)
2279                 || get_user_ual(optval, vptr + 3 * n)
2280                 || get_user_ual(optlen, vptr + 4 * n))
2281                 return -TARGET_EFAULT;
2282 
2283             ret = do_getsockopt(sockfd, level, optname, optval, optlen);
2284         }
2285         break;
2286     default:
2287         gemu_log("Unsupported socketcall: %d\n", num);
2288         ret = -TARGET_ENOSYS;
2289         break;
2290     }
2291     return ret;
2292 }
2293 #endif
2294 
2295 #define N_SHM_REGIONS	32
2296 
2297 static struct shm_region {
2298     abi_ulong	start;
2299     abi_ulong	size;
2300 } shm_regions[N_SHM_REGIONS];
2301 
2302 struct target_ipc_perm
2303 {
2304     abi_long __key;
2305     abi_ulong uid;
2306     abi_ulong gid;
2307     abi_ulong cuid;
2308     abi_ulong cgid;
2309     unsigned short int mode;
2310     unsigned short int __pad1;
2311     unsigned short int __seq;
2312     unsigned short int __pad2;
2313     abi_ulong __unused1;
2314     abi_ulong __unused2;
2315 };
2316 
2317 struct target_semid_ds
2318 {
2319   struct target_ipc_perm sem_perm;
2320   abi_ulong sem_otime;
2321   abi_ulong __unused1;
2322   abi_ulong sem_ctime;
2323   abi_ulong __unused2;
2324   abi_ulong sem_nsems;
2325   abi_ulong __unused3;
2326   abi_ulong __unused4;
2327 };
2328 
2329 static inline abi_long target_to_host_ipc_perm(struct ipc_perm *host_ip,
2330                                                abi_ulong target_addr)
2331 {
2332     struct target_ipc_perm *target_ip;
2333     struct target_semid_ds *target_sd;
2334 
2335     if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2336         return -TARGET_EFAULT;
2337     target_ip = &(target_sd->sem_perm);
2338     host_ip->__key = tswapal(target_ip->__key);
2339     host_ip->uid = tswapal(target_ip->uid);
2340     host_ip->gid = tswapal(target_ip->gid);
2341     host_ip->cuid = tswapal(target_ip->cuid);
2342     host_ip->cgid = tswapal(target_ip->cgid);
2343     host_ip->mode = tswap16(target_ip->mode);
2344     unlock_user_struct(target_sd, target_addr, 0);
2345     return 0;
2346 }
2347 
2348 static inline abi_long host_to_target_ipc_perm(abi_ulong target_addr,
2349                                                struct ipc_perm *host_ip)
2350 {
2351     struct target_ipc_perm *target_ip;
2352     struct target_semid_ds *target_sd;
2353 
2354     if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2355         return -TARGET_EFAULT;
2356     target_ip = &(target_sd->sem_perm);
2357     target_ip->__key = tswapal(host_ip->__key);
2358     target_ip->uid = tswapal(host_ip->uid);
2359     target_ip->gid = tswapal(host_ip->gid);
2360     target_ip->cuid = tswapal(host_ip->cuid);
2361     target_ip->cgid = tswapal(host_ip->cgid);
2362     target_ip->mode = tswap16(host_ip->mode);
2363     unlock_user_struct(target_sd, target_addr, 1);
2364     return 0;
2365 }
2366 
2367 static inline abi_long target_to_host_semid_ds(struct semid_ds *host_sd,
2368                                                abi_ulong target_addr)
2369 {
2370     struct target_semid_ds *target_sd;
2371 
2372     if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2373         return -TARGET_EFAULT;
2374     if (target_to_host_ipc_perm(&(host_sd->sem_perm),target_addr))
2375         return -TARGET_EFAULT;
2376     host_sd->sem_nsems = tswapal(target_sd->sem_nsems);
2377     host_sd->sem_otime = tswapal(target_sd->sem_otime);
2378     host_sd->sem_ctime = tswapal(target_sd->sem_ctime);
2379     unlock_user_struct(target_sd, target_addr, 0);
2380     return 0;
2381 }
2382 
2383 static inline abi_long host_to_target_semid_ds(abi_ulong target_addr,
2384                                                struct semid_ds *host_sd)
2385 {
2386     struct target_semid_ds *target_sd;
2387 
2388     if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2389         return -TARGET_EFAULT;
2390     if (host_to_target_ipc_perm(target_addr,&(host_sd->sem_perm)))
2391         return -TARGET_EFAULT;
2392     target_sd->sem_nsems = tswapal(host_sd->sem_nsems);
2393     target_sd->sem_otime = tswapal(host_sd->sem_otime);
2394     target_sd->sem_ctime = tswapal(host_sd->sem_ctime);
2395     unlock_user_struct(target_sd, target_addr, 1);
2396     return 0;
2397 }
2398 
2399 struct target_seminfo {
2400     int semmap;
2401     int semmni;
2402     int semmns;
2403     int semmnu;
2404     int semmsl;
2405     int semopm;
2406     int semume;
2407     int semusz;
2408     int semvmx;
2409     int semaem;
2410 };
2411 
2412 static inline abi_long host_to_target_seminfo(abi_ulong target_addr,
2413                                               struct seminfo *host_seminfo)
2414 {
2415     struct target_seminfo *target_seminfo;
2416     if (!lock_user_struct(VERIFY_WRITE, target_seminfo, target_addr, 0))
2417         return -TARGET_EFAULT;
2418     __put_user(host_seminfo->semmap, &target_seminfo->semmap);
2419     __put_user(host_seminfo->semmni, &target_seminfo->semmni);
2420     __put_user(host_seminfo->semmns, &target_seminfo->semmns);
2421     __put_user(host_seminfo->semmnu, &target_seminfo->semmnu);
2422     __put_user(host_seminfo->semmsl, &target_seminfo->semmsl);
2423     __put_user(host_seminfo->semopm, &target_seminfo->semopm);
2424     __put_user(host_seminfo->semume, &target_seminfo->semume);
2425     __put_user(host_seminfo->semusz, &target_seminfo->semusz);
2426     __put_user(host_seminfo->semvmx, &target_seminfo->semvmx);
2427     __put_user(host_seminfo->semaem, &target_seminfo->semaem);
2428     unlock_user_struct(target_seminfo, target_addr, 1);
2429     return 0;
2430 }
2431 
2432 union semun {
2433 	int val;
2434 	struct semid_ds *buf;
2435 	unsigned short *array;
2436 	struct seminfo *__buf;
2437 };
2438 
2439 union target_semun {
2440 	int val;
2441 	abi_ulong buf;
2442 	abi_ulong array;
2443 	abi_ulong __buf;
2444 };
2445 
2446 static inline abi_long target_to_host_semarray(int semid, unsigned short **host_array,
2447                                                abi_ulong target_addr)
2448 {
2449     int nsems;
2450     unsigned short *array;
2451     union semun semun;
2452     struct semid_ds semid_ds;
2453     int i, ret;
2454 
2455     semun.buf = &semid_ds;
2456 
2457     ret = semctl(semid, 0, IPC_STAT, semun);
2458     if (ret == -1)
2459         return get_errno(ret);
2460 
2461     nsems = semid_ds.sem_nsems;
2462 
2463     *host_array = malloc(nsems*sizeof(unsigned short));
2464     array = lock_user(VERIFY_READ, target_addr,
2465                       nsems*sizeof(unsigned short), 1);
2466     if (!array)
2467         return -TARGET_EFAULT;
2468 
2469     for(i=0; i<nsems; i++) {
2470         __get_user((*host_array)[i], &array[i]);
2471     }
2472     unlock_user(array, target_addr, 0);
2473 
2474     return 0;
2475 }
2476 
2477 static inline abi_long host_to_target_semarray(int semid, abi_ulong target_addr,
2478                                                unsigned short **host_array)
2479 {
2480     int nsems;
2481     unsigned short *array;
2482     union semun semun;
2483     struct semid_ds semid_ds;
2484     int i, ret;
2485 
2486     semun.buf = &semid_ds;
2487 
2488     ret = semctl(semid, 0, IPC_STAT, semun);
2489     if (ret == -1)
2490         return get_errno(ret);
2491 
2492     nsems = semid_ds.sem_nsems;
2493 
2494     array = lock_user(VERIFY_WRITE, target_addr,
2495                       nsems*sizeof(unsigned short), 0);
2496     if (!array)
2497         return -TARGET_EFAULT;
2498 
2499     for(i=0; i<nsems; i++) {
2500         __put_user((*host_array)[i], &array[i]);
2501     }
2502     free(*host_array);
2503     unlock_user(array, target_addr, 1);
2504 
2505     return 0;
2506 }
2507 
2508 static inline abi_long do_semctl(int semid, int semnum, int cmd,
2509                                  union target_semun target_su)
2510 {
2511     union semun arg;
2512     struct semid_ds dsarg;
2513     unsigned short *array = NULL;
2514     struct seminfo seminfo;
2515     abi_long ret = -TARGET_EINVAL;
2516     abi_long err;
2517     cmd &= 0xff;
2518 
2519     switch( cmd ) {
2520 	case GETVAL:
2521 	case SETVAL:
2522             arg.val = tswap32(target_su.val);
2523             ret = get_errno(semctl(semid, semnum, cmd, arg));
2524             target_su.val = tswap32(arg.val);
2525             break;
2526 	case GETALL:
2527 	case SETALL:
2528             err = target_to_host_semarray(semid, &array, target_su.array);
2529             if (err)
2530                 return err;
2531             arg.array = array;
2532             ret = get_errno(semctl(semid, semnum, cmd, arg));
2533             err = host_to_target_semarray(semid, target_su.array, &array);
2534             if (err)
2535                 return err;
2536             break;
2537 	case IPC_STAT:
2538 	case IPC_SET:
2539 	case SEM_STAT:
2540             err = target_to_host_semid_ds(&dsarg, target_su.buf);
2541             if (err)
2542                 return err;
2543             arg.buf = &dsarg;
2544             ret = get_errno(semctl(semid, semnum, cmd, arg));
2545             err = host_to_target_semid_ds(target_su.buf, &dsarg);
2546             if (err)
2547                 return err;
2548             break;
2549 	case IPC_INFO:
2550 	case SEM_INFO:
2551             arg.__buf = &seminfo;
2552             ret = get_errno(semctl(semid, semnum, cmd, arg));
2553             err = host_to_target_seminfo(target_su.__buf, &seminfo);
2554             if (err)
2555                 return err;
2556             break;
2557 	case IPC_RMID:
2558 	case GETPID:
2559 	case GETNCNT:
2560 	case GETZCNT:
2561             ret = get_errno(semctl(semid, semnum, cmd, NULL));
2562             break;
2563     }
2564 
2565     return ret;
2566 }
2567 
2568 struct target_sembuf {
2569     unsigned short sem_num;
2570     short sem_op;
2571     short sem_flg;
2572 };
2573 
2574 static inline abi_long target_to_host_sembuf(struct sembuf *host_sembuf,
2575                                              abi_ulong target_addr,
2576                                              unsigned nsops)
2577 {
2578     struct target_sembuf *target_sembuf;
2579     int i;
2580 
2581     target_sembuf = lock_user(VERIFY_READ, target_addr,
2582                               nsops*sizeof(struct target_sembuf), 1);
2583     if (!target_sembuf)
2584         return -TARGET_EFAULT;
2585 
2586     for(i=0; i<nsops; i++) {
2587         __get_user(host_sembuf[i].sem_num, &target_sembuf[i].sem_num);
2588         __get_user(host_sembuf[i].sem_op, &target_sembuf[i].sem_op);
2589         __get_user(host_sembuf[i].sem_flg, &target_sembuf[i].sem_flg);
2590     }
2591 
2592     unlock_user(target_sembuf, target_addr, 0);
2593 
2594     return 0;
2595 }
2596 
2597 static inline abi_long do_semop(int semid, abi_long ptr, unsigned nsops)
2598 {
2599     struct sembuf sops[nsops];
2600 
2601     if (target_to_host_sembuf(sops, ptr, nsops))
2602         return -TARGET_EFAULT;
2603 
2604     return get_errno(semop(semid, sops, nsops));
2605 }
2606 
2607 struct target_msqid_ds
2608 {
2609     struct target_ipc_perm msg_perm;
2610     abi_ulong msg_stime;
2611 #if TARGET_ABI_BITS == 32
2612     abi_ulong __unused1;
2613 #endif
2614     abi_ulong msg_rtime;
2615 #if TARGET_ABI_BITS == 32
2616     abi_ulong __unused2;
2617 #endif
2618     abi_ulong msg_ctime;
2619 #if TARGET_ABI_BITS == 32
2620     abi_ulong __unused3;
2621 #endif
2622     abi_ulong __msg_cbytes;
2623     abi_ulong msg_qnum;
2624     abi_ulong msg_qbytes;
2625     abi_ulong msg_lspid;
2626     abi_ulong msg_lrpid;
2627     abi_ulong __unused4;
2628     abi_ulong __unused5;
2629 };
2630 
2631 static inline abi_long target_to_host_msqid_ds(struct msqid_ds *host_md,
2632                                                abi_ulong target_addr)
2633 {
2634     struct target_msqid_ds *target_md;
2635 
2636     if (!lock_user_struct(VERIFY_READ, target_md, target_addr, 1))
2637         return -TARGET_EFAULT;
2638     if (target_to_host_ipc_perm(&(host_md->msg_perm),target_addr))
2639         return -TARGET_EFAULT;
2640     host_md->msg_stime = tswapal(target_md->msg_stime);
2641     host_md->msg_rtime = tswapal(target_md->msg_rtime);
2642     host_md->msg_ctime = tswapal(target_md->msg_ctime);
2643     host_md->__msg_cbytes = tswapal(target_md->__msg_cbytes);
2644     host_md->msg_qnum = tswapal(target_md->msg_qnum);
2645     host_md->msg_qbytes = tswapal(target_md->msg_qbytes);
2646     host_md->msg_lspid = tswapal(target_md->msg_lspid);
2647     host_md->msg_lrpid = tswapal(target_md->msg_lrpid);
2648     unlock_user_struct(target_md, target_addr, 0);
2649     return 0;
2650 }
2651 
2652 static inline abi_long host_to_target_msqid_ds(abi_ulong target_addr,
2653                                                struct msqid_ds *host_md)
2654 {
2655     struct target_msqid_ds *target_md;
2656 
2657     if (!lock_user_struct(VERIFY_WRITE, target_md, target_addr, 0))
2658         return -TARGET_EFAULT;
2659     if (host_to_target_ipc_perm(target_addr,&(host_md->msg_perm)))
2660         return -TARGET_EFAULT;
2661     target_md->msg_stime = tswapal(host_md->msg_stime);
2662     target_md->msg_rtime = tswapal(host_md->msg_rtime);
2663     target_md->msg_ctime = tswapal(host_md->msg_ctime);
2664     target_md->__msg_cbytes = tswapal(host_md->__msg_cbytes);
2665     target_md->msg_qnum = tswapal(host_md->msg_qnum);
2666     target_md->msg_qbytes = tswapal(host_md->msg_qbytes);
2667     target_md->msg_lspid = tswapal(host_md->msg_lspid);
2668     target_md->msg_lrpid = tswapal(host_md->msg_lrpid);
2669     unlock_user_struct(target_md, target_addr, 1);
2670     return 0;
2671 }
2672 
2673 struct target_msginfo {
2674     int msgpool;
2675     int msgmap;
2676     int msgmax;
2677     int msgmnb;
2678     int msgmni;
2679     int msgssz;
2680     int msgtql;
2681     unsigned short int msgseg;
2682 };
2683 
2684 static inline abi_long host_to_target_msginfo(abi_ulong target_addr,
2685                                               struct msginfo *host_msginfo)
2686 {
2687     struct target_msginfo *target_msginfo;
2688     if (!lock_user_struct(VERIFY_WRITE, target_msginfo, target_addr, 0))
2689         return -TARGET_EFAULT;
2690     __put_user(host_msginfo->msgpool, &target_msginfo->msgpool);
2691     __put_user(host_msginfo->msgmap, &target_msginfo->msgmap);
2692     __put_user(host_msginfo->msgmax, &target_msginfo->msgmax);
2693     __put_user(host_msginfo->msgmnb, &target_msginfo->msgmnb);
2694     __put_user(host_msginfo->msgmni, &target_msginfo->msgmni);
2695     __put_user(host_msginfo->msgssz, &target_msginfo->msgssz);
2696     __put_user(host_msginfo->msgtql, &target_msginfo->msgtql);
2697     __put_user(host_msginfo->msgseg, &target_msginfo->msgseg);
2698     unlock_user_struct(target_msginfo, target_addr, 1);
2699     return 0;
2700 }
2701 
2702 static inline abi_long do_msgctl(int msgid, int cmd, abi_long ptr)
2703 {
2704     struct msqid_ds dsarg;
2705     struct msginfo msginfo;
2706     abi_long ret = -TARGET_EINVAL;
2707 
2708     cmd &= 0xff;
2709 
2710     switch (cmd) {
2711     case IPC_STAT:
2712     case IPC_SET:
2713     case MSG_STAT:
2714         if (target_to_host_msqid_ds(&dsarg,ptr))
2715             return -TARGET_EFAULT;
2716         ret = get_errno(msgctl(msgid, cmd, &dsarg));
2717         if (host_to_target_msqid_ds(ptr,&dsarg))
2718             return -TARGET_EFAULT;
2719         break;
2720     case IPC_RMID:
2721         ret = get_errno(msgctl(msgid, cmd, NULL));
2722         break;
2723     case IPC_INFO:
2724     case MSG_INFO:
2725         ret = get_errno(msgctl(msgid, cmd, (struct msqid_ds *)&msginfo));
2726         if (host_to_target_msginfo(ptr, &msginfo))
2727             return -TARGET_EFAULT;
2728         break;
2729     }
2730 
2731     return ret;
2732 }
2733 
2734 struct target_msgbuf {
2735     abi_long mtype;
2736     char	mtext[1];
2737 };
2738 
2739 static inline abi_long do_msgsnd(int msqid, abi_long msgp,
2740                                  unsigned int msgsz, int msgflg)
2741 {
2742     struct target_msgbuf *target_mb;
2743     struct msgbuf *host_mb;
2744     abi_long ret = 0;
2745 
2746     if (!lock_user_struct(VERIFY_READ, target_mb, msgp, 0))
2747         return -TARGET_EFAULT;
2748     host_mb = malloc(msgsz+sizeof(long));
2749     host_mb->mtype = (abi_long) tswapal(target_mb->mtype);
2750     memcpy(host_mb->mtext, target_mb->mtext, msgsz);
2751     ret = get_errno(msgsnd(msqid, host_mb, msgsz, msgflg));
2752     free(host_mb);
2753     unlock_user_struct(target_mb, msgp, 0);
2754 
2755     return ret;
2756 }
2757 
2758 static inline abi_long do_msgrcv(int msqid, abi_long msgp,
2759                                  unsigned int msgsz, abi_long msgtyp,
2760                                  int msgflg)
2761 {
2762     struct target_msgbuf *target_mb;
2763     char *target_mtext;
2764     struct msgbuf *host_mb;
2765     abi_long ret = 0;
2766 
2767     if (!lock_user_struct(VERIFY_WRITE, target_mb, msgp, 0))
2768         return -TARGET_EFAULT;
2769 
2770     host_mb = g_malloc(msgsz+sizeof(long));
2771     ret = get_errno(msgrcv(msqid, host_mb, msgsz, msgtyp, msgflg));
2772 
2773     if (ret > 0) {
2774         abi_ulong target_mtext_addr = msgp + sizeof(abi_ulong);
2775         target_mtext = lock_user(VERIFY_WRITE, target_mtext_addr, ret, 0);
2776         if (!target_mtext) {
2777             ret = -TARGET_EFAULT;
2778             goto end;
2779         }
2780         memcpy(target_mb->mtext, host_mb->mtext, ret);
2781         unlock_user(target_mtext, target_mtext_addr, ret);
2782     }
2783 
2784     target_mb->mtype = tswapal(host_mb->mtype);
2785 
2786 end:
2787     if (target_mb)
2788         unlock_user_struct(target_mb, msgp, 1);
2789     g_free(host_mb);
2790     return ret;
2791 }
2792 
2793 struct target_shmid_ds
2794 {
2795     struct target_ipc_perm shm_perm;
2796     abi_ulong shm_segsz;
2797     abi_ulong shm_atime;
2798 #if TARGET_ABI_BITS == 32
2799     abi_ulong __unused1;
2800 #endif
2801     abi_ulong shm_dtime;
2802 #if TARGET_ABI_BITS == 32
2803     abi_ulong __unused2;
2804 #endif
2805     abi_ulong shm_ctime;
2806 #if TARGET_ABI_BITS == 32
2807     abi_ulong __unused3;
2808 #endif
2809     int shm_cpid;
2810     int shm_lpid;
2811     abi_ulong shm_nattch;
2812     unsigned long int __unused4;
2813     unsigned long int __unused5;
2814 };
2815 
2816 static inline abi_long target_to_host_shmid_ds(struct shmid_ds *host_sd,
2817                                                abi_ulong target_addr)
2818 {
2819     struct target_shmid_ds *target_sd;
2820 
2821     if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2822         return -TARGET_EFAULT;
2823     if (target_to_host_ipc_perm(&(host_sd->shm_perm), target_addr))
2824         return -TARGET_EFAULT;
2825     __get_user(host_sd->shm_segsz, &target_sd->shm_segsz);
2826     __get_user(host_sd->shm_atime, &target_sd->shm_atime);
2827     __get_user(host_sd->shm_dtime, &target_sd->shm_dtime);
2828     __get_user(host_sd->shm_ctime, &target_sd->shm_ctime);
2829     __get_user(host_sd->shm_cpid, &target_sd->shm_cpid);
2830     __get_user(host_sd->shm_lpid, &target_sd->shm_lpid);
2831     __get_user(host_sd->shm_nattch, &target_sd->shm_nattch);
2832     unlock_user_struct(target_sd, target_addr, 0);
2833     return 0;
2834 }
2835 
2836 static inline abi_long host_to_target_shmid_ds(abi_ulong target_addr,
2837                                                struct shmid_ds *host_sd)
2838 {
2839     struct target_shmid_ds *target_sd;
2840 
2841     if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2842         return -TARGET_EFAULT;
2843     if (host_to_target_ipc_perm(target_addr, &(host_sd->shm_perm)))
2844         return -TARGET_EFAULT;
2845     __put_user(host_sd->shm_segsz, &target_sd->shm_segsz);
2846     __put_user(host_sd->shm_atime, &target_sd->shm_atime);
2847     __put_user(host_sd->shm_dtime, &target_sd->shm_dtime);
2848     __put_user(host_sd->shm_ctime, &target_sd->shm_ctime);
2849     __put_user(host_sd->shm_cpid, &target_sd->shm_cpid);
2850     __put_user(host_sd->shm_lpid, &target_sd->shm_lpid);
2851     __put_user(host_sd->shm_nattch, &target_sd->shm_nattch);
2852     unlock_user_struct(target_sd, target_addr, 1);
2853     return 0;
2854 }
2855 
2856 struct  target_shminfo {
2857     abi_ulong shmmax;
2858     abi_ulong shmmin;
2859     abi_ulong shmmni;
2860     abi_ulong shmseg;
2861     abi_ulong shmall;
2862 };
2863 
2864 static inline abi_long host_to_target_shminfo(abi_ulong target_addr,
2865                                               struct shminfo *host_shminfo)
2866 {
2867     struct target_shminfo *target_shminfo;
2868     if (!lock_user_struct(VERIFY_WRITE, target_shminfo, target_addr, 0))
2869         return -TARGET_EFAULT;
2870     __put_user(host_shminfo->shmmax, &target_shminfo->shmmax);
2871     __put_user(host_shminfo->shmmin, &target_shminfo->shmmin);
2872     __put_user(host_shminfo->shmmni, &target_shminfo->shmmni);
2873     __put_user(host_shminfo->shmseg, &target_shminfo->shmseg);
2874     __put_user(host_shminfo->shmall, &target_shminfo->shmall);
2875     unlock_user_struct(target_shminfo, target_addr, 1);
2876     return 0;
2877 }
2878 
2879 struct target_shm_info {
2880     int used_ids;
2881     abi_ulong shm_tot;
2882     abi_ulong shm_rss;
2883     abi_ulong shm_swp;
2884     abi_ulong swap_attempts;
2885     abi_ulong swap_successes;
2886 };
2887 
2888 static inline abi_long host_to_target_shm_info(abi_ulong target_addr,
2889                                                struct shm_info *host_shm_info)
2890 {
2891     struct target_shm_info *target_shm_info;
2892     if (!lock_user_struct(VERIFY_WRITE, target_shm_info, target_addr, 0))
2893         return -TARGET_EFAULT;
2894     __put_user(host_shm_info->used_ids, &target_shm_info->used_ids);
2895     __put_user(host_shm_info->shm_tot, &target_shm_info->shm_tot);
2896     __put_user(host_shm_info->shm_rss, &target_shm_info->shm_rss);
2897     __put_user(host_shm_info->shm_swp, &target_shm_info->shm_swp);
2898     __put_user(host_shm_info->swap_attempts, &target_shm_info->swap_attempts);
2899     __put_user(host_shm_info->swap_successes, &target_shm_info->swap_successes);
2900     unlock_user_struct(target_shm_info, target_addr, 1);
2901     return 0;
2902 }
2903 
2904 static inline abi_long do_shmctl(int shmid, int cmd, abi_long buf)
2905 {
2906     struct shmid_ds dsarg;
2907     struct shminfo shminfo;
2908     struct shm_info shm_info;
2909     abi_long ret = -TARGET_EINVAL;
2910 
2911     cmd &= 0xff;
2912 
2913     switch(cmd) {
2914     case IPC_STAT:
2915     case IPC_SET:
2916     case SHM_STAT:
2917         if (target_to_host_shmid_ds(&dsarg, buf))
2918             return -TARGET_EFAULT;
2919         ret = get_errno(shmctl(shmid, cmd, &dsarg));
2920         if (host_to_target_shmid_ds(buf, &dsarg))
2921             return -TARGET_EFAULT;
2922         break;
2923     case IPC_INFO:
2924         ret = get_errno(shmctl(shmid, cmd, (struct shmid_ds *)&shminfo));
2925         if (host_to_target_shminfo(buf, &shminfo))
2926             return -TARGET_EFAULT;
2927         break;
2928     case SHM_INFO:
2929         ret = get_errno(shmctl(shmid, cmd, (struct shmid_ds *)&shm_info));
2930         if (host_to_target_shm_info(buf, &shm_info))
2931             return -TARGET_EFAULT;
2932         break;
2933     case IPC_RMID:
2934     case SHM_LOCK:
2935     case SHM_UNLOCK:
2936         ret = get_errno(shmctl(shmid, cmd, NULL));
2937         break;
2938     }
2939 
2940     return ret;
2941 }
2942 
2943 static inline abi_ulong do_shmat(int shmid, abi_ulong shmaddr, int shmflg)
2944 {
2945     abi_long raddr;
2946     void *host_raddr;
2947     struct shmid_ds shm_info;
2948     int i,ret;
2949 
2950     /* find out the length of the shared memory segment */
2951     ret = get_errno(shmctl(shmid, IPC_STAT, &shm_info));
2952     if (is_error(ret)) {
2953         /* can't get length, bail out */
2954         return ret;
2955     }
2956 
2957     mmap_lock();
2958 
2959     if (shmaddr)
2960         host_raddr = shmat(shmid, (void *)g2h(shmaddr), shmflg);
2961     else {
2962         abi_ulong mmap_start;
2963 
2964         mmap_start = mmap_find_vma(0, shm_info.shm_segsz);
2965 
2966         if (mmap_start == -1) {
2967             errno = ENOMEM;
2968             host_raddr = (void *)-1;
2969         } else
2970             host_raddr = shmat(shmid, g2h(mmap_start), shmflg | SHM_REMAP);
2971     }
2972 
2973     if (host_raddr == (void *)-1) {
2974         mmap_unlock();
2975         return get_errno((long)host_raddr);
2976     }
2977     raddr=h2g((unsigned long)host_raddr);
2978 
2979     page_set_flags(raddr, raddr + shm_info.shm_segsz,
2980                    PAGE_VALID | PAGE_READ |
2981                    ((shmflg & SHM_RDONLY)? 0 : PAGE_WRITE));
2982 
2983     for (i = 0; i < N_SHM_REGIONS; i++) {
2984         if (shm_regions[i].start == 0) {
2985             shm_regions[i].start = raddr;
2986             shm_regions[i].size = shm_info.shm_segsz;
2987             break;
2988         }
2989     }
2990 
2991     mmap_unlock();
2992     return raddr;
2993 
2994 }
2995 
2996 static inline abi_long do_shmdt(abi_ulong shmaddr)
2997 {
2998     int i;
2999 
3000     for (i = 0; i < N_SHM_REGIONS; ++i) {
3001         if (shm_regions[i].start == shmaddr) {
3002             shm_regions[i].start = 0;
3003             page_set_flags(shmaddr, shmaddr + shm_regions[i].size, 0);
3004             break;
3005         }
3006     }
3007 
3008     return get_errno(shmdt(g2h(shmaddr)));
3009 }
3010 
3011 #ifdef TARGET_NR_ipc
3012 /* ??? This only works with linear mappings.  */
3013 /* do_ipc() must return target values and target errnos. */
3014 static abi_long do_ipc(unsigned int call, int first,
3015                        int second, int third,
3016                        abi_long ptr, abi_long fifth)
3017 {
3018     int version;
3019     abi_long ret = 0;
3020 
3021     version = call >> 16;
3022     call &= 0xffff;
3023 
3024     switch (call) {
3025     case IPCOP_semop:
3026         ret = do_semop(first, ptr, second);
3027         break;
3028 
3029     case IPCOP_semget:
3030         ret = get_errno(semget(first, second, third));
3031         break;
3032 
3033     case IPCOP_semctl:
3034         ret = do_semctl(first, second, third, (union target_semun)(abi_ulong) ptr);
3035         break;
3036 
3037     case IPCOP_msgget:
3038         ret = get_errno(msgget(first, second));
3039         break;
3040 
3041     case IPCOP_msgsnd:
3042         ret = do_msgsnd(first, ptr, second, third);
3043         break;
3044 
3045     case IPCOP_msgctl:
3046         ret = do_msgctl(first, second, ptr);
3047         break;
3048 
3049     case IPCOP_msgrcv:
3050         switch (version) {
3051         case 0:
3052             {
3053                 struct target_ipc_kludge {
3054                     abi_long msgp;
3055                     abi_long msgtyp;
3056                 } *tmp;
3057 
3058                 if (!lock_user_struct(VERIFY_READ, tmp, ptr, 1)) {
3059                     ret = -TARGET_EFAULT;
3060                     break;
3061                 }
3062 
3063                 ret = do_msgrcv(first, tswapal(tmp->msgp), second, tswapal(tmp->msgtyp), third);
3064 
3065                 unlock_user_struct(tmp, ptr, 0);
3066                 break;
3067             }
3068         default:
3069             ret = do_msgrcv(first, ptr, second, fifth, third);
3070         }
3071         break;
3072 
3073     case IPCOP_shmat:
3074         switch (version) {
3075         default:
3076         {
3077             abi_ulong raddr;
3078             raddr = do_shmat(first, ptr, second);
3079             if (is_error(raddr))
3080                 return get_errno(raddr);
3081             if (put_user_ual(raddr, third))
3082                 return -TARGET_EFAULT;
3083             break;
3084         }
3085         case 1:
3086             ret = -TARGET_EINVAL;
3087             break;
3088         }
3089 	break;
3090     case IPCOP_shmdt:
3091         ret = do_shmdt(ptr);
3092 	break;
3093 
3094     case IPCOP_shmget:
3095 	/* IPC_* flag values are the same on all linux platforms */
3096 	ret = get_errno(shmget(first, second, third));
3097 	break;
3098 
3099 	/* IPC_* and SHM_* command values are the same on all linux platforms */
3100     case IPCOP_shmctl:
3101         ret = do_shmctl(first, second, third);
3102         break;
3103     default:
3104 	gemu_log("Unsupported ipc call: %d (version %d)\n", call, version);
3105 	ret = -TARGET_ENOSYS;
3106 	break;
3107     }
3108     return ret;
3109 }
3110 #endif
3111 
3112 /* kernel structure types definitions */
3113 
3114 #define STRUCT(name, ...) STRUCT_ ## name,
3115 #define STRUCT_SPECIAL(name) STRUCT_ ## name,
3116 enum {
3117 #include "syscall_types.h"
3118 };
3119 #undef STRUCT
3120 #undef STRUCT_SPECIAL
3121 
3122 #define STRUCT(name, ...) static const argtype struct_ ## name ## _def[] = {  __VA_ARGS__, TYPE_NULL };
3123 #define STRUCT_SPECIAL(name)
3124 #include "syscall_types.h"
3125 #undef STRUCT
3126 #undef STRUCT_SPECIAL
3127 
3128 typedef struct IOCTLEntry IOCTLEntry;
3129 
3130 typedef abi_long do_ioctl_fn(const IOCTLEntry *ie, uint8_t *buf_temp,
3131                              int fd, abi_long cmd, abi_long arg);
3132 
3133 struct IOCTLEntry {
3134     unsigned int target_cmd;
3135     unsigned int host_cmd;
3136     const char *name;
3137     int access;
3138     do_ioctl_fn *do_ioctl;
3139     const argtype arg_type[5];
3140 };
3141 
3142 #define IOC_R 0x0001
3143 #define IOC_W 0x0002
3144 #define IOC_RW (IOC_R | IOC_W)
3145 
3146 #define MAX_STRUCT_SIZE 4096
3147 
3148 #ifdef CONFIG_FIEMAP
3149 /* So fiemap access checks don't overflow on 32 bit systems.
3150  * This is very slightly smaller than the limit imposed by
3151  * the underlying kernel.
3152  */
3153 #define FIEMAP_MAX_EXTENTS ((UINT_MAX - sizeof(struct fiemap))  \
3154                             / sizeof(struct fiemap_extent))
3155 
3156 static abi_long do_ioctl_fs_ioc_fiemap(const IOCTLEntry *ie, uint8_t *buf_temp,
3157                                        int fd, abi_long cmd, abi_long arg)
3158 {
3159     /* The parameter for this ioctl is a struct fiemap followed
3160      * by an array of struct fiemap_extent whose size is set
3161      * in fiemap->fm_extent_count. The array is filled in by the
3162      * ioctl.
3163      */
3164     int target_size_in, target_size_out;
3165     struct fiemap *fm;
3166     const argtype *arg_type = ie->arg_type;
3167     const argtype extent_arg_type[] = { MK_STRUCT(STRUCT_fiemap_extent) };
3168     void *argptr, *p;
3169     abi_long ret;
3170     int i, extent_size = thunk_type_size(extent_arg_type, 0);
3171     uint32_t outbufsz;
3172     int free_fm = 0;
3173 
3174     assert(arg_type[0] == TYPE_PTR);
3175     assert(ie->access == IOC_RW);
3176     arg_type++;
3177     target_size_in = thunk_type_size(arg_type, 0);
3178     argptr = lock_user(VERIFY_READ, arg, target_size_in, 1);
3179     if (!argptr) {
3180         return -TARGET_EFAULT;
3181     }
3182     thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
3183     unlock_user(argptr, arg, 0);
3184     fm = (struct fiemap *)buf_temp;
3185     if (fm->fm_extent_count > FIEMAP_MAX_EXTENTS) {
3186         return -TARGET_EINVAL;
3187     }
3188 
3189     outbufsz = sizeof (*fm) +
3190         (sizeof(struct fiemap_extent) * fm->fm_extent_count);
3191 
3192     if (outbufsz > MAX_STRUCT_SIZE) {
3193         /* We can't fit all the extents into the fixed size buffer.
3194          * Allocate one that is large enough and use it instead.
3195          */
3196         fm = malloc(outbufsz);
3197         if (!fm) {
3198             return -TARGET_ENOMEM;
3199         }
3200         memcpy(fm, buf_temp, sizeof(struct fiemap));
3201         free_fm = 1;
3202     }
3203     ret = get_errno(ioctl(fd, ie->host_cmd, fm));
3204     if (!is_error(ret)) {
3205         target_size_out = target_size_in;
3206         /* An extent_count of 0 means we were only counting the extents
3207          * so there are no structs to copy
3208          */
3209         if (fm->fm_extent_count != 0) {
3210             target_size_out += fm->fm_mapped_extents * extent_size;
3211         }
3212         argptr = lock_user(VERIFY_WRITE, arg, target_size_out, 0);
3213         if (!argptr) {
3214             ret = -TARGET_EFAULT;
3215         } else {
3216             /* Convert the struct fiemap */
3217             thunk_convert(argptr, fm, arg_type, THUNK_TARGET);
3218             if (fm->fm_extent_count != 0) {
3219                 p = argptr + target_size_in;
3220                 /* ...and then all the struct fiemap_extents */
3221                 for (i = 0; i < fm->fm_mapped_extents; i++) {
3222                     thunk_convert(p, &fm->fm_extents[i], extent_arg_type,
3223                                   THUNK_TARGET);
3224                     p += extent_size;
3225                 }
3226             }
3227             unlock_user(argptr, arg, target_size_out);
3228         }
3229     }
3230     if (free_fm) {
3231         free(fm);
3232     }
3233     return ret;
3234 }
3235 #endif
3236 
3237 static abi_long do_ioctl_ifconf(const IOCTLEntry *ie, uint8_t *buf_temp,
3238                                 int fd, abi_long cmd, abi_long arg)
3239 {
3240     const argtype *arg_type = ie->arg_type;
3241     int target_size;
3242     void *argptr;
3243     int ret;
3244     struct ifconf *host_ifconf;
3245     uint32_t outbufsz;
3246     const argtype ifreq_arg_type[] = { MK_STRUCT(STRUCT_sockaddr_ifreq) };
3247     int target_ifreq_size;
3248     int nb_ifreq;
3249     int free_buf = 0;
3250     int i;
3251     int target_ifc_len;
3252     abi_long target_ifc_buf;
3253     int host_ifc_len;
3254     char *host_ifc_buf;
3255 
3256     assert(arg_type[0] == TYPE_PTR);
3257     assert(ie->access == IOC_RW);
3258 
3259     arg_type++;
3260     target_size = thunk_type_size(arg_type, 0);
3261 
3262     argptr = lock_user(VERIFY_READ, arg, target_size, 1);
3263     if (!argptr)
3264         return -TARGET_EFAULT;
3265     thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
3266     unlock_user(argptr, arg, 0);
3267 
3268     host_ifconf = (struct ifconf *)(unsigned long)buf_temp;
3269     target_ifc_len = host_ifconf->ifc_len;
3270     target_ifc_buf = (abi_long)(unsigned long)host_ifconf->ifc_buf;
3271 
3272     target_ifreq_size = thunk_type_size(ifreq_arg_type, 0);
3273     nb_ifreq = target_ifc_len / target_ifreq_size;
3274     host_ifc_len = nb_ifreq * sizeof(struct ifreq);
3275 
3276     outbufsz = sizeof(*host_ifconf) + host_ifc_len;
3277     if (outbufsz > MAX_STRUCT_SIZE) {
3278         /* We can't fit all the extents into the fixed size buffer.
3279          * Allocate one that is large enough and use it instead.
3280          */
3281         host_ifconf = malloc(outbufsz);
3282         if (!host_ifconf) {
3283             return -TARGET_ENOMEM;
3284         }
3285         memcpy(host_ifconf, buf_temp, sizeof(*host_ifconf));
3286         free_buf = 1;
3287     }
3288     host_ifc_buf = (char*)host_ifconf + sizeof(*host_ifconf);
3289 
3290     host_ifconf->ifc_len = host_ifc_len;
3291     host_ifconf->ifc_buf = host_ifc_buf;
3292 
3293     ret = get_errno(ioctl(fd, ie->host_cmd, host_ifconf));
3294     if (!is_error(ret)) {
3295 	/* convert host ifc_len to target ifc_len */
3296 
3297         nb_ifreq = host_ifconf->ifc_len / sizeof(struct ifreq);
3298         target_ifc_len = nb_ifreq * target_ifreq_size;
3299         host_ifconf->ifc_len = target_ifc_len;
3300 
3301 	/* restore target ifc_buf */
3302 
3303         host_ifconf->ifc_buf = (char *)(unsigned long)target_ifc_buf;
3304 
3305 	/* copy struct ifconf to target user */
3306 
3307         argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
3308         if (!argptr)
3309             return -TARGET_EFAULT;
3310         thunk_convert(argptr, host_ifconf, arg_type, THUNK_TARGET);
3311         unlock_user(argptr, arg, target_size);
3312 
3313 	/* copy ifreq[] to target user */
3314 
3315         argptr = lock_user(VERIFY_WRITE, target_ifc_buf, target_ifc_len, 0);
3316         for (i = 0; i < nb_ifreq ; i++) {
3317             thunk_convert(argptr + i * target_ifreq_size,
3318                           host_ifc_buf + i * sizeof(struct ifreq),
3319                           ifreq_arg_type, THUNK_TARGET);
3320         }
3321         unlock_user(argptr, target_ifc_buf, target_ifc_len);
3322     }
3323 
3324     if (free_buf) {
3325         free(host_ifconf);
3326     }
3327 
3328     return ret;
3329 }
3330 
3331 static abi_long do_ioctl_dm(const IOCTLEntry *ie, uint8_t *buf_temp, int fd,
3332                             abi_long cmd, abi_long arg)
3333 {
3334     void *argptr;
3335     struct dm_ioctl *host_dm;
3336     abi_long guest_data;
3337     uint32_t guest_data_size;
3338     int target_size;
3339     const argtype *arg_type = ie->arg_type;
3340     abi_long ret;
3341     void *big_buf = NULL;
3342     char *host_data;
3343 
3344     arg_type++;
3345     target_size = thunk_type_size(arg_type, 0);
3346     argptr = lock_user(VERIFY_READ, arg, target_size, 1);
3347     if (!argptr) {
3348         ret = -TARGET_EFAULT;
3349         goto out;
3350     }
3351     thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
3352     unlock_user(argptr, arg, 0);
3353 
3354     /* buf_temp is too small, so fetch things into a bigger buffer */
3355     big_buf = g_malloc0(((struct dm_ioctl*)buf_temp)->data_size * 2);
3356     memcpy(big_buf, buf_temp, target_size);
3357     buf_temp = big_buf;
3358     host_dm = big_buf;
3359 
3360     guest_data = arg + host_dm->data_start;
3361     if ((guest_data - arg) < 0) {
3362         ret = -EINVAL;
3363         goto out;
3364     }
3365     guest_data_size = host_dm->data_size - host_dm->data_start;
3366     host_data = (char*)host_dm + host_dm->data_start;
3367 
3368     argptr = lock_user(VERIFY_READ, guest_data, guest_data_size, 1);
3369     switch (ie->host_cmd) {
3370     case DM_REMOVE_ALL:
3371     case DM_LIST_DEVICES:
3372     case DM_DEV_CREATE:
3373     case DM_DEV_REMOVE:
3374     case DM_DEV_SUSPEND:
3375     case DM_DEV_STATUS:
3376     case DM_DEV_WAIT:
3377     case DM_TABLE_STATUS:
3378     case DM_TABLE_CLEAR:
3379     case DM_TABLE_DEPS:
3380     case DM_LIST_VERSIONS:
3381         /* no input data */
3382         break;
3383     case DM_DEV_RENAME:
3384     case DM_DEV_SET_GEOMETRY:
3385         /* data contains only strings */
3386         memcpy(host_data, argptr, guest_data_size);
3387         break;
3388     case DM_TARGET_MSG:
3389         memcpy(host_data, argptr, guest_data_size);
3390         *(uint64_t*)host_data = tswap64(*(uint64_t*)argptr);
3391         break;
3392     case DM_TABLE_LOAD:
3393     {
3394         void *gspec = argptr;
3395         void *cur_data = host_data;
3396         const argtype arg_type[] = { MK_STRUCT(STRUCT_dm_target_spec) };
3397         int spec_size = thunk_type_size(arg_type, 0);
3398         int i;
3399 
3400         for (i = 0; i < host_dm->target_count; i++) {
3401             struct dm_target_spec *spec = cur_data;
3402             uint32_t next;
3403             int slen;
3404 
3405             thunk_convert(spec, gspec, arg_type, THUNK_HOST);
3406             slen = strlen((char*)gspec + spec_size) + 1;
3407             next = spec->next;
3408             spec->next = sizeof(*spec) + slen;
3409             strcpy((char*)&spec[1], gspec + spec_size);
3410             gspec += next;
3411             cur_data += spec->next;
3412         }
3413         break;
3414     }
3415     default:
3416         ret = -TARGET_EINVAL;
3417         goto out;
3418     }
3419     unlock_user(argptr, guest_data, 0);
3420 
3421     ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
3422     if (!is_error(ret)) {
3423         guest_data = arg + host_dm->data_start;
3424         guest_data_size = host_dm->data_size - host_dm->data_start;
3425         argptr = lock_user(VERIFY_WRITE, guest_data, guest_data_size, 0);
3426         switch (ie->host_cmd) {
3427         case DM_REMOVE_ALL:
3428         case DM_DEV_CREATE:
3429         case DM_DEV_REMOVE:
3430         case DM_DEV_RENAME:
3431         case DM_DEV_SUSPEND:
3432         case DM_DEV_STATUS:
3433         case DM_TABLE_LOAD:
3434         case DM_TABLE_CLEAR:
3435         case DM_TARGET_MSG:
3436         case DM_DEV_SET_GEOMETRY:
3437             /* no return data */
3438             break;
3439         case DM_LIST_DEVICES:
3440         {
3441             struct dm_name_list *nl = (void*)host_dm + host_dm->data_start;
3442             uint32_t remaining_data = guest_data_size;
3443             void *cur_data = argptr;
3444             const argtype arg_type[] = { MK_STRUCT(STRUCT_dm_name_list) };
3445             int nl_size = 12; /* can't use thunk_size due to alignment */
3446 
3447             while (1) {
3448                 uint32_t next = nl->next;
3449                 if (next) {
3450                     nl->next = nl_size + (strlen(nl->name) + 1);
3451                 }
3452                 if (remaining_data < nl->next) {
3453                     host_dm->flags |= DM_BUFFER_FULL_FLAG;
3454                     break;
3455                 }
3456                 thunk_convert(cur_data, nl, arg_type, THUNK_TARGET);
3457                 strcpy(cur_data + nl_size, nl->name);
3458                 cur_data += nl->next;
3459                 remaining_data -= nl->next;
3460                 if (!next) {
3461                     break;
3462                 }
3463                 nl = (void*)nl + next;
3464             }
3465             break;
3466         }
3467         case DM_DEV_WAIT:
3468         case DM_TABLE_STATUS:
3469         {
3470             struct dm_target_spec *spec = (void*)host_dm + host_dm->data_start;
3471             void *cur_data = argptr;
3472             const argtype arg_type[] = { MK_STRUCT(STRUCT_dm_target_spec) };
3473             int spec_size = thunk_type_size(arg_type, 0);
3474             int i;
3475 
3476             for (i = 0; i < host_dm->target_count; i++) {
3477                 uint32_t next = spec->next;
3478                 int slen = strlen((char*)&spec[1]) + 1;
3479                 spec->next = (cur_data - argptr) + spec_size + slen;
3480                 if (guest_data_size < spec->next) {
3481                     host_dm->flags |= DM_BUFFER_FULL_FLAG;
3482                     break;
3483                 }
3484                 thunk_convert(cur_data, spec, arg_type, THUNK_TARGET);
3485                 strcpy(cur_data + spec_size, (char*)&spec[1]);
3486                 cur_data = argptr + spec->next;
3487                 spec = (void*)host_dm + host_dm->data_start + next;
3488             }
3489             break;
3490         }
3491         case DM_TABLE_DEPS:
3492         {
3493             void *hdata = (void*)host_dm + host_dm->data_start;
3494             int count = *(uint32_t*)hdata;
3495             uint64_t *hdev = hdata + 8;
3496             uint64_t *gdev = argptr + 8;
3497             int i;
3498 
3499             *(uint32_t*)argptr = tswap32(count);
3500             for (i = 0; i < count; i++) {
3501                 *gdev = tswap64(*hdev);
3502                 gdev++;
3503                 hdev++;
3504             }
3505             break;
3506         }
3507         case DM_LIST_VERSIONS:
3508         {
3509             struct dm_target_versions *vers = (void*)host_dm + host_dm->data_start;
3510             uint32_t remaining_data = guest_data_size;
3511             void *cur_data = argptr;
3512             const argtype arg_type[] = { MK_STRUCT(STRUCT_dm_target_versions) };
3513             int vers_size = thunk_type_size(arg_type, 0);
3514 
3515             while (1) {
3516                 uint32_t next = vers->next;
3517                 if (next) {
3518                     vers->next = vers_size + (strlen(vers->name) + 1);
3519                 }
3520                 if (remaining_data < vers->next) {
3521                     host_dm->flags |= DM_BUFFER_FULL_FLAG;
3522                     break;
3523                 }
3524                 thunk_convert(cur_data, vers, arg_type, THUNK_TARGET);
3525                 strcpy(cur_data + vers_size, vers->name);
3526                 cur_data += vers->next;
3527                 remaining_data -= vers->next;
3528                 if (!next) {
3529                     break;
3530                 }
3531                 vers = (void*)vers + next;
3532             }
3533             break;
3534         }
3535         default:
3536             ret = -TARGET_EINVAL;
3537             goto out;
3538         }
3539         unlock_user(argptr, guest_data, guest_data_size);
3540 
3541         argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
3542         if (!argptr) {
3543             ret = -TARGET_EFAULT;
3544             goto out;
3545         }
3546         thunk_convert(argptr, buf_temp, arg_type, THUNK_TARGET);
3547         unlock_user(argptr, arg, target_size);
3548     }
3549 out:
3550     g_free(big_buf);
3551     return ret;
3552 }
3553 
3554 static IOCTLEntry ioctl_entries[] = {
3555 #define IOCTL(cmd, access, ...) \
3556     { TARGET_ ## cmd, cmd, #cmd, access, 0, {  __VA_ARGS__ } },
3557 #define IOCTL_SPECIAL(cmd, access, dofn, ...)                      \
3558     { TARGET_ ## cmd, cmd, #cmd, access, dofn, {  __VA_ARGS__ } },
3559 #include "ioctls.h"
3560     { 0, 0, },
3561 };
3562 
3563 /* ??? Implement proper locking for ioctls.  */
3564 /* do_ioctl() Must return target values and target errnos. */
3565 static abi_long do_ioctl(int fd, abi_long cmd, abi_long arg)
3566 {
3567     const IOCTLEntry *ie;
3568     const argtype *arg_type;
3569     abi_long ret;
3570     uint8_t buf_temp[MAX_STRUCT_SIZE];
3571     int target_size;
3572     void *argptr;
3573 
3574     ie = ioctl_entries;
3575     for(;;) {
3576         if (ie->target_cmd == 0) {
3577             gemu_log("Unsupported ioctl: cmd=0x%04lx\n", (long)cmd);
3578             return -TARGET_ENOSYS;
3579         }
3580         if (ie->target_cmd == cmd)
3581             break;
3582         ie++;
3583     }
3584     arg_type = ie->arg_type;
3585 #if defined(DEBUG)
3586     gemu_log("ioctl: cmd=0x%04lx (%s)\n", (long)cmd, ie->name);
3587 #endif
3588     if (ie->do_ioctl) {
3589         return ie->do_ioctl(ie, buf_temp, fd, cmd, arg);
3590     }
3591 
3592     switch(arg_type[0]) {
3593     case TYPE_NULL:
3594         /* no argument */
3595         ret = get_errno(ioctl(fd, ie->host_cmd));
3596         break;
3597     case TYPE_PTRVOID:
3598     case TYPE_INT:
3599         /* int argment */
3600         ret = get_errno(ioctl(fd, ie->host_cmd, arg));
3601         break;
3602     case TYPE_PTR:
3603         arg_type++;
3604         target_size = thunk_type_size(arg_type, 0);
3605         switch(ie->access) {
3606         case IOC_R:
3607             ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
3608             if (!is_error(ret)) {
3609                 argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
3610                 if (!argptr)
3611                     return -TARGET_EFAULT;
3612                 thunk_convert(argptr, buf_temp, arg_type, THUNK_TARGET);
3613                 unlock_user(argptr, arg, target_size);
3614             }
3615             break;
3616         case IOC_W:
3617             argptr = lock_user(VERIFY_READ, arg, target_size, 1);
3618             if (!argptr)
3619                 return -TARGET_EFAULT;
3620             thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
3621             unlock_user(argptr, arg, 0);
3622             ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
3623             break;
3624         default:
3625         case IOC_RW:
3626             argptr = lock_user(VERIFY_READ, arg, target_size, 1);
3627             if (!argptr)
3628                 return -TARGET_EFAULT;
3629             thunk_convert(buf_temp, argptr, arg_type, THUNK_HOST);
3630             unlock_user(argptr, arg, 0);
3631             ret = get_errno(ioctl(fd, ie->host_cmd, buf_temp));
3632             if (!is_error(ret)) {
3633                 argptr = lock_user(VERIFY_WRITE, arg, target_size, 0);
3634                 if (!argptr)
3635                     return -TARGET_EFAULT;
3636                 thunk_convert(argptr, buf_temp, arg_type, THUNK_TARGET);
3637                 unlock_user(argptr, arg, target_size);
3638             }
3639             break;
3640         }
3641         break;
3642     default:
3643         gemu_log("Unsupported ioctl type: cmd=0x%04lx type=%d\n",
3644                  (long)cmd, arg_type[0]);
3645         ret = -TARGET_ENOSYS;
3646         break;
3647     }
3648     return ret;
3649 }
3650 
3651 static const bitmask_transtbl iflag_tbl[] = {
3652         { TARGET_IGNBRK, TARGET_IGNBRK, IGNBRK, IGNBRK },
3653         { TARGET_BRKINT, TARGET_BRKINT, BRKINT, BRKINT },
3654         { TARGET_IGNPAR, TARGET_IGNPAR, IGNPAR, IGNPAR },
3655         { TARGET_PARMRK, TARGET_PARMRK, PARMRK, PARMRK },
3656         { TARGET_INPCK, TARGET_INPCK, INPCK, INPCK },
3657         { TARGET_ISTRIP, TARGET_ISTRIP, ISTRIP, ISTRIP },
3658         { TARGET_INLCR, TARGET_INLCR, INLCR, INLCR },
3659         { TARGET_IGNCR, TARGET_IGNCR, IGNCR, IGNCR },
3660         { TARGET_ICRNL, TARGET_ICRNL, ICRNL, ICRNL },
3661         { TARGET_IUCLC, TARGET_IUCLC, IUCLC, IUCLC },
3662         { TARGET_IXON, TARGET_IXON, IXON, IXON },
3663         { TARGET_IXANY, TARGET_IXANY, IXANY, IXANY },
3664         { TARGET_IXOFF, TARGET_IXOFF, IXOFF, IXOFF },
3665         { TARGET_IMAXBEL, TARGET_IMAXBEL, IMAXBEL, IMAXBEL },
3666         { 0, 0, 0, 0 }
3667 };
3668 
3669 static const bitmask_transtbl oflag_tbl[] = {
3670 	{ TARGET_OPOST, TARGET_OPOST, OPOST, OPOST },
3671 	{ TARGET_OLCUC, TARGET_OLCUC, OLCUC, OLCUC },
3672 	{ TARGET_ONLCR, TARGET_ONLCR, ONLCR, ONLCR },
3673 	{ TARGET_OCRNL, TARGET_OCRNL, OCRNL, OCRNL },
3674 	{ TARGET_ONOCR, TARGET_ONOCR, ONOCR, ONOCR },
3675 	{ TARGET_ONLRET, TARGET_ONLRET, ONLRET, ONLRET },
3676 	{ TARGET_OFILL, TARGET_OFILL, OFILL, OFILL },
3677 	{ TARGET_OFDEL, TARGET_OFDEL, OFDEL, OFDEL },
3678 	{ TARGET_NLDLY, TARGET_NL0, NLDLY, NL0 },
3679 	{ TARGET_NLDLY, TARGET_NL1, NLDLY, NL1 },
3680 	{ TARGET_CRDLY, TARGET_CR0, CRDLY, CR0 },
3681 	{ TARGET_CRDLY, TARGET_CR1, CRDLY, CR1 },
3682 	{ TARGET_CRDLY, TARGET_CR2, CRDLY, CR2 },
3683 	{ TARGET_CRDLY, TARGET_CR3, CRDLY, CR3 },
3684 	{ TARGET_TABDLY, TARGET_TAB0, TABDLY, TAB0 },
3685 	{ TARGET_TABDLY, TARGET_TAB1, TABDLY, TAB1 },
3686 	{ TARGET_TABDLY, TARGET_TAB2, TABDLY, TAB2 },
3687 	{ TARGET_TABDLY, TARGET_TAB3, TABDLY, TAB3 },
3688 	{ TARGET_BSDLY, TARGET_BS0, BSDLY, BS0 },
3689 	{ TARGET_BSDLY, TARGET_BS1, BSDLY, BS1 },
3690 	{ TARGET_VTDLY, TARGET_VT0, VTDLY, VT0 },
3691 	{ TARGET_VTDLY, TARGET_VT1, VTDLY, VT1 },
3692 	{ TARGET_FFDLY, TARGET_FF0, FFDLY, FF0 },
3693 	{ TARGET_FFDLY, TARGET_FF1, FFDLY, FF1 },
3694 	{ 0, 0, 0, 0 }
3695 };
3696 
3697 static const bitmask_transtbl cflag_tbl[] = {
3698 	{ TARGET_CBAUD, TARGET_B0, CBAUD, B0 },
3699 	{ TARGET_CBAUD, TARGET_B50, CBAUD, B50 },
3700 	{ TARGET_CBAUD, TARGET_B75, CBAUD, B75 },
3701 	{ TARGET_CBAUD, TARGET_B110, CBAUD, B110 },
3702 	{ TARGET_CBAUD, TARGET_B134, CBAUD, B134 },
3703 	{ TARGET_CBAUD, TARGET_B150, CBAUD, B150 },
3704 	{ TARGET_CBAUD, TARGET_B200, CBAUD, B200 },
3705 	{ TARGET_CBAUD, TARGET_B300, CBAUD, B300 },
3706 	{ TARGET_CBAUD, TARGET_B600, CBAUD, B600 },
3707 	{ TARGET_CBAUD, TARGET_B1200, CBAUD, B1200 },
3708 	{ TARGET_CBAUD, TARGET_B1800, CBAUD, B1800 },
3709 	{ TARGET_CBAUD, TARGET_B2400, CBAUD, B2400 },
3710 	{ TARGET_CBAUD, TARGET_B4800, CBAUD, B4800 },
3711 	{ TARGET_CBAUD, TARGET_B9600, CBAUD, B9600 },
3712 	{ TARGET_CBAUD, TARGET_B19200, CBAUD, B19200 },
3713 	{ TARGET_CBAUD, TARGET_B38400, CBAUD, B38400 },
3714 	{ TARGET_CBAUD, TARGET_B57600, CBAUD, B57600 },
3715 	{ TARGET_CBAUD, TARGET_B115200, CBAUD, B115200 },
3716 	{ TARGET_CBAUD, TARGET_B230400, CBAUD, B230400 },
3717 	{ TARGET_CBAUD, TARGET_B460800, CBAUD, B460800 },
3718 	{ TARGET_CSIZE, TARGET_CS5, CSIZE, CS5 },
3719 	{ TARGET_CSIZE, TARGET_CS6, CSIZE, CS6 },
3720 	{ TARGET_CSIZE, TARGET_CS7, CSIZE, CS7 },
3721 	{ TARGET_CSIZE, TARGET_CS8, CSIZE, CS8 },
3722 	{ TARGET_CSTOPB, TARGET_CSTOPB, CSTOPB, CSTOPB },
3723 	{ TARGET_CREAD, TARGET_CREAD, CREAD, CREAD },
3724 	{ TARGET_PARENB, TARGET_PARENB, PARENB, PARENB },
3725 	{ TARGET_PARODD, TARGET_PARODD, PARODD, PARODD },
3726 	{ TARGET_HUPCL, TARGET_HUPCL, HUPCL, HUPCL },
3727 	{ TARGET_CLOCAL, TARGET_CLOCAL, CLOCAL, CLOCAL },
3728 	{ TARGET_CRTSCTS, TARGET_CRTSCTS, CRTSCTS, CRTSCTS },
3729 	{ 0, 0, 0, 0 }
3730 };
3731 
3732 static const bitmask_transtbl lflag_tbl[] = {
3733 	{ TARGET_ISIG, TARGET_ISIG, ISIG, ISIG },
3734 	{ TARGET_ICANON, TARGET_ICANON, ICANON, ICANON },
3735 	{ TARGET_XCASE, TARGET_XCASE, XCASE, XCASE },
3736 	{ TARGET_ECHO, TARGET_ECHO, ECHO, ECHO },
3737 	{ TARGET_ECHOE, TARGET_ECHOE, ECHOE, ECHOE },
3738 	{ TARGET_ECHOK, TARGET_ECHOK, ECHOK, ECHOK },
3739 	{ TARGET_ECHONL, TARGET_ECHONL, ECHONL, ECHONL },
3740 	{ TARGET_NOFLSH, TARGET_NOFLSH, NOFLSH, NOFLSH },
3741 	{ TARGET_TOSTOP, TARGET_TOSTOP, TOSTOP, TOSTOP },
3742 	{ TARGET_ECHOCTL, TARGET_ECHOCTL, ECHOCTL, ECHOCTL },
3743 	{ TARGET_ECHOPRT, TARGET_ECHOPRT, ECHOPRT, ECHOPRT },
3744 	{ TARGET_ECHOKE, TARGET_ECHOKE, ECHOKE, ECHOKE },
3745 	{ TARGET_FLUSHO, TARGET_FLUSHO, FLUSHO, FLUSHO },
3746 	{ TARGET_PENDIN, TARGET_PENDIN, PENDIN, PENDIN },
3747 	{ TARGET_IEXTEN, TARGET_IEXTEN, IEXTEN, IEXTEN },
3748 	{ 0, 0, 0, 0 }
3749 };
3750 
3751 static void target_to_host_termios (void *dst, const void *src)
3752 {
3753     struct host_termios *host = dst;
3754     const struct target_termios *target = src;
3755 
3756     host->c_iflag =
3757         target_to_host_bitmask(tswap32(target->c_iflag), iflag_tbl);
3758     host->c_oflag =
3759         target_to_host_bitmask(tswap32(target->c_oflag), oflag_tbl);
3760     host->c_cflag =
3761         target_to_host_bitmask(tswap32(target->c_cflag), cflag_tbl);
3762     host->c_lflag =
3763         target_to_host_bitmask(tswap32(target->c_lflag), lflag_tbl);
3764     host->c_line = target->c_line;
3765 
3766     memset(host->c_cc, 0, sizeof(host->c_cc));
3767     host->c_cc[VINTR] = target->c_cc[TARGET_VINTR];
3768     host->c_cc[VQUIT] = target->c_cc[TARGET_VQUIT];
3769     host->c_cc[VERASE] = target->c_cc[TARGET_VERASE];
3770     host->c_cc[VKILL] = target->c_cc[TARGET_VKILL];
3771     host->c_cc[VEOF] = target->c_cc[TARGET_VEOF];
3772     host->c_cc[VTIME] = target->c_cc[TARGET_VTIME];
3773     host->c_cc[VMIN] = target->c_cc[TARGET_VMIN];
3774     host->c_cc[VSWTC] = target->c_cc[TARGET_VSWTC];
3775     host->c_cc[VSTART] = target->c_cc[TARGET_VSTART];
3776     host->c_cc[VSTOP] = target->c_cc[TARGET_VSTOP];
3777     host->c_cc[VSUSP] = target->c_cc[TARGET_VSUSP];
3778     host->c_cc[VEOL] = target->c_cc[TARGET_VEOL];
3779     host->c_cc[VREPRINT] = target->c_cc[TARGET_VREPRINT];
3780     host->c_cc[VDISCARD] = target->c_cc[TARGET_VDISCARD];
3781     host->c_cc[VWERASE] = target->c_cc[TARGET_VWERASE];
3782     host->c_cc[VLNEXT] = target->c_cc[TARGET_VLNEXT];
3783     host->c_cc[VEOL2] = target->c_cc[TARGET_VEOL2];
3784 }
3785 
3786 static void host_to_target_termios (void *dst, const void *src)
3787 {
3788     struct target_termios *target = dst;
3789     const struct host_termios *host = src;
3790 
3791     target->c_iflag =
3792         tswap32(host_to_target_bitmask(host->c_iflag, iflag_tbl));
3793     target->c_oflag =
3794         tswap32(host_to_target_bitmask(host->c_oflag, oflag_tbl));
3795     target->c_cflag =
3796         tswap32(host_to_target_bitmask(host->c_cflag, cflag_tbl));
3797     target->c_lflag =
3798         tswap32(host_to_target_bitmask(host->c_lflag, lflag_tbl));
3799     target->c_line = host->c_line;
3800 
3801     memset(target->c_cc, 0, sizeof(target->c_cc));
3802     target->c_cc[TARGET_VINTR] = host->c_cc[VINTR];
3803     target->c_cc[TARGET_VQUIT] = host->c_cc[VQUIT];
3804     target->c_cc[TARGET_VERASE] = host->c_cc[VERASE];
3805     target->c_cc[TARGET_VKILL] = host->c_cc[VKILL];
3806     target->c_cc[TARGET_VEOF] = host->c_cc[VEOF];
3807     target->c_cc[TARGET_VTIME] = host->c_cc[VTIME];
3808     target->c_cc[TARGET_VMIN] = host->c_cc[VMIN];
3809     target->c_cc[TARGET_VSWTC] = host->c_cc[VSWTC];
3810     target->c_cc[TARGET_VSTART] = host->c_cc[VSTART];
3811     target->c_cc[TARGET_VSTOP] = host->c_cc[VSTOP];
3812     target->c_cc[TARGET_VSUSP] = host->c_cc[VSUSP];
3813     target->c_cc[TARGET_VEOL] = host->c_cc[VEOL];
3814     target->c_cc[TARGET_VREPRINT] = host->c_cc[VREPRINT];
3815     target->c_cc[TARGET_VDISCARD] = host->c_cc[VDISCARD];
3816     target->c_cc[TARGET_VWERASE] = host->c_cc[VWERASE];
3817     target->c_cc[TARGET_VLNEXT] = host->c_cc[VLNEXT];
3818     target->c_cc[TARGET_VEOL2] = host->c_cc[VEOL2];
3819 }
3820 
3821 static const StructEntry struct_termios_def = {
3822     .convert = { host_to_target_termios, target_to_host_termios },
3823     .size = { sizeof(struct target_termios), sizeof(struct host_termios) },
3824     .align = { __alignof__(struct target_termios), __alignof__(struct host_termios) },
3825 };
3826 
3827 static bitmask_transtbl mmap_flags_tbl[] = {
3828 	{ TARGET_MAP_SHARED, TARGET_MAP_SHARED, MAP_SHARED, MAP_SHARED },
3829 	{ TARGET_MAP_PRIVATE, TARGET_MAP_PRIVATE, MAP_PRIVATE, MAP_PRIVATE },
3830 	{ TARGET_MAP_FIXED, TARGET_MAP_FIXED, MAP_FIXED, MAP_FIXED },
3831 	{ TARGET_MAP_ANONYMOUS, TARGET_MAP_ANONYMOUS, MAP_ANONYMOUS, MAP_ANONYMOUS },
3832 	{ TARGET_MAP_GROWSDOWN, TARGET_MAP_GROWSDOWN, MAP_GROWSDOWN, MAP_GROWSDOWN },
3833 	{ TARGET_MAP_DENYWRITE, TARGET_MAP_DENYWRITE, MAP_DENYWRITE, MAP_DENYWRITE },
3834 	{ TARGET_MAP_EXECUTABLE, TARGET_MAP_EXECUTABLE, MAP_EXECUTABLE, MAP_EXECUTABLE },
3835 	{ TARGET_MAP_LOCKED, TARGET_MAP_LOCKED, MAP_LOCKED, MAP_LOCKED },
3836 	{ 0, 0, 0, 0 }
3837 };
3838 
3839 #if defined(TARGET_I386)
3840 
3841 /* NOTE: there is really one LDT for all the threads */
3842 static uint8_t *ldt_table;
3843 
3844 static abi_long read_ldt(abi_ulong ptr, unsigned long bytecount)
3845 {
3846     int size;
3847     void *p;
3848 
3849     if (!ldt_table)
3850         return 0;
3851     size = TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE;
3852     if (size > bytecount)
3853         size = bytecount;
3854     p = lock_user(VERIFY_WRITE, ptr, size, 0);
3855     if (!p)
3856         return -TARGET_EFAULT;
3857     /* ??? Should this by byteswapped?  */
3858     memcpy(p, ldt_table, size);
3859     unlock_user(p, ptr, size);
3860     return size;
3861 }
3862 
3863 /* XXX: add locking support */
3864 static abi_long write_ldt(CPUX86State *env,
3865                           abi_ulong ptr, unsigned long bytecount, int oldmode)
3866 {
3867     struct target_modify_ldt_ldt_s ldt_info;
3868     struct target_modify_ldt_ldt_s *target_ldt_info;
3869     int seg_32bit, contents, read_exec_only, limit_in_pages;
3870     int seg_not_present, useable, lm;
3871     uint32_t *lp, entry_1, entry_2;
3872 
3873     if (bytecount != sizeof(ldt_info))
3874         return -TARGET_EINVAL;
3875     if (!lock_user_struct(VERIFY_READ, target_ldt_info, ptr, 1))
3876         return -TARGET_EFAULT;
3877     ldt_info.entry_number = tswap32(target_ldt_info->entry_number);
3878     ldt_info.base_addr = tswapal(target_ldt_info->base_addr);
3879     ldt_info.limit = tswap32(target_ldt_info->limit);
3880     ldt_info.flags = tswap32(target_ldt_info->flags);
3881     unlock_user_struct(target_ldt_info, ptr, 0);
3882 
3883     if (ldt_info.entry_number >= TARGET_LDT_ENTRIES)
3884         return -TARGET_EINVAL;
3885     seg_32bit = ldt_info.flags & 1;
3886     contents = (ldt_info.flags >> 1) & 3;
3887     read_exec_only = (ldt_info.flags >> 3) & 1;
3888     limit_in_pages = (ldt_info.flags >> 4) & 1;
3889     seg_not_present = (ldt_info.flags >> 5) & 1;
3890     useable = (ldt_info.flags >> 6) & 1;
3891 #ifdef TARGET_ABI32
3892     lm = 0;
3893 #else
3894     lm = (ldt_info.flags >> 7) & 1;
3895 #endif
3896     if (contents == 3) {
3897         if (oldmode)
3898             return -TARGET_EINVAL;
3899         if (seg_not_present == 0)
3900             return -TARGET_EINVAL;
3901     }
3902     /* allocate the LDT */
3903     if (!ldt_table) {
3904         env->ldt.base = target_mmap(0,
3905                                     TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE,
3906                                     PROT_READ|PROT_WRITE,
3907                                     MAP_ANONYMOUS|MAP_PRIVATE, -1, 0);
3908         if (env->ldt.base == -1)
3909             return -TARGET_ENOMEM;
3910         memset(g2h(env->ldt.base), 0,
3911                TARGET_LDT_ENTRIES * TARGET_LDT_ENTRY_SIZE);
3912         env->ldt.limit = 0xffff;
3913         ldt_table = g2h(env->ldt.base);
3914     }
3915 
3916     /* NOTE: same code as Linux kernel */
3917     /* Allow LDTs to be cleared by the user. */
3918     if (ldt_info.base_addr == 0 && ldt_info.limit == 0) {
3919         if (oldmode ||
3920             (contents == 0		&&
3921              read_exec_only == 1	&&
3922              seg_32bit == 0		&&
3923              limit_in_pages == 0	&&
3924              seg_not_present == 1	&&
3925              useable == 0 )) {
3926             entry_1 = 0;
3927             entry_2 = 0;
3928             goto install;
3929         }
3930     }
3931 
3932     entry_1 = ((ldt_info.base_addr & 0x0000ffff) << 16) |
3933         (ldt_info.limit & 0x0ffff);
3934     entry_2 = (ldt_info.base_addr & 0xff000000) |
3935         ((ldt_info.base_addr & 0x00ff0000) >> 16) |
3936         (ldt_info.limit & 0xf0000) |
3937         ((read_exec_only ^ 1) << 9) |
3938         (contents << 10) |
3939         ((seg_not_present ^ 1) << 15) |
3940         (seg_32bit << 22) |
3941         (limit_in_pages << 23) |
3942         (lm << 21) |
3943         0x7000;
3944     if (!oldmode)
3945         entry_2 |= (useable << 20);
3946 
3947     /* Install the new entry ...  */
3948 install:
3949     lp = (uint32_t *)(ldt_table + (ldt_info.entry_number << 3));
3950     lp[0] = tswap32(entry_1);
3951     lp[1] = tswap32(entry_2);
3952     return 0;
3953 }
3954 
3955 /* specific and weird i386 syscalls */
3956 static abi_long do_modify_ldt(CPUX86State *env, int func, abi_ulong ptr,
3957                               unsigned long bytecount)
3958 {
3959     abi_long ret;
3960 
3961     switch (func) {
3962     case 0:
3963         ret = read_ldt(ptr, bytecount);
3964         break;
3965     case 1:
3966         ret = write_ldt(env, ptr, bytecount, 1);
3967         break;
3968     case 0x11:
3969         ret = write_ldt(env, ptr, bytecount, 0);
3970         break;
3971     default:
3972         ret = -TARGET_ENOSYS;
3973         break;
3974     }
3975     return ret;
3976 }
3977 
3978 #if defined(TARGET_I386) && defined(TARGET_ABI32)
3979 static abi_long do_set_thread_area(CPUX86State *env, abi_ulong ptr)
3980 {
3981     uint64_t *gdt_table = g2h(env->gdt.base);
3982     struct target_modify_ldt_ldt_s ldt_info;
3983     struct target_modify_ldt_ldt_s *target_ldt_info;
3984     int seg_32bit, contents, read_exec_only, limit_in_pages;
3985     int seg_not_present, useable, lm;
3986     uint32_t *lp, entry_1, entry_2;
3987     int i;
3988 
3989     lock_user_struct(VERIFY_WRITE, target_ldt_info, ptr, 1);
3990     if (!target_ldt_info)
3991         return -TARGET_EFAULT;
3992     ldt_info.entry_number = tswap32(target_ldt_info->entry_number);
3993     ldt_info.base_addr = tswapal(target_ldt_info->base_addr);
3994     ldt_info.limit = tswap32(target_ldt_info->limit);
3995     ldt_info.flags = tswap32(target_ldt_info->flags);
3996     if (ldt_info.entry_number == -1) {
3997         for (i=TARGET_GDT_ENTRY_TLS_MIN; i<=TARGET_GDT_ENTRY_TLS_MAX; i++) {
3998             if (gdt_table[i] == 0) {
3999                 ldt_info.entry_number = i;
4000                 target_ldt_info->entry_number = tswap32(i);
4001                 break;
4002             }
4003         }
4004     }
4005     unlock_user_struct(target_ldt_info, ptr, 1);
4006 
4007     if (ldt_info.entry_number < TARGET_GDT_ENTRY_TLS_MIN ||
4008         ldt_info.entry_number > TARGET_GDT_ENTRY_TLS_MAX)
4009            return -TARGET_EINVAL;
4010     seg_32bit = ldt_info.flags & 1;
4011     contents = (ldt_info.flags >> 1) & 3;
4012     read_exec_only = (ldt_info.flags >> 3) & 1;
4013     limit_in_pages = (ldt_info.flags >> 4) & 1;
4014     seg_not_present = (ldt_info.flags >> 5) & 1;
4015     useable = (ldt_info.flags >> 6) & 1;
4016 #ifdef TARGET_ABI32
4017     lm = 0;
4018 #else
4019     lm = (ldt_info.flags >> 7) & 1;
4020 #endif
4021 
4022     if (contents == 3) {
4023         if (seg_not_present == 0)
4024             return -TARGET_EINVAL;
4025     }
4026 
4027     /* NOTE: same code as Linux kernel */
4028     /* Allow LDTs to be cleared by the user. */
4029     if (ldt_info.base_addr == 0 && ldt_info.limit == 0) {
4030         if ((contents == 0             &&
4031              read_exec_only == 1       &&
4032              seg_32bit == 0            &&
4033              limit_in_pages == 0       &&
4034              seg_not_present == 1      &&
4035              useable == 0 )) {
4036             entry_1 = 0;
4037             entry_2 = 0;
4038             goto install;
4039         }
4040     }
4041 
4042     entry_1 = ((ldt_info.base_addr & 0x0000ffff) << 16) |
4043         (ldt_info.limit & 0x0ffff);
4044     entry_2 = (ldt_info.base_addr & 0xff000000) |
4045         ((ldt_info.base_addr & 0x00ff0000) >> 16) |
4046         (ldt_info.limit & 0xf0000) |
4047         ((read_exec_only ^ 1) << 9) |
4048         (contents << 10) |
4049         ((seg_not_present ^ 1) << 15) |
4050         (seg_32bit << 22) |
4051         (limit_in_pages << 23) |
4052         (useable << 20) |
4053         (lm << 21) |
4054         0x7000;
4055 
4056     /* Install the new entry ...  */
4057 install:
4058     lp = (uint32_t *)(gdt_table + ldt_info.entry_number);
4059     lp[0] = tswap32(entry_1);
4060     lp[1] = tswap32(entry_2);
4061     return 0;
4062 }
4063 
4064 static abi_long do_get_thread_area(CPUX86State *env, abi_ulong ptr)
4065 {
4066     struct target_modify_ldt_ldt_s *target_ldt_info;
4067     uint64_t *gdt_table = g2h(env->gdt.base);
4068     uint32_t base_addr, limit, flags;
4069     int seg_32bit, contents, read_exec_only, limit_in_pages, idx;
4070     int seg_not_present, useable, lm;
4071     uint32_t *lp, entry_1, entry_2;
4072 
4073     lock_user_struct(VERIFY_WRITE, target_ldt_info, ptr, 1);
4074     if (!target_ldt_info)
4075         return -TARGET_EFAULT;
4076     idx = tswap32(target_ldt_info->entry_number);
4077     if (idx < TARGET_GDT_ENTRY_TLS_MIN ||
4078         idx > TARGET_GDT_ENTRY_TLS_MAX) {
4079         unlock_user_struct(target_ldt_info, ptr, 1);
4080         return -TARGET_EINVAL;
4081     }
4082     lp = (uint32_t *)(gdt_table + idx);
4083     entry_1 = tswap32(lp[0]);
4084     entry_2 = tswap32(lp[1]);
4085 
4086     read_exec_only = ((entry_2 >> 9) & 1) ^ 1;
4087     contents = (entry_2 >> 10) & 3;
4088     seg_not_present = ((entry_2 >> 15) & 1) ^ 1;
4089     seg_32bit = (entry_2 >> 22) & 1;
4090     limit_in_pages = (entry_2 >> 23) & 1;
4091     useable = (entry_2 >> 20) & 1;
4092 #ifdef TARGET_ABI32
4093     lm = 0;
4094 #else
4095     lm = (entry_2 >> 21) & 1;
4096 #endif
4097     flags = (seg_32bit << 0) | (contents << 1) |
4098         (read_exec_only << 3) | (limit_in_pages << 4) |
4099         (seg_not_present << 5) | (useable << 6) | (lm << 7);
4100     limit = (entry_1 & 0xffff) | (entry_2  & 0xf0000);
4101     base_addr = (entry_1 >> 16) |
4102         (entry_2 & 0xff000000) |
4103         ((entry_2 & 0xff) << 16);
4104     target_ldt_info->base_addr = tswapal(base_addr);
4105     target_ldt_info->limit = tswap32(limit);
4106     target_ldt_info->flags = tswap32(flags);
4107     unlock_user_struct(target_ldt_info, ptr, 1);
4108     return 0;
4109 }
4110 #endif /* TARGET_I386 && TARGET_ABI32 */
4111 
4112 #ifndef TARGET_ABI32
4113 static abi_long do_arch_prctl(CPUX86State *env, int code, abi_ulong addr)
4114 {
4115     abi_long ret = 0;
4116     abi_ulong val;
4117     int idx;
4118 
4119     switch(code) {
4120     case TARGET_ARCH_SET_GS:
4121     case TARGET_ARCH_SET_FS:
4122         if (code == TARGET_ARCH_SET_GS)
4123             idx = R_GS;
4124         else
4125             idx = R_FS;
4126         cpu_x86_load_seg(env, idx, 0);
4127         env->segs[idx].base = addr;
4128         break;
4129     case TARGET_ARCH_GET_GS:
4130     case TARGET_ARCH_GET_FS:
4131         if (code == TARGET_ARCH_GET_GS)
4132             idx = R_GS;
4133         else
4134             idx = R_FS;
4135         val = env->segs[idx].base;
4136         if (put_user(val, addr, abi_ulong))
4137             ret = -TARGET_EFAULT;
4138         break;
4139     default:
4140         ret = -TARGET_EINVAL;
4141         break;
4142     }
4143     return ret;
4144 }
4145 #endif
4146 
4147 #endif /* defined(TARGET_I386) */
4148 
4149 #define NEW_STACK_SIZE 0x40000
4150 
4151 #if defined(CONFIG_USE_NPTL)
4152 
4153 static pthread_mutex_t clone_lock = PTHREAD_MUTEX_INITIALIZER;
4154 typedef struct {
4155     CPUArchState *env;
4156     pthread_mutex_t mutex;
4157     pthread_cond_t cond;
4158     pthread_t thread;
4159     uint32_t tid;
4160     abi_ulong child_tidptr;
4161     abi_ulong parent_tidptr;
4162     sigset_t sigmask;
4163 } new_thread_info;
4164 
4165 static void *clone_func(void *arg)
4166 {
4167     new_thread_info *info = arg;
4168     CPUArchState *env;
4169     CPUState *cpu;
4170     TaskState *ts;
4171 
4172     env = info->env;
4173     cpu = ENV_GET_CPU(env);
4174     thread_cpu = cpu;
4175     ts = (TaskState *)env->opaque;
4176     info->tid = gettid();
4177     cpu->host_tid = info->tid;
4178     task_settid(ts);
4179     if (info->child_tidptr)
4180         put_user_u32(info->tid, info->child_tidptr);
4181     if (info->parent_tidptr)
4182         put_user_u32(info->tid, info->parent_tidptr);
4183     /* Enable signals.  */
4184     sigprocmask(SIG_SETMASK, &info->sigmask, NULL);
4185     /* Signal to the parent that we're ready.  */
4186     pthread_mutex_lock(&info->mutex);
4187     pthread_cond_broadcast(&info->cond);
4188     pthread_mutex_unlock(&info->mutex);
4189     /* Wait until the parent has finshed initializing the tls state.  */
4190     pthread_mutex_lock(&clone_lock);
4191     pthread_mutex_unlock(&clone_lock);
4192     cpu_loop(env);
4193     /* never exits */
4194     return NULL;
4195 }
4196 #else
4197 
4198 static int clone_func(void *arg)
4199 {
4200     CPUArchState *env = arg;
4201     cpu_loop(env);
4202     /* never exits */
4203     return 0;
4204 }
4205 #endif
4206 
4207 /* do_fork() Must return host values and target errnos (unlike most
4208    do_*() functions). */
4209 static int do_fork(CPUArchState *env, unsigned int flags, abi_ulong newsp,
4210                    abi_ulong parent_tidptr, target_ulong newtls,
4211                    abi_ulong child_tidptr)
4212 {
4213     int ret;
4214     TaskState *ts;
4215     CPUArchState *new_env;
4216 #if defined(CONFIG_USE_NPTL)
4217     unsigned int nptl_flags;
4218     sigset_t sigmask;
4219 #else
4220     uint8_t *new_stack;
4221 #endif
4222 
4223     /* Emulate vfork() with fork() */
4224     if (flags & CLONE_VFORK)
4225         flags &= ~(CLONE_VFORK | CLONE_VM);
4226 
4227     if (flags & CLONE_VM) {
4228         TaskState *parent_ts = (TaskState *)env->opaque;
4229 #if defined(CONFIG_USE_NPTL)
4230         new_thread_info info;
4231         pthread_attr_t attr;
4232 #endif
4233         ts = g_malloc0(sizeof(TaskState));
4234         init_task_state(ts);
4235         /* we create a new CPU instance. */
4236         new_env = cpu_copy(env);
4237 #if defined(TARGET_I386) || defined(TARGET_SPARC) || defined(TARGET_PPC)
4238         cpu_reset(ENV_GET_CPU(new_env));
4239 #endif
4240         /* Init regs that differ from the parent.  */
4241         cpu_clone_regs(new_env, newsp);
4242         new_env->opaque = ts;
4243         ts->bprm = parent_ts->bprm;
4244         ts->info = parent_ts->info;
4245 #if defined(CONFIG_USE_NPTL)
4246         nptl_flags = flags;
4247         flags &= ~CLONE_NPTL_FLAGS2;
4248 
4249         if (nptl_flags & CLONE_CHILD_CLEARTID) {
4250             ts->child_tidptr = child_tidptr;
4251         }
4252 
4253         if (nptl_flags & CLONE_SETTLS)
4254             cpu_set_tls (new_env, newtls);
4255 
4256         /* Grab a mutex so that thread setup appears atomic.  */
4257         pthread_mutex_lock(&clone_lock);
4258 
4259         memset(&info, 0, sizeof(info));
4260         pthread_mutex_init(&info.mutex, NULL);
4261         pthread_mutex_lock(&info.mutex);
4262         pthread_cond_init(&info.cond, NULL);
4263         info.env = new_env;
4264         if (nptl_flags & CLONE_CHILD_SETTID)
4265             info.child_tidptr = child_tidptr;
4266         if (nptl_flags & CLONE_PARENT_SETTID)
4267             info.parent_tidptr = parent_tidptr;
4268 
4269         ret = pthread_attr_init(&attr);
4270         ret = pthread_attr_setstacksize(&attr, NEW_STACK_SIZE);
4271         ret = pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
4272         /* It is not safe to deliver signals until the child has finished
4273            initializing, so temporarily block all signals.  */
4274         sigfillset(&sigmask);
4275         sigprocmask(SIG_BLOCK, &sigmask, &info.sigmask);
4276 
4277         ret = pthread_create(&info.thread, &attr, clone_func, &info);
4278         /* TODO: Free new CPU state if thread creation failed.  */
4279 
4280         sigprocmask(SIG_SETMASK, &info.sigmask, NULL);
4281         pthread_attr_destroy(&attr);
4282         if (ret == 0) {
4283             /* Wait for the child to initialize.  */
4284             pthread_cond_wait(&info.cond, &info.mutex);
4285             ret = info.tid;
4286             if (flags & CLONE_PARENT_SETTID)
4287                 put_user_u32(ret, parent_tidptr);
4288         } else {
4289             ret = -1;
4290         }
4291         pthread_mutex_unlock(&info.mutex);
4292         pthread_cond_destroy(&info.cond);
4293         pthread_mutex_destroy(&info.mutex);
4294         pthread_mutex_unlock(&clone_lock);
4295 #else
4296         if (flags & CLONE_NPTL_FLAGS2)
4297             return -EINVAL;
4298         /* This is probably going to die very quickly, but do it anyway.  */
4299         new_stack = g_malloc0 (NEW_STACK_SIZE);
4300 #ifdef __ia64__
4301         ret = __clone2(clone_func, new_stack, NEW_STACK_SIZE, flags, new_env);
4302 #else
4303 	ret = clone(clone_func, new_stack + NEW_STACK_SIZE, flags, new_env);
4304 #endif
4305 #endif
4306     } else {
4307         /* if no CLONE_VM, we consider it is a fork */
4308         if ((flags & ~(CSIGNAL | CLONE_NPTL_FLAGS2)) != 0)
4309             return -EINVAL;
4310         fork_start();
4311         ret = fork();
4312         if (ret == 0) {
4313             /* Child Process.  */
4314             cpu_clone_regs(env, newsp);
4315             fork_end(1);
4316 #if defined(CONFIG_USE_NPTL)
4317             /* There is a race condition here.  The parent process could
4318                theoretically read the TID in the child process before the child
4319                tid is set.  This would require using either ptrace
4320                (not implemented) or having *_tidptr to point at a shared memory
4321                mapping.  We can't repeat the spinlock hack used above because
4322                the child process gets its own copy of the lock.  */
4323             if (flags & CLONE_CHILD_SETTID)
4324                 put_user_u32(gettid(), child_tidptr);
4325             if (flags & CLONE_PARENT_SETTID)
4326                 put_user_u32(gettid(), parent_tidptr);
4327             ts = (TaskState *)env->opaque;
4328             if (flags & CLONE_SETTLS)
4329                 cpu_set_tls (env, newtls);
4330             if (flags & CLONE_CHILD_CLEARTID)
4331                 ts->child_tidptr = child_tidptr;
4332 #endif
4333         } else {
4334             fork_end(0);
4335         }
4336     }
4337     return ret;
4338 }
4339 
4340 /* warning : doesn't handle linux specific flags... */
4341 static int target_to_host_fcntl_cmd(int cmd)
4342 {
4343     switch(cmd) {
4344 	case TARGET_F_DUPFD:
4345 	case TARGET_F_GETFD:
4346 	case TARGET_F_SETFD:
4347 	case TARGET_F_GETFL:
4348 	case TARGET_F_SETFL:
4349             return cmd;
4350         case TARGET_F_GETLK:
4351 	    return F_GETLK;
4352 	case TARGET_F_SETLK:
4353 	    return F_SETLK;
4354 	case TARGET_F_SETLKW:
4355 	    return F_SETLKW;
4356 	case TARGET_F_GETOWN:
4357 	    return F_GETOWN;
4358 	case TARGET_F_SETOWN:
4359 	    return F_SETOWN;
4360 	case TARGET_F_GETSIG:
4361 	    return F_GETSIG;
4362 	case TARGET_F_SETSIG:
4363 	    return F_SETSIG;
4364 #if TARGET_ABI_BITS == 32
4365         case TARGET_F_GETLK64:
4366 	    return F_GETLK64;
4367 	case TARGET_F_SETLK64:
4368 	    return F_SETLK64;
4369 	case TARGET_F_SETLKW64:
4370 	    return F_SETLKW64;
4371 #endif
4372         case TARGET_F_SETLEASE:
4373             return F_SETLEASE;
4374         case TARGET_F_GETLEASE:
4375             return F_GETLEASE;
4376 #ifdef F_DUPFD_CLOEXEC
4377         case TARGET_F_DUPFD_CLOEXEC:
4378             return F_DUPFD_CLOEXEC;
4379 #endif
4380         case TARGET_F_NOTIFY:
4381             return F_NOTIFY;
4382 	default:
4383             return -TARGET_EINVAL;
4384     }
4385     return -TARGET_EINVAL;
4386 }
4387 
4388 #define TRANSTBL_CONVERT(a) { -1, TARGET_##a, -1, a }
4389 static const bitmask_transtbl flock_tbl[] = {
4390     TRANSTBL_CONVERT(F_RDLCK),
4391     TRANSTBL_CONVERT(F_WRLCK),
4392     TRANSTBL_CONVERT(F_UNLCK),
4393     TRANSTBL_CONVERT(F_EXLCK),
4394     TRANSTBL_CONVERT(F_SHLCK),
4395     { 0, 0, 0, 0 }
4396 };
4397 
4398 static abi_long do_fcntl(int fd, int cmd, abi_ulong arg)
4399 {
4400     struct flock fl;
4401     struct target_flock *target_fl;
4402     struct flock64 fl64;
4403     struct target_flock64 *target_fl64;
4404     abi_long ret;
4405     int host_cmd = target_to_host_fcntl_cmd(cmd);
4406 
4407     if (host_cmd == -TARGET_EINVAL)
4408 	    return host_cmd;
4409 
4410     switch(cmd) {
4411     case TARGET_F_GETLK:
4412         if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))
4413             return -TARGET_EFAULT;
4414         fl.l_type =
4415                   target_to_host_bitmask(tswap16(target_fl->l_type), flock_tbl);
4416         fl.l_whence = tswap16(target_fl->l_whence);
4417         fl.l_start = tswapal(target_fl->l_start);
4418         fl.l_len = tswapal(target_fl->l_len);
4419         fl.l_pid = tswap32(target_fl->l_pid);
4420         unlock_user_struct(target_fl, arg, 0);
4421         ret = get_errno(fcntl(fd, host_cmd, &fl));
4422         if (ret == 0) {
4423             if (!lock_user_struct(VERIFY_WRITE, target_fl, arg, 0))
4424                 return -TARGET_EFAULT;
4425             target_fl->l_type =
4426                           host_to_target_bitmask(tswap16(fl.l_type), flock_tbl);
4427             target_fl->l_whence = tswap16(fl.l_whence);
4428             target_fl->l_start = tswapal(fl.l_start);
4429             target_fl->l_len = tswapal(fl.l_len);
4430             target_fl->l_pid = tswap32(fl.l_pid);
4431             unlock_user_struct(target_fl, arg, 1);
4432         }
4433         break;
4434 
4435     case TARGET_F_SETLK:
4436     case TARGET_F_SETLKW:
4437         if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))
4438             return -TARGET_EFAULT;
4439         fl.l_type =
4440                   target_to_host_bitmask(tswap16(target_fl->l_type), flock_tbl);
4441         fl.l_whence = tswap16(target_fl->l_whence);
4442         fl.l_start = tswapal(target_fl->l_start);
4443         fl.l_len = tswapal(target_fl->l_len);
4444         fl.l_pid = tswap32(target_fl->l_pid);
4445         unlock_user_struct(target_fl, arg, 0);
4446         ret = get_errno(fcntl(fd, host_cmd, &fl));
4447         break;
4448 
4449     case TARGET_F_GETLK64:
4450         if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))
4451             return -TARGET_EFAULT;
4452         fl64.l_type =
4453            target_to_host_bitmask(tswap16(target_fl64->l_type), flock_tbl) >> 1;
4454         fl64.l_whence = tswap16(target_fl64->l_whence);
4455         fl64.l_start = tswap64(target_fl64->l_start);
4456         fl64.l_len = tswap64(target_fl64->l_len);
4457         fl64.l_pid = tswap32(target_fl64->l_pid);
4458         unlock_user_struct(target_fl64, arg, 0);
4459         ret = get_errno(fcntl(fd, host_cmd, &fl64));
4460         if (ret == 0) {
4461             if (!lock_user_struct(VERIFY_WRITE, target_fl64, arg, 0))
4462                 return -TARGET_EFAULT;
4463             target_fl64->l_type =
4464                    host_to_target_bitmask(tswap16(fl64.l_type), flock_tbl) >> 1;
4465             target_fl64->l_whence = tswap16(fl64.l_whence);
4466             target_fl64->l_start = tswap64(fl64.l_start);
4467             target_fl64->l_len = tswap64(fl64.l_len);
4468             target_fl64->l_pid = tswap32(fl64.l_pid);
4469             unlock_user_struct(target_fl64, arg, 1);
4470         }
4471         break;
4472     case TARGET_F_SETLK64:
4473     case TARGET_F_SETLKW64:
4474         if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))
4475             return -TARGET_EFAULT;
4476         fl64.l_type =
4477            target_to_host_bitmask(tswap16(target_fl64->l_type), flock_tbl) >> 1;
4478         fl64.l_whence = tswap16(target_fl64->l_whence);
4479         fl64.l_start = tswap64(target_fl64->l_start);
4480         fl64.l_len = tswap64(target_fl64->l_len);
4481         fl64.l_pid = tswap32(target_fl64->l_pid);
4482         unlock_user_struct(target_fl64, arg, 0);
4483         ret = get_errno(fcntl(fd, host_cmd, &fl64));
4484         break;
4485 
4486     case TARGET_F_GETFL:
4487         ret = get_errno(fcntl(fd, host_cmd, arg));
4488         if (ret >= 0) {
4489             ret = host_to_target_bitmask(ret, fcntl_flags_tbl);
4490         }
4491         break;
4492 
4493     case TARGET_F_SETFL:
4494         ret = get_errno(fcntl(fd, host_cmd, target_to_host_bitmask(arg, fcntl_flags_tbl)));
4495         break;
4496 
4497     case TARGET_F_SETOWN:
4498     case TARGET_F_GETOWN:
4499     case TARGET_F_SETSIG:
4500     case TARGET_F_GETSIG:
4501     case TARGET_F_SETLEASE:
4502     case TARGET_F_GETLEASE:
4503         ret = get_errno(fcntl(fd, host_cmd, arg));
4504         break;
4505 
4506     default:
4507         ret = get_errno(fcntl(fd, cmd, arg));
4508         break;
4509     }
4510     return ret;
4511 }
4512 
4513 #ifdef USE_UID16
4514 
4515 static inline int high2lowuid(int uid)
4516 {
4517     if (uid > 65535)
4518         return 65534;
4519     else
4520         return uid;
4521 }
4522 
4523 static inline int high2lowgid(int gid)
4524 {
4525     if (gid > 65535)
4526         return 65534;
4527     else
4528         return gid;
4529 }
4530 
4531 static inline int low2highuid(int uid)
4532 {
4533     if ((int16_t)uid == -1)
4534         return -1;
4535     else
4536         return uid;
4537 }
4538 
4539 static inline int low2highgid(int gid)
4540 {
4541     if ((int16_t)gid == -1)
4542         return -1;
4543     else
4544         return gid;
4545 }
4546 static inline int tswapid(int id)
4547 {
4548     return tswap16(id);
4549 }
4550 #else /* !USE_UID16 */
4551 static inline int high2lowuid(int uid)
4552 {
4553     return uid;
4554 }
4555 static inline int high2lowgid(int gid)
4556 {
4557     return gid;
4558 }
4559 static inline int low2highuid(int uid)
4560 {
4561     return uid;
4562 }
4563 static inline int low2highgid(int gid)
4564 {
4565     return gid;
4566 }
4567 static inline int tswapid(int id)
4568 {
4569     return tswap32(id);
4570 }
4571 #endif /* USE_UID16 */
4572 
4573 void syscall_init(void)
4574 {
4575     IOCTLEntry *ie;
4576     const argtype *arg_type;
4577     int size;
4578     int i;
4579 
4580 #define STRUCT(name, ...) thunk_register_struct(STRUCT_ ## name, #name, struct_ ## name ## _def);
4581 #define STRUCT_SPECIAL(name) thunk_register_struct_direct(STRUCT_ ## name, #name, &struct_ ## name ## _def);
4582 #include "syscall_types.h"
4583 #undef STRUCT
4584 #undef STRUCT_SPECIAL
4585 
4586     /* Build target_to_host_errno_table[] table from
4587      * host_to_target_errno_table[]. */
4588     for (i = 0; i < ERRNO_TABLE_SIZE; i++) {
4589         target_to_host_errno_table[host_to_target_errno_table[i]] = i;
4590     }
4591 
4592     /* we patch the ioctl size if necessary. We rely on the fact that
4593        no ioctl has all the bits at '1' in the size field */
4594     ie = ioctl_entries;
4595     while (ie->target_cmd != 0) {
4596         if (((ie->target_cmd >> TARGET_IOC_SIZESHIFT) & TARGET_IOC_SIZEMASK) ==
4597             TARGET_IOC_SIZEMASK) {
4598             arg_type = ie->arg_type;
4599             if (arg_type[0] != TYPE_PTR) {
4600                 fprintf(stderr, "cannot patch size for ioctl 0x%x\n",
4601                         ie->target_cmd);
4602                 exit(1);
4603             }
4604             arg_type++;
4605             size = thunk_type_size(arg_type, 0);
4606             ie->target_cmd = (ie->target_cmd &
4607                               ~(TARGET_IOC_SIZEMASK << TARGET_IOC_SIZESHIFT)) |
4608                 (size << TARGET_IOC_SIZESHIFT);
4609         }
4610 
4611         /* automatic consistency check if same arch */
4612 #if (defined(__i386__) && defined(TARGET_I386) && defined(TARGET_ABI32)) || \
4613     (defined(__x86_64__) && defined(TARGET_X86_64))
4614         if (unlikely(ie->target_cmd != ie->host_cmd)) {
4615             fprintf(stderr, "ERROR: ioctl(%s): target=0x%x host=0x%x\n",
4616                     ie->name, ie->target_cmd, ie->host_cmd);
4617         }
4618 #endif
4619         ie++;
4620     }
4621 }
4622 
4623 #if TARGET_ABI_BITS == 32
4624 static inline uint64_t target_offset64(uint32_t word0, uint32_t word1)
4625 {
4626 #ifdef TARGET_WORDS_BIGENDIAN
4627     return ((uint64_t)word0 << 32) | word1;
4628 #else
4629     return ((uint64_t)word1 << 32) | word0;
4630 #endif
4631 }
4632 #else /* TARGET_ABI_BITS == 32 */
4633 static inline uint64_t target_offset64(uint64_t word0, uint64_t word1)
4634 {
4635     return word0;
4636 }
4637 #endif /* TARGET_ABI_BITS != 32 */
4638 
4639 #ifdef TARGET_NR_truncate64
4640 static inline abi_long target_truncate64(void *cpu_env, const char *arg1,
4641                                          abi_long arg2,
4642                                          abi_long arg3,
4643                                          abi_long arg4)
4644 {
4645     if (regpairs_aligned(cpu_env)) {
4646         arg2 = arg3;
4647         arg3 = arg4;
4648     }
4649     return get_errno(truncate64(arg1, target_offset64(arg2, arg3)));
4650 }
4651 #endif
4652 
4653 #ifdef TARGET_NR_ftruncate64
4654 static inline abi_long target_ftruncate64(void *cpu_env, abi_long arg1,
4655                                           abi_long arg2,
4656                                           abi_long arg3,
4657                                           abi_long arg4)
4658 {
4659     if (regpairs_aligned(cpu_env)) {
4660         arg2 = arg3;
4661         arg3 = arg4;
4662     }
4663     return get_errno(ftruncate64(arg1, target_offset64(arg2, arg3)));
4664 }
4665 #endif
4666 
4667 static inline abi_long target_to_host_timespec(struct timespec *host_ts,
4668                                                abi_ulong target_addr)
4669 {
4670     struct target_timespec *target_ts;
4671 
4672     if (!lock_user_struct(VERIFY_READ, target_ts, target_addr, 1))
4673         return -TARGET_EFAULT;
4674     host_ts->tv_sec = tswapal(target_ts->tv_sec);
4675     host_ts->tv_nsec = tswapal(target_ts->tv_nsec);
4676     unlock_user_struct(target_ts, target_addr, 0);
4677     return 0;
4678 }
4679 
4680 static inline abi_long host_to_target_timespec(abi_ulong target_addr,
4681                                                struct timespec *host_ts)
4682 {
4683     struct target_timespec *target_ts;
4684 
4685     if (!lock_user_struct(VERIFY_WRITE, target_ts, target_addr, 0))
4686         return -TARGET_EFAULT;
4687     target_ts->tv_sec = tswapal(host_ts->tv_sec);
4688     target_ts->tv_nsec = tswapal(host_ts->tv_nsec);
4689     unlock_user_struct(target_ts, target_addr, 1);
4690     return 0;
4691 }
4692 
4693 #if defined(TARGET_NR_stat64) || defined(TARGET_NR_newfstatat)
4694 static inline abi_long host_to_target_stat64(void *cpu_env,
4695                                              abi_ulong target_addr,
4696                                              struct stat *host_st)
4697 {
4698 #ifdef TARGET_ARM
4699     if (((CPUARMState *)cpu_env)->eabi) {
4700         struct target_eabi_stat64 *target_st;
4701 
4702         if (!lock_user_struct(VERIFY_WRITE, target_st, target_addr, 0))
4703             return -TARGET_EFAULT;
4704         memset(target_st, 0, sizeof(struct target_eabi_stat64));
4705         __put_user(host_st->st_dev, &target_st->st_dev);
4706         __put_user(host_st->st_ino, &target_st->st_ino);
4707 #ifdef TARGET_STAT64_HAS_BROKEN_ST_INO
4708         __put_user(host_st->st_ino, &target_st->__st_ino);
4709 #endif
4710         __put_user(host_st->st_mode, &target_st->st_mode);
4711         __put_user(host_st->st_nlink, &target_st->st_nlink);
4712         __put_user(host_st->st_uid, &target_st->st_uid);
4713         __put_user(host_st->st_gid, &target_st->st_gid);
4714         __put_user(host_st->st_rdev, &target_st->st_rdev);
4715         __put_user(host_st->st_size, &target_st->st_size);
4716         __put_user(host_st->st_blksize, &target_st->st_blksize);
4717         __put_user(host_st->st_blocks, &target_st->st_blocks);
4718         __put_user(host_st->st_atime, &target_st->target_st_atime);
4719         __put_user(host_st->st_mtime, &target_st->target_st_mtime);
4720         __put_user(host_st->st_ctime, &target_st->target_st_ctime);
4721         unlock_user_struct(target_st, target_addr, 1);
4722     } else
4723 #endif
4724     {
4725 #if TARGET_ABI_BITS == 64 && !defined(TARGET_ALPHA)
4726         struct target_stat *target_st;
4727 #else
4728         struct target_stat64 *target_st;
4729 #endif
4730 
4731         if (!lock_user_struct(VERIFY_WRITE, target_st, target_addr, 0))
4732             return -TARGET_EFAULT;
4733         memset(target_st, 0, sizeof(*target_st));
4734         __put_user(host_st->st_dev, &target_st->st_dev);
4735         __put_user(host_st->st_ino, &target_st->st_ino);
4736 #ifdef TARGET_STAT64_HAS_BROKEN_ST_INO
4737         __put_user(host_st->st_ino, &target_st->__st_ino);
4738 #endif
4739         __put_user(host_st->st_mode, &target_st->st_mode);
4740         __put_user(host_st->st_nlink, &target_st->st_nlink);
4741         __put_user(host_st->st_uid, &target_st->st_uid);
4742         __put_user(host_st->st_gid, &target_st->st_gid);
4743         __put_user(host_st->st_rdev, &target_st->st_rdev);
4744         /* XXX: better use of kernel struct */
4745         __put_user(host_st->st_size, &target_st->st_size);
4746         __put_user(host_st->st_blksize, &target_st->st_blksize);
4747         __put_user(host_st->st_blocks, &target_st->st_blocks);
4748         __put_user(host_st->st_atime, &target_st->target_st_atime);
4749         __put_user(host_st->st_mtime, &target_st->target_st_mtime);
4750         __put_user(host_st->st_ctime, &target_st->target_st_ctime);
4751         unlock_user_struct(target_st, target_addr, 1);
4752     }
4753 
4754     return 0;
4755 }
4756 #endif
4757 
4758 #if defined(CONFIG_USE_NPTL)
4759 /* ??? Using host futex calls even when target atomic operations
4760    are not really atomic probably breaks things.  However implementing
4761    futexes locally would make futexes shared between multiple processes
4762    tricky.  However they're probably useless because guest atomic
4763    operations won't work either.  */
4764 static int do_futex(target_ulong uaddr, int op, int val, target_ulong timeout,
4765                     target_ulong uaddr2, int val3)
4766 {
4767     struct timespec ts, *pts;
4768     int base_op;
4769 
4770     /* ??? We assume FUTEX_* constants are the same on both host
4771        and target.  */
4772 #ifdef FUTEX_CMD_MASK
4773     base_op = op & FUTEX_CMD_MASK;
4774 #else
4775     base_op = op;
4776 #endif
4777     switch (base_op) {
4778     case FUTEX_WAIT:
4779     case FUTEX_WAIT_BITSET:
4780         if (timeout) {
4781             pts = &ts;
4782             target_to_host_timespec(pts, timeout);
4783         } else {
4784             pts = NULL;
4785         }
4786         return get_errno(sys_futex(g2h(uaddr), op, tswap32(val),
4787                          pts, NULL, val3));
4788     case FUTEX_WAKE:
4789         return get_errno(sys_futex(g2h(uaddr), op, val, NULL, NULL, 0));
4790     case FUTEX_FD:
4791         return get_errno(sys_futex(g2h(uaddr), op, val, NULL, NULL, 0));
4792     case FUTEX_REQUEUE:
4793     case FUTEX_CMP_REQUEUE:
4794     case FUTEX_WAKE_OP:
4795         /* For FUTEX_REQUEUE, FUTEX_CMP_REQUEUE, and FUTEX_WAKE_OP, the
4796            TIMEOUT parameter is interpreted as a uint32_t by the kernel.
4797            But the prototype takes a `struct timespec *'; insert casts
4798            to satisfy the compiler.  We do not need to tswap TIMEOUT
4799            since it's not compared to guest memory.  */
4800         pts = (struct timespec *)(uintptr_t) timeout;
4801         return get_errno(sys_futex(g2h(uaddr), op, val, pts,
4802                                    g2h(uaddr2),
4803                                    (base_op == FUTEX_CMP_REQUEUE
4804                                     ? tswap32(val3)
4805                                     : val3)));
4806     default:
4807         return -TARGET_ENOSYS;
4808     }
4809 }
4810 #endif
4811 
4812 /* Map host to target signal numbers for the wait family of syscalls.
4813    Assume all other status bits are the same.  */
4814 int host_to_target_waitstatus(int status)
4815 {
4816     if (WIFSIGNALED(status)) {
4817         return host_to_target_signal(WTERMSIG(status)) | (status & ~0x7f);
4818     }
4819     if (WIFSTOPPED(status)) {
4820         return (host_to_target_signal(WSTOPSIG(status)) << 8)
4821                | (status & 0xff);
4822     }
4823     return status;
4824 }
4825 
4826 int get_osversion(void)
4827 {
4828     static int osversion;
4829     struct new_utsname buf;
4830     const char *s;
4831     int i, n, tmp;
4832     if (osversion)
4833         return osversion;
4834     if (qemu_uname_release && *qemu_uname_release) {
4835         s = qemu_uname_release;
4836     } else {
4837         if (sys_uname(&buf))
4838             return 0;
4839         s = buf.release;
4840     }
4841     tmp = 0;
4842     for (i = 0; i < 3; i++) {
4843         n = 0;
4844         while (*s >= '0' && *s <= '9') {
4845             n *= 10;
4846             n += *s - '0';
4847             s++;
4848         }
4849         tmp = (tmp << 8) + n;
4850         if (*s == '.')
4851             s++;
4852     }
4853     osversion = tmp;
4854     return osversion;
4855 }
4856 
4857 
4858 static int open_self_maps(void *cpu_env, int fd)
4859 {
4860 #if defined(TARGET_ARM) || defined(TARGET_M68K) || defined(TARGET_UNICORE32)
4861     TaskState *ts = ((CPUArchState *)cpu_env)->opaque;
4862 #endif
4863     FILE *fp;
4864     char *line = NULL;
4865     size_t len = 0;
4866     ssize_t read;
4867 
4868     fp = fopen("/proc/self/maps", "r");
4869     if (fp == NULL) {
4870         return -EACCES;
4871     }
4872 
4873     while ((read = getline(&line, &len, fp)) != -1) {
4874         int fields, dev_maj, dev_min, inode;
4875         uint64_t min, max, offset;
4876         char flag_r, flag_w, flag_x, flag_p;
4877         char path[512] = "";
4878         fields = sscanf(line, "%"PRIx64"-%"PRIx64" %c%c%c%c %"PRIx64" %x:%x %d"
4879                         " %512s", &min, &max, &flag_r, &flag_w, &flag_x,
4880                         &flag_p, &offset, &dev_maj, &dev_min, &inode, path);
4881 
4882         if ((fields < 10) || (fields > 11)) {
4883             continue;
4884         }
4885         if (!strncmp(path, "[stack]", 7)) {
4886             continue;
4887         }
4888         if (h2g_valid(min) && h2g_valid(max)) {
4889             dprintf(fd, TARGET_ABI_FMT_lx "-" TARGET_ABI_FMT_lx
4890                     " %c%c%c%c %08" PRIx64 " %02x:%02x %d %s%s\n",
4891                     h2g(min), h2g(max), flag_r, flag_w,
4892                     flag_x, flag_p, offset, dev_maj, dev_min, inode,
4893                     path[0] ? "         " : "", path);
4894         }
4895     }
4896 
4897     free(line);
4898     fclose(fp);
4899 
4900 #if defined(TARGET_ARM) || defined(TARGET_M68K) || defined(TARGET_UNICORE32)
4901     dprintf(fd, "%08llx-%08llx rw-p %08llx 00:00 0          [stack]\n",
4902                 (unsigned long long)ts->info->stack_limit,
4903                 (unsigned long long)(ts->info->start_stack +
4904                                      (TARGET_PAGE_SIZE - 1)) & TARGET_PAGE_MASK,
4905                 (unsigned long long)0);
4906 #endif
4907 
4908     return 0;
4909 }
4910 
4911 static int open_self_stat(void *cpu_env, int fd)
4912 {
4913     TaskState *ts = ((CPUArchState *)cpu_env)->opaque;
4914     abi_ulong start_stack = ts->info->start_stack;
4915     int i;
4916 
4917     for (i = 0; i < 44; i++) {
4918       char buf[128];
4919       int len;
4920       uint64_t val = 0;
4921 
4922       if (i == 0) {
4923         /* pid */
4924         val = getpid();
4925         snprintf(buf, sizeof(buf), "%"PRId64 " ", val);
4926       } else if (i == 1) {
4927         /* app name */
4928         snprintf(buf, sizeof(buf), "(%s) ", ts->bprm->argv[0]);
4929       } else if (i == 27) {
4930         /* stack bottom */
4931         val = start_stack;
4932         snprintf(buf, sizeof(buf), "%"PRId64 " ", val);
4933       } else {
4934         /* for the rest, there is MasterCard */
4935         snprintf(buf, sizeof(buf), "0%c", i == 43 ? '\n' : ' ');
4936       }
4937 
4938       len = strlen(buf);
4939       if (write(fd, buf, len) != len) {
4940           return -1;
4941       }
4942     }
4943 
4944     return 0;
4945 }
4946 
4947 static int open_self_auxv(void *cpu_env, int fd)
4948 {
4949     TaskState *ts = ((CPUArchState *)cpu_env)->opaque;
4950     abi_ulong auxv = ts->info->saved_auxv;
4951     abi_ulong len = ts->info->auxv_len;
4952     char *ptr;
4953 
4954     /*
4955      * Auxiliary vector is stored in target process stack.
4956      * read in whole auxv vector and copy it to file
4957      */
4958     ptr = lock_user(VERIFY_READ, auxv, len, 0);
4959     if (ptr != NULL) {
4960         while (len > 0) {
4961             ssize_t r;
4962             r = write(fd, ptr, len);
4963             if (r <= 0) {
4964                 break;
4965             }
4966             len -= r;
4967             ptr += r;
4968         }
4969         lseek(fd, 0, SEEK_SET);
4970         unlock_user(ptr, auxv, len);
4971     }
4972 
4973     return 0;
4974 }
4975 
4976 static int do_open(void *cpu_env, const char *pathname, int flags, mode_t mode)
4977 {
4978     struct fake_open {
4979         const char *filename;
4980         int (*fill)(void *cpu_env, int fd);
4981     };
4982     const struct fake_open *fake_open;
4983     static const struct fake_open fakes[] = {
4984         { "/proc/self/maps", open_self_maps },
4985         { "/proc/self/stat", open_self_stat },
4986         { "/proc/self/auxv", open_self_auxv },
4987         { NULL, NULL }
4988     };
4989 
4990     for (fake_open = fakes; fake_open->filename; fake_open++) {
4991         if (!strncmp(pathname, fake_open->filename,
4992                      strlen(fake_open->filename))) {
4993             break;
4994         }
4995     }
4996 
4997     if (fake_open->filename) {
4998         const char *tmpdir;
4999         char filename[PATH_MAX];
5000         int fd, r;
5001 
5002         /* create temporary file to map stat to */
5003         tmpdir = getenv("TMPDIR");
5004         if (!tmpdir)
5005             tmpdir = "/tmp";
5006         snprintf(filename, sizeof(filename), "%s/qemu-open.XXXXXX", tmpdir);
5007         fd = mkstemp(filename);
5008         if (fd < 0) {
5009             return fd;
5010         }
5011         unlink(filename);
5012 
5013         if ((r = fake_open->fill(cpu_env, fd))) {
5014             close(fd);
5015             return r;
5016         }
5017         lseek(fd, 0, SEEK_SET);
5018 
5019         return fd;
5020     }
5021 
5022     return get_errno(open(path(pathname), flags, mode));
5023 }
5024 
5025 /* do_syscall() should always have a single exit point at the end so
5026    that actions, such as logging of syscall results, can be performed.
5027    All errnos that do_syscall() returns must be -TARGET_<errcode>. */
5028 abi_long do_syscall(void *cpu_env, int num, abi_long arg1,
5029                     abi_long arg2, abi_long arg3, abi_long arg4,
5030                     abi_long arg5, abi_long arg6, abi_long arg7,
5031                     abi_long arg8)
5032 {
5033 #ifdef CONFIG_USE_NPTL
5034     CPUState *cpu = ENV_GET_CPU(cpu_env);
5035 #endif
5036     abi_long ret;
5037     struct stat st;
5038     struct statfs stfs;
5039     void *p;
5040 
5041 #ifdef DEBUG
5042     gemu_log("syscall %d", num);
5043 #endif
5044     if(do_strace)
5045         print_syscall(num, arg1, arg2, arg3, arg4, arg5, arg6);
5046 
5047     switch(num) {
5048     case TARGET_NR_exit:
5049 #ifdef CONFIG_USE_NPTL
5050         /* In old applications this may be used to implement _exit(2).
5051            However in threaded applictions it is used for thread termination,
5052            and _exit_group is used for application termination.
5053            Do thread termination if we have more then one thread.  */
5054         /* FIXME: This probably breaks if a signal arrives.  We should probably
5055            be disabling signals.  */
5056         if (first_cpu->next_cpu) {
5057             TaskState *ts;
5058             CPUState **lastp;
5059             CPUState *p;
5060 
5061             cpu_list_lock();
5062             lastp = &first_cpu;
5063             p = first_cpu;
5064             while (p && p != cpu) {
5065                 lastp = &p->next_cpu;
5066                 p = p->next_cpu;
5067             }
5068             /* If we didn't find the CPU for this thread then something is
5069                horribly wrong.  */
5070             if (!p) {
5071                 abort();
5072             }
5073             /* Remove the CPU from the list.  */
5074             *lastp = p->next_cpu;
5075             cpu_list_unlock();
5076             ts = ((CPUArchState *)cpu_env)->opaque;
5077             if (ts->child_tidptr) {
5078                 put_user_u32(0, ts->child_tidptr);
5079                 sys_futex(g2h(ts->child_tidptr), FUTEX_WAKE, INT_MAX,
5080                           NULL, NULL, 0);
5081             }
5082             thread_cpu = NULL;
5083             object_unref(OBJECT(ENV_GET_CPU(cpu_env)));
5084             g_free(ts);
5085             pthread_exit(NULL);
5086         }
5087 #endif
5088 #ifdef TARGET_GPROF
5089         _mcleanup();
5090 #endif
5091         gdb_exit(cpu_env, arg1);
5092         _exit(arg1);
5093         ret = 0; /* avoid warning */
5094         break;
5095     case TARGET_NR_read:
5096         if (arg3 == 0)
5097             ret = 0;
5098         else {
5099             if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
5100                 goto efault;
5101             ret = get_errno(read(arg1, p, arg3));
5102             unlock_user(p, arg2, ret);
5103         }
5104         break;
5105     case TARGET_NR_write:
5106         if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
5107             goto efault;
5108         ret = get_errno(write(arg1, p, arg3));
5109         unlock_user(p, arg2, 0);
5110         break;
5111     case TARGET_NR_open:
5112         if (!(p = lock_user_string(arg1)))
5113             goto efault;
5114         ret = get_errno(do_open(cpu_env, p,
5115                                 target_to_host_bitmask(arg2, fcntl_flags_tbl),
5116                                 arg3));
5117         unlock_user(p, arg1, 0);
5118         break;
5119 #if defined(TARGET_NR_openat) && defined(__NR_openat)
5120     case TARGET_NR_openat:
5121         if (!(p = lock_user_string(arg2)))
5122             goto efault;
5123         ret = get_errno(sys_openat(arg1,
5124                                    path(p),
5125                                    target_to_host_bitmask(arg3, fcntl_flags_tbl),
5126                                    arg4));
5127         unlock_user(p, arg2, 0);
5128         break;
5129 #endif
5130     case TARGET_NR_close:
5131         ret = get_errno(close(arg1));
5132         break;
5133     case TARGET_NR_brk:
5134         ret = do_brk(arg1);
5135         break;
5136     case TARGET_NR_fork:
5137         ret = get_errno(do_fork(cpu_env, SIGCHLD, 0, 0, 0, 0));
5138         break;
5139 #ifdef TARGET_NR_waitpid
5140     case TARGET_NR_waitpid:
5141         {
5142             int status;
5143             ret = get_errno(waitpid(arg1, &status, arg3));
5144             if (!is_error(ret) && arg2 && ret
5145                 && put_user_s32(host_to_target_waitstatus(status), arg2))
5146                 goto efault;
5147         }
5148         break;
5149 #endif
5150 #ifdef TARGET_NR_waitid
5151     case TARGET_NR_waitid:
5152         {
5153             siginfo_t info;
5154             info.si_pid = 0;
5155             ret = get_errno(waitid(arg1, arg2, &info, arg4));
5156             if (!is_error(ret) && arg3 && info.si_pid != 0) {
5157                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_siginfo_t), 0)))
5158                     goto efault;
5159                 host_to_target_siginfo(p, &info);
5160                 unlock_user(p, arg3, sizeof(target_siginfo_t));
5161             }
5162         }
5163         break;
5164 #endif
5165 #ifdef TARGET_NR_creat /* not on alpha */
5166     case TARGET_NR_creat:
5167         if (!(p = lock_user_string(arg1)))
5168             goto efault;
5169         ret = get_errno(creat(p, arg2));
5170         unlock_user(p, arg1, 0);
5171         break;
5172 #endif
5173     case TARGET_NR_link:
5174         {
5175             void * p2;
5176             p = lock_user_string(arg1);
5177             p2 = lock_user_string(arg2);
5178             if (!p || !p2)
5179                 ret = -TARGET_EFAULT;
5180             else
5181                 ret = get_errno(link(p, p2));
5182             unlock_user(p2, arg2, 0);
5183             unlock_user(p, arg1, 0);
5184         }
5185         break;
5186 #if defined(TARGET_NR_linkat)
5187     case TARGET_NR_linkat:
5188         {
5189             void * p2 = NULL;
5190             if (!arg2 || !arg4)
5191                 goto efault;
5192             p  = lock_user_string(arg2);
5193             p2 = lock_user_string(arg4);
5194             if (!p || !p2)
5195                 ret = -TARGET_EFAULT;
5196             else
5197                 ret = get_errno(linkat(arg1, p, arg3, p2, arg5));
5198             unlock_user(p, arg2, 0);
5199             unlock_user(p2, arg4, 0);
5200         }
5201         break;
5202 #endif
5203     case TARGET_NR_unlink:
5204         if (!(p = lock_user_string(arg1)))
5205             goto efault;
5206         ret = get_errno(unlink(p));
5207         unlock_user(p, arg1, 0);
5208         break;
5209 #if defined(TARGET_NR_unlinkat)
5210     case TARGET_NR_unlinkat:
5211         if (!(p = lock_user_string(arg2)))
5212             goto efault;
5213         ret = get_errno(unlinkat(arg1, p, arg3));
5214         unlock_user(p, arg2, 0);
5215         break;
5216 #endif
5217     case TARGET_NR_execve:
5218         {
5219             char **argp, **envp;
5220             int argc, envc;
5221             abi_ulong gp;
5222             abi_ulong guest_argp;
5223             abi_ulong guest_envp;
5224             abi_ulong addr;
5225             char **q;
5226             int total_size = 0;
5227 
5228             argc = 0;
5229             guest_argp = arg2;
5230             for (gp = guest_argp; gp; gp += sizeof(abi_ulong)) {
5231                 if (get_user_ual(addr, gp))
5232                     goto efault;
5233                 if (!addr)
5234                     break;
5235                 argc++;
5236             }
5237             envc = 0;
5238             guest_envp = arg3;
5239             for (gp = guest_envp; gp; gp += sizeof(abi_ulong)) {
5240                 if (get_user_ual(addr, gp))
5241                     goto efault;
5242                 if (!addr)
5243                     break;
5244                 envc++;
5245             }
5246 
5247             argp = alloca((argc + 1) * sizeof(void *));
5248             envp = alloca((envc + 1) * sizeof(void *));
5249 
5250             for (gp = guest_argp, q = argp; gp;
5251                   gp += sizeof(abi_ulong), q++) {
5252                 if (get_user_ual(addr, gp))
5253                     goto execve_efault;
5254                 if (!addr)
5255                     break;
5256                 if (!(*q = lock_user_string(addr)))
5257                     goto execve_efault;
5258                 total_size += strlen(*q) + 1;
5259             }
5260             *q = NULL;
5261 
5262             for (gp = guest_envp, q = envp; gp;
5263                   gp += sizeof(abi_ulong), q++) {
5264                 if (get_user_ual(addr, gp))
5265                     goto execve_efault;
5266                 if (!addr)
5267                     break;
5268                 if (!(*q = lock_user_string(addr)))
5269                     goto execve_efault;
5270                 total_size += strlen(*q) + 1;
5271             }
5272             *q = NULL;
5273 
5274             /* This case will not be caught by the host's execve() if its
5275                page size is bigger than the target's. */
5276             if (total_size > MAX_ARG_PAGES * TARGET_PAGE_SIZE) {
5277                 ret = -TARGET_E2BIG;
5278                 goto execve_end;
5279             }
5280             if (!(p = lock_user_string(arg1)))
5281                 goto execve_efault;
5282             ret = get_errno(execve(p, argp, envp));
5283             unlock_user(p, arg1, 0);
5284 
5285             goto execve_end;
5286 
5287         execve_efault:
5288             ret = -TARGET_EFAULT;
5289 
5290         execve_end:
5291             for (gp = guest_argp, q = argp; *q;
5292                   gp += sizeof(abi_ulong), q++) {
5293                 if (get_user_ual(addr, gp)
5294                     || !addr)
5295                     break;
5296                 unlock_user(*q, addr, 0);
5297             }
5298             for (gp = guest_envp, q = envp; *q;
5299                   gp += sizeof(abi_ulong), q++) {
5300                 if (get_user_ual(addr, gp)
5301                     || !addr)
5302                     break;
5303                 unlock_user(*q, addr, 0);
5304             }
5305         }
5306         break;
5307     case TARGET_NR_chdir:
5308         if (!(p = lock_user_string(arg1)))
5309             goto efault;
5310         ret = get_errno(chdir(p));
5311         unlock_user(p, arg1, 0);
5312         break;
5313 #ifdef TARGET_NR_time
5314     case TARGET_NR_time:
5315         {
5316             time_t host_time;
5317             ret = get_errno(time(&host_time));
5318             if (!is_error(ret)
5319                 && arg1
5320                 && put_user_sal(host_time, arg1))
5321                 goto efault;
5322         }
5323         break;
5324 #endif
5325     case TARGET_NR_mknod:
5326         if (!(p = lock_user_string(arg1)))
5327             goto efault;
5328         ret = get_errno(mknod(p, arg2, arg3));
5329         unlock_user(p, arg1, 0);
5330         break;
5331 #if defined(TARGET_NR_mknodat)
5332     case TARGET_NR_mknodat:
5333         if (!(p = lock_user_string(arg2)))
5334             goto efault;
5335         ret = get_errno(mknodat(arg1, p, arg3, arg4));
5336         unlock_user(p, arg2, 0);
5337         break;
5338 #endif
5339     case TARGET_NR_chmod:
5340         if (!(p = lock_user_string(arg1)))
5341             goto efault;
5342         ret = get_errno(chmod(p, arg2));
5343         unlock_user(p, arg1, 0);
5344         break;
5345 #ifdef TARGET_NR_break
5346     case TARGET_NR_break:
5347         goto unimplemented;
5348 #endif
5349 #ifdef TARGET_NR_oldstat
5350     case TARGET_NR_oldstat:
5351         goto unimplemented;
5352 #endif
5353     case TARGET_NR_lseek:
5354         ret = get_errno(lseek(arg1, arg2, arg3));
5355         break;
5356 #if defined(TARGET_NR_getxpid) && defined(TARGET_ALPHA)
5357     /* Alpha specific */
5358     case TARGET_NR_getxpid:
5359         ((CPUAlphaState *)cpu_env)->ir[IR_A4] = getppid();
5360         ret = get_errno(getpid());
5361         break;
5362 #endif
5363 #ifdef TARGET_NR_getpid
5364     case TARGET_NR_getpid:
5365         ret = get_errno(getpid());
5366         break;
5367 #endif
5368     case TARGET_NR_mount:
5369 		{
5370 			/* need to look at the data field */
5371 			void *p2, *p3;
5372 			p = lock_user_string(arg1);
5373 			p2 = lock_user_string(arg2);
5374 			p3 = lock_user_string(arg3);
5375                         if (!p || !p2 || !p3)
5376                             ret = -TARGET_EFAULT;
5377                         else {
5378                             /* FIXME - arg5 should be locked, but it isn't clear how to
5379                              * do that since it's not guaranteed to be a NULL-terminated
5380                              * string.
5381                              */
5382                             if ( ! arg5 )
5383                                 ret = get_errno(mount(p, p2, p3, (unsigned long)arg4, NULL));
5384                             else
5385                                 ret = get_errno(mount(p, p2, p3, (unsigned long)arg4, g2h(arg5)));
5386                         }
5387                         unlock_user(p, arg1, 0);
5388                         unlock_user(p2, arg2, 0);
5389                         unlock_user(p3, arg3, 0);
5390 			break;
5391 		}
5392 #ifdef TARGET_NR_umount
5393     case TARGET_NR_umount:
5394         if (!(p = lock_user_string(arg1)))
5395             goto efault;
5396         ret = get_errno(umount(p));
5397         unlock_user(p, arg1, 0);
5398         break;
5399 #endif
5400 #ifdef TARGET_NR_stime /* not on alpha */
5401     case TARGET_NR_stime:
5402         {
5403             time_t host_time;
5404             if (get_user_sal(host_time, arg1))
5405                 goto efault;
5406             ret = get_errno(stime(&host_time));
5407         }
5408         break;
5409 #endif
5410     case TARGET_NR_ptrace:
5411         goto unimplemented;
5412 #ifdef TARGET_NR_alarm /* not on alpha */
5413     case TARGET_NR_alarm:
5414         ret = alarm(arg1);
5415         break;
5416 #endif
5417 #ifdef TARGET_NR_oldfstat
5418     case TARGET_NR_oldfstat:
5419         goto unimplemented;
5420 #endif
5421 #ifdef TARGET_NR_pause /* not on alpha */
5422     case TARGET_NR_pause:
5423         ret = get_errno(pause());
5424         break;
5425 #endif
5426 #ifdef TARGET_NR_utime
5427     case TARGET_NR_utime:
5428         {
5429             struct utimbuf tbuf, *host_tbuf;
5430             struct target_utimbuf *target_tbuf;
5431             if (arg2) {
5432                 if (!lock_user_struct(VERIFY_READ, target_tbuf, arg2, 1))
5433                     goto efault;
5434                 tbuf.actime = tswapal(target_tbuf->actime);
5435                 tbuf.modtime = tswapal(target_tbuf->modtime);
5436                 unlock_user_struct(target_tbuf, arg2, 0);
5437                 host_tbuf = &tbuf;
5438             } else {
5439                 host_tbuf = NULL;
5440             }
5441             if (!(p = lock_user_string(arg1)))
5442                 goto efault;
5443             ret = get_errno(utime(p, host_tbuf));
5444             unlock_user(p, arg1, 0);
5445         }
5446         break;
5447 #endif
5448     case TARGET_NR_utimes:
5449         {
5450             struct timeval *tvp, tv[2];
5451             if (arg2) {
5452                 if (copy_from_user_timeval(&tv[0], arg2)
5453                     || copy_from_user_timeval(&tv[1],
5454                                               arg2 + sizeof(struct target_timeval)))
5455                     goto efault;
5456                 tvp = tv;
5457             } else {
5458                 tvp = NULL;
5459             }
5460             if (!(p = lock_user_string(arg1)))
5461                 goto efault;
5462             ret = get_errno(utimes(p, tvp));
5463             unlock_user(p, arg1, 0);
5464         }
5465         break;
5466 #if defined(TARGET_NR_futimesat)
5467     case TARGET_NR_futimesat:
5468         {
5469             struct timeval *tvp, tv[2];
5470             if (arg3) {
5471                 if (copy_from_user_timeval(&tv[0], arg3)
5472                     || copy_from_user_timeval(&tv[1],
5473                                               arg3 + sizeof(struct target_timeval)))
5474                     goto efault;
5475                 tvp = tv;
5476             } else {
5477                 tvp = NULL;
5478             }
5479             if (!(p = lock_user_string(arg2)))
5480                 goto efault;
5481             ret = get_errno(futimesat(arg1, path(p), tvp));
5482             unlock_user(p, arg2, 0);
5483         }
5484         break;
5485 #endif
5486 #ifdef TARGET_NR_stty
5487     case TARGET_NR_stty:
5488         goto unimplemented;
5489 #endif
5490 #ifdef TARGET_NR_gtty
5491     case TARGET_NR_gtty:
5492         goto unimplemented;
5493 #endif
5494     case TARGET_NR_access:
5495         if (!(p = lock_user_string(arg1)))
5496             goto efault;
5497         ret = get_errno(access(path(p), arg2));
5498         unlock_user(p, arg1, 0);
5499         break;
5500 #if defined(TARGET_NR_faccessat) && defined(__NR_faccessat)
5501     case TARGET_NR_faccessat:
5502         if (!(p = lock_user_string(arg2)))
5503             goto efault;
5504         ret = get_errno(faccessat(arg1, p, arg3, 0));
5505         unlock_user(p, arg2, 0);
5506         break;
5507 #endif
5508 #ifdef TARGET_NR_nice /* not on alpha */
5509     case TARGET_NR_nice:
5510         ret = get_errno(nice(arg1));
5511         break;
5512 #endif
5513 #ifdef TARGET_NR_ftime
5514     case TARGET_NR_ftime:
5515         goto unimplemented;
5516 #endif
5517     case TARGET_NR_sync:
5518         sync();
5519         ret = 0;
5520         break;
5521     case TARGET_NR_kill:
5522         ret = get_errno(kill(arg1, target_to_host_signal(arg2)));
5523         break;
5524     case TARGET_NR_rename:
5525         {
5526             void *p2;
5527             p = lock_user_string(arg1);
5528             p2 = lock_user_string(arg2);
5529             if (!p || !p2)
5530                 ret = -TARGET_EFAULT;
5531             else
5532                 ret = get_errno(rename(p, p2));
5533             unlock_user(p2, arg2, 0);
5534             unlock_user(p, arg1, 0);
5535         }
5536         break;
5537 #if defined(TARGET_NR_renameat)
5538     case TARGET_NR_renameat:
5539         {
5540             void *p2;
5541             p  = lock_user_string(arg2);
5542             p2 = lock_user_string(arg4);
5543             if (!p || !p2)
5544                 ret = -TARGET_EFAULT;
5545             else
5546                 ret = get_errno(renameat(arg1, p, arg3, p2));
5547             unlock_user(p2, arg4, 0);
5548             unlock_user(p, arg2, 0);
5549         }
5550         break;
5551 #endif
5552     case TARGET_NR_mkdir:
5553         if (!(p = lock_user_string(arg1)))
5554             goto efault;
5555         ret = get_errno(mkdir(p, arg2));
5556         unlock_user(p, arg1, 0);
5557         break;
5558 #if defined(TARGET_NR_mkdirat)
5559     case TARGET_NR_mkdirat:
5560         if (!(p = lock_user_string(arg2)))
5561             goto efault;
5562         ret = get_errno(mkdirat(arg1, p, arg3));
5563         unlock_user(p, arg2, 0);
5564         break;
5565 #endif
5566     case TARGET_NR_rmdir:
5567         if (!(p = lock_user_string(arg1)))
5568             goto efault;
5569         ret = get_errno(rmdir(p));
5570         unlock_user(p, arg1, 0);
5571         break;
5572     case TARGET_NR_dup:
5573         ret = get_errno(dup(arg1));
5574         break;
5575     case TARGET_NR_pipe:
5576         ret = do_pipe(cpu_env, arg1, 0, 0);
5577         break;
5578 #ifdef TARGET_NR_pipe2
5579     case TARGET_NR_pipe2:
5580         ret = do_pipe(cpu_env, arg1,
5581                       target_to_host_bitmask(arg2, fcntl_flags_tbl), 1);
5582         break;
5583 #endif
5584     case TARGET_NR_times:
5585         {
5586             struct target_tms *tmsp;
5587             struct tms tms;
5588             ret = get_errno(times(&tms));
5589             if (arg1) {
5590                 tmsp = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_tms), 0);
5591                 if (!tmsp)
5592                     goto efault;
5593                 tmsp->tms_utime = tswapal(host_to_target_clock_t(tms.tms_utime));
5594                 tmsp->tms_stime = tswapal(host_to_target_clock_t(tms.tms_stime));
5595                 tmsp->tms_cutime = tswapal(host_to_target_clock_t(tms.tms_cutime));
5596                 tmsp->tms_cstime = tswapal(host_to_target_clock_t(tms.tms_cstime));
5597             }
5598             if (!is_error(ret))
5599                 ret = host_to_target_clock_t(ret);
5600         }
5601         break;
5602 #ifdef TARGET_NR_prof
5603     case TARGET_NR_prof:
5604         goto unimplemented;
5605 #endif
5606 #ifdef TARGET_NR_signal
5607     case TARGET_NR_signal:
5608         goto unimplemented;
5609 #endif
5610     case TARGET_NR_acct:
5611         if (arg1 == 0) {
5612             ret = get_errno(acct(NULL));
5613         } else {
5614             if (!(p = lock_user_string(arg1)))
5615                 goto efault;
5616             ret = get_errno(acct(path(p)));
5617             unlock_user(p, arg1, 0);
5618         }
5619         break;
5620 #ifdef TARGET_NR_umount2 /* not on alpha */
5621     case TARGET_NR_umount2:
5622         if (!(p = lock_user_string(arg1)))
5623             goto efault;
5624         ret = get_errno(umount2(p, arg2));
5625         unlock_user(p, arg1, 0);
5626         break;
5627 #endif
5628 #ifdef TARGET_NR_lock
5629     case TARGET_NR_lock:
5630         goto unimplemented;
5631 #endif
5632     case TARGET_NR_ioctl:
5633         ret = do_ioctl(arg1, arg2, arg3);
5634         break;
5635     case TARGET_NR_fcntl:
5636         ret = do_fcntl(arg1, arg2, arg3);
5637         break;
5638 #ifdef TARGET_NR_mpx
5639     case TARGET_NR_mpx:
5640         goto unimplemented;
5641 #endif
5642     case TARGET_NR_setpgid:
5643         ret = get_errno(setpgid(arg1, arg2));
5644         break;
5645 #ifdef TARGET_NR_ulimit
5646     case TARGET_NR_ulimit:
5647         goto unimplemented;
5648 #endif
5649 #ifdef TARGET_NR_oldolduname
5650     case TARGET_NR_oldolduname:
5651         goto unimplemented;
5652 #endif
5653     case TARGET_NR_umask:
5654         ret = get_errno(umask(arg1));
5655         break;
5656     case TARGET_NR_chroot:
5657         if (!(p = lock_user_string(arg1)))
5658             goto efault;
5659         ret = get_errno(chroot(p));
5660         unlock_user(p, arg1, 0);
5661         break;
5662     case TARGET_NR_ustat:
5663         goto unimplemented;
5664     case TARGET_NR_dup2:
5665         ret = get_errno(dup2(arg1, arg2));
5666         break;
5667 #if defined(CONFIG_DUP3) && defined(TARGET_NR_dup3)
5668     case TARGET_NR_dup3:
5669         ret = get_errno(dup3(arg1, arg2, arg3));
5670         break;
5671 #endif
5672 #ifdef TARGET_NR_getppid /* not on alpha */
5673     case TARGET_NR_getppid:
5674         ret = get_errno(getppid());
5675         break;
5676 #endif
5677     case TARGET_NR_getpgrp:
5678         ret = get_errno(getpgrp());
5679         break;
5680     case TARGET_NR_setsid:
5681         ret = get_errno(setsid());
5682         break;
5683 #ifdef TARGET_NR_sigaction
5684     case TARGET_NR_sigaction:
5685         {
5686 #if defined(TARGET_ALPHA)
5687             struct target_sigaction act, oact, *pact = 0;
5688             struct target_old_sigaction *old_act;
5689             if (arg2) {
5690                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5691                     goto efault;
5692                 act._sa_handler = old_act->_sa_handler;
5693                 target_siginitset(&act.sa_mask, old_act->sa_mask);
5694                 act.sa_flags = old_act->sa_flags;
5695                 act.sa_restorer = 0;
5696                 unlock_user_struct(old_act, arg2, 0);
5697                 pact = &act;
5698             }
5699             ret = get_errno(do_sigaction(arg1, pact, &oact));
5700             if (!is_error(ret) && arg3) {
5701                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5702                     goto efault;
5703                 old_act->_sa_handler = oact._sa_handler;
5704                 old_act->sa_mask = oact.sa_mask.sig[0];
5705                 old_act->sa_flags = oact.sa_flags;
5706                 unlock_user_struct(old_act, arg3, 1);
5707             }
5708 #elif defined(TARGET_MIPS)
5709 	    struct target_sigaction act, oact, *pact, *old_act;
5710 
5711 	    if (arg2) {
5712                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5713                     goto efault;
5714 		act._sa_handler = old_act->_sa_handler;
5715 		target_siginitset(&act.sa_mask, old_act->sa_mask.sig[0]);
5716 		act.sa_flags = old_act->sa_flags;
5717 		unlock_user_struct(old_act, arg2, 0);
5718 		pact = &act;
5719 	    } else {
5720 		pact = NULL;
5721 	    }
5722 
5723 	    ret = get_errno(do_sigaction(arg1, pact, &oact));
5724 
5725 	    if (!is_error(ret) && arg3) {
5726                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5727                     goto efault;
5728 		old_act->_sa_handler = oact._sa_handler;
5729 		old_act->sa_flags = oact.sa_flags;
5730 		old_act->sa_mask.sig[0] = oact.sa_mask.sig[0];
5731 		old_act->sa_mask.sig[1] = 0;
5732 		old_act->sa_mask.sig[2] = 0;
5733 		old_act->sa_mask.sig[3] = 0;
5734 		unlock_user_struct(old_act, arg3, 1);
5735 	    }
5736 #else
5737             struct target_old_sigaction *old_act;
5738             struct target_sigaction act, oact, *pact;
5739             if (arg2) {
5740                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5741                     goto efault;
5742                 act._sa_handler = old_act->_sa_handler;
5743                 target_siginitset(&act.sa_mask, old_act->sa_mask);
5744                 act.sa_flags = old_act->sa_flags;
5745                 act.sa_restorer = old_act->sa_restorer;
5746                 unlock_user_struct(old_act, arg2, 0);
5747                 pact = &act;
5748             } else {
5749                 pact = NULL;
5750             }
5751             ret = get_errno(do_sigaction(arg1, pact, &oact));
5752             if (!is_error(ret) && arg3) {
5753                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5754                     goto efault;
5755                 old_act->_sa_handler = oact._sa_handler;
5756                 old_act->sa_mask = oact.sa_mask.sig[0];
5757                 old_act->sa_flags = oact.sa_flags;
5758                 old_act->sa_restorer = oact.sa_restorer;
5759                 unlock_user_struct(old_act, arg3, 1);
5760             }
5761 #endif
5762         }
5763         break;
5764 #endif
5765     case TARGET_NR_rt_sigaction:
5766         {
5767 #if defined(TARGET_ALPHA)
5768             struct target_sigaction act, oact, *pact = 0;
5769             struct target_rt_sigaction *rt_act;
5770             /* ??? arg4 == sizeof(sigset_t).  */
5771             if (arg2) {
5772                 if (!lock_user_struct(VERIFY_READ, rt_act, arg2, 1))
5773                     goto efault;
5774                 act._sa_handler = rt_act->_sa_handler;
5775                 act.sa_mask = rt_act->sa_mask;
5776                 act.sa_flags = rt_act->sa_flags;
5777                 act.sa_restorer = arg5;
5778                 unlock_user_struct(rt_act, arg2, 0);
5779                 pact = &act;
5780             }
5781             ret = get_errno(do_sigaction(arg1, pact, &oact));
5782             if (!is_error(ret) && arg3) {
5783                 if (!lock_user_struct(VERIFY_WRITE, rt_act, arg3, 0))
5784                     goto efault;
5785                 rt_act->_sa_handler = oact._sa_handler;
5786                 rt_act->sa_mask = oact.sa_mask;
5787                 rt_act->sa_flags = oact.sa_flags;
5788                 unlock_user_struct(rt_act, arg3, 1);
5789             }
5790 #else
5791             struct target_sigaction *act;
5792             struct target_sigaction *oact;
5793 
5794             if (arg2) {
5795                 if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
5796                     goto efault;
5797             } else
5798                 act = NULL;
5799             if (arg3) {
5800                 if (!lock_user_struct(VERIFY_WRITE, oact, arg3, 0)) {
5801                     ret = -TARGET_EFAULT;
5802                     goto rt_sigaction_fail;
5803                 }
5804             } else
5805                 oact = NULL;
5806             ret = get_errno(do_sigaction(arg1, act, oact));
5807 	rt_sigaction_fail:
5808             if (act)
5809                 unlock_user_struct(act, arg2, 0);
5810             if (oact)
5811                 unlock_user_struct(oact, arg3, 1);
5812 #endif
5813         }
5814         break;
5815 #ifdef TARGET_NR_sgetmask /* not on alpha */
5816     case TARGET_NR_sgetmask:
5817         {
5818             sigset_t cur_set;
5819             abi_ulong target_set;
5820             sigprocmask(0, NULL, &cur_set);
5821             host_to_target_old_sigset(&target_set, &cur_set);
5822             ret = target_set;
5823         }
5824         break;
5825 #endif
5826 #ifdef TARGET_NR_ssetmask /* not on alpha */
5827     case TARGET_NR_ssetmask:
5828         {
5829             sigset_t set, oset, cur_set;
5830             abi_ulong target_set = arg1;
5831             sigprocmask(0, NULL, &cur_set);
5832             target_to_host_old_sigset(&set, &target_set);
5833             sigorset(&set, &set, &cur_set);
5834             sigprocmask(SIG_SETMASK, &set, &oset);
5835             host_to_target_old_sigset(&target_set, &oset);
5836             ret = target_set;
5837         }
5838         break;
5839 #endif
5840 #ifdef TARGET_NR_sigprocmask
5841     case TARGET_NR_sigprocmask:
5842         {
5843 #if defined(TARGET_ALPHA)
5844             sigset_t set, oldset;
5845             abi_ulong mask;
5846             int how;
5847 
5848             switch (arg1) {
5849             case TARGET_SIG_BLOCK:
5850                 how = SIG_BLOCK;
5851                 break;
5852             case TARGET_SIG_UNBLOCK:
5853                 how = SIG_UNBLOCK;
5854                 break;
5855             case TARGET_SIG_SETMASK:
5856                 how = SIG_SETMASK;
5857                 break;
5858             default:
5859                 ret = -TARGET_EINVAL;
5860                 goto fail;
5861             }
5862             mask = arg2;
5863             target_to_host_old_sigset(&set, &mask);
5864 
5865             ret = get_errno(sigprocmask(how, &set, &oldset));
5866             if (!is_error(ret)) {
5867                 host_to_target_old_sigset(&mask, &oldset);
5868                 ret = mask;
5869                 ((CPUAlphaState *)cpu_env)->ir[IR_V0] = 0; /* force no error */
5870             }
5871 #else
5872             sigset_t set, oldset, *set_ptr;
5873             int how;
5874 
5875             if (arg2) {
5876                 switch (arg1) {
5877                 case TARGET_SIG_BLOCK:
5878                     how = SIG_BLOCK;
5879                     break;
5880                 case TARGET_SIG_UNBLOCK:
5881                     how = SIG_UNBLOCK;
5882                     break;
5883                 case TARGET_SIG_SETMASK:
5884                     how = SIG_SETMASK;
5885                     break;
5886                 default:
5887                     ret = -TARGET_EINVAL;
5888                     goto fail;
5889                 }
5890                 if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
5891                     goto efault;
5892                 target_to_host_old_sigset(&set, p);
5893                 unlock_user(p, arg2, 0);
5894                 set_ptr = &set;
5895             } else {
5896                 how = 0;
5897                 set_ptr = NULL;
5898             }
5899             ret = get_errno(sigprocmask(how, set_ptr, &oldset));
5900             if (!is_error(ret) && arg3) {
5901                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
5902                     goto efault;
5903                 host_to_target_old_sigset(p, &oldset);
5904                 unlock_user(p, arg3, sizeof(target_sigset_t));
5905             }
5906 #endif
5907         }
5908         break;
5909 #endif
5910     case TARGET_NR_rt_sigprocmask:
5911         {
5912             int how = arg1;
5913             sigset_t set, oldset, *set_ptr;
5914 
5915             if (arg2) {
5916                 switch(how) {
5917                 case TARGET_SIG_BLOCK:
5918                     how = SIG_BLOCK;
5919                     break;
5920                 case TARGET_SIG_UNBLOCK:
5921                     how = SIG_UNBLOCK;
5922                     break;
5923                 case TARGET_SIG_SETMASK:
5924                     how = SIG_SETMASK;
5925                     break;
5926                 default:
5927                     ret = -TARGET_EINVAL;
5928                     goto fail;
5929                 }
5930                 if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
5931                     goto efault;
5932                 target_to_host_sigset(&set, p);
5933                 unlock_user(p, arg2, 0);
5934                 set_ptr = &set;
5935             } else {
5936                 how = 0;
5937                 set_ptr = NULL;
5938             }
5939             ret = get_errno(sigprocmask(how, set_ptr, &oldset));
5940             if (!is_error(ret) && arg3) {
5941                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
5942                     goto efault;
5943                 host_to_target_sigset(p, &oldset);
5944                 unlock_user(p, arg3, sizeof(target_sigset_t));
5945             }
5946         }
5947         break;
5948 #ifdef TARGET_NR_sigpending
5949     case TARGET_NR_sigpending:
5950         {
5951             sigset_t set;
5952             ret = get_errno(sigpending(&set));
5953             if (!is_error(ret)) {
5954                 if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
5955                     goto efault;
5956                 host_to_target_old_sigset(p, &set);
5957                 unlock_user(p, arg1, sizeof(target_sigset_t));
5958             }
5959         }
5960         break;
5961 #endif
5962     case TARGET_NR_rt_sigpending:
5963         {
5964             sigset_t set;
5965             ret = get_errno(sigpending(&set));
5966             if (!is_error(ret)) {
5967                 if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
5968                     goto efault;
5969                 host_to_target_sigset(p, &set);
5970                 unlock_user(p, arg1, sizeof(target_sigset_t));
5971             }
5972         }
5973         break;
5974 #ifdef TARGET_NR_sigsuspend
5975     case TARGET_NR_sigsuspend:
5976         {
5977             sigset_t set;
5978 #if defined(TARGET_ALPHA)
5979             abi_ulong mask = arg1;
5980             target_to_host_old_sigset(&set, &mask);
5981 #else
5982             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
5983                 goto efault;
5984             target_to_host_old_sigset(&set, p);
5985             unlock_user(p, arg1, 0);
5986 #endif
5987             ret = get_errno(sigsuspend(&set));
5988         }
5989         break;
5990 #endif
5991     case TARGET_NR_rt_sigsuspend:
5992         {
5993             sigset_t set;
5994             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
5995                 goto efault;
5996             target_to_host_sigset(&set, p);
5997             unlock_user(p, arg1, 0);
5998             ret = get_errno(sigsuspend(&set));
5999         }
6000         break;
6001     case TARGET_NR_rt_sigtimedwait:
6002         {
6003             sigset_t set;
6004             struct timespec uts, *puts;
6005             siginfo_t uinfo;
6006 
6007             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
6008                 goto efault;
6009             target_to_host_sigset(&set, p);
6010             unlock_user(p, arg1, 0);
6011             if (arg3) {
6012                 puts = &uts;
6013                 target_to_host_timespec(puts, arg3);
6014             } else {
6015                 puts = NULL;
6016             }
6017             ret = get_errno(sigtimedwait(&set, &uinfo, puts));
6018             if (!is_error(ret) && arg2) {
6019                 if (!(p = lock_user(VERIFY_WRITE, arg2, sizeof(target_siginfo_t), 0)))
6020                     goto efault;
6021                 host_to_target_siginfo(p, &uinfo);
6022                 unlock_user(p, arg2, sizeof(target_siginfo_t));
6023             }
6024         }
6025         break;
6026     case TARGET_NR_rt_sigqueueinfo:
6027         {
6028             siginfo_t uinfo;
6029             if (!(p = lock_user(VERIFY_READ, arg3, sizeof(target_sigset_t), 1)))
6030                 goto efault;
6031             target_to_host_siginfo(&uinfo, p);
6032             unlock_user(p, arg1, 0);
6033             ret = get_errno(sys_rt_sigqueueinfo(arg1, arg2, &uinfo));
6034         }
6035         break;
6036 #ifdef TARGET_NR_sigreturn
6037     case TARGET_NR_sigreturn:
6038         /* NOTE: ret is eax, so not transcoding must be done */
6039         ret = do_sigreturn(cpu_env);
6040         break;
6041 #endif
6042     case TARGET_NR_rt_sigreturn:
6043         /* NOTE: ret is eax, so not transcoding must be done */
6044         ret = do_rt_sigreturn(cpu_env);
6045         break;
6046     case TARGET_NR_sethostname:
6047         if (!(p = lock_user_string(arg1)))
6048             goto efault;
6049         ret = get_errno(sethostname(p, arg2));
6050         unlock_user(p, arg1, 0);
6051         break;
6052     case TARGET_NR_setrlimit:
6053         {
6054             int resource = target_to_host_resource(arg1);
6055             struct target_rlimit *target_rlim;
6056             struct rlimit rlim;
6057             if (!lock_user_struct(VERIFY_READ, target_rlim, arg2, 1))
6058                 goto efault;
6059             rlim.rlim_cur = target_to_host_rlim(target_rlim->rlim_cur);
6060             rlim.rlim_max = target_to_host_rlim(target_rlim->rlim_max);
6061             unlock_user_struct(target_rlim, arg2, 0);
6062             ret = get_errno(setrlimit(resource, &rlim));
6063         }
6064         break;
6065     case TARGET_NR_getrlimit:
6066         {
6067             int resource = target_to_host_resource(arg1);
6068             struct target_rlimit *target_rlim;
6069             struct rlimit rlim;
6070 
6071             ret = get_errno(getrlimit(resource, &rlim));
6072             if (!is_error(ret)) {
6073                 if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
6074                     goto efault;
6075                 target_rlim->rlim_cur = host_to_target_rlim(rlim.rlim_cur);
6076                 target_rlim->rlim_max = host_to_target_rlim(rlim.rlim_max);
6077                 unlock_user_struct(target_rlim, arg2, 1);
6078             }
6079         }
6080         break;
6081     case TARGET_NR_getrusage:
6082         {
6083             struct rusage rusage;
6084             ret = get_errno(getrusage(arg1, &rusage));
6085             if (!is_error(ret)) {
6086                 host_to_target_rusage(arg2, &rusage);
6087             }
6088         }
6089         break;
6090     case TARGET_NR_gettimeofday:
6091         {
6092             struct timeval tv;
6093             ret = get_errno(gettimeofday(&tv, NULL));
6094             if (!is_error(ret)) {
6095                 if (copy_to_user_timeval(arg1, &tv))
6096                     goto efault;
6097             }
6098         }
6099         break;
6100     case TARGET_NR_settimeofday:
6101         {
6102             struct timeval tv;
6103             if (copy_from_user_timeval(&tv, arg1))
6104                 goto efault;
6105             ret = get_errno(settimeofday(&tv, NULL));
6106         }
6107         break;
6108 #if defined(TARGET_NR_select)
6109     case TARGET_NR_select:
6110 #if defined(TARGET_S390X) || defined(TARGET_ALPHA)
6111         ret = do_select(arg1, arg2, arg3, arg4, arg5);
6112 #else
6113         {
6114             struct target_sel_arg_struct *sel;
6115             abi_ulong inp, outp, exp, tvp;
6116             long nsel;
6117 
6118             if (!lock_user_struct(VERIFY_READ, sel, arg1, 1))
6119                 goto efault;
6120             nsel = tswapal(sel->n);
6121             inp = tswapal(sel->inp);
6122             outp = tswapal(sel->outp);
6123             exp = tswapal(sel->exp);
6124             tvp = tswapal(sel->tvp);
6125             unlock_user_struct(sel, arg1, 0);
6126             ret = do_select(nsel, inp, outp, exp, tvp);
6127         }
6128 #endif
6129         break;
6130 #endif
6131 #ifdef TARGET_NR_pselect6
6132     case TARGET_NR_pselect6:
6133         {
6134             abi_long rfd_addr, wfd_addr, efd_addr, n, ts_addr;
6135             fd_set rfds, wfds, efds;
6136             fd_set *rfds_ptr, *wfds_ptr, *efds_ptr;
6137             struct timespec ts, *ts_ptr;
6138 
6139             /*
6140              * The 6th arg is actually two args smashed together,
6141              * so we cannot use the C library.
6142              */
6143             sigset_t set;
6144             struct {
6145                 sigset_t *set;
6146                 size_t size;
6147             } sig, *sig_ptr;
6148 
6149             abi_ulong arg_sigset, arg_sigsize, *arg7;
6150             target_sigset_t *target_sigset;
6151 
6152             n = arg1;
6153             rfd_addr = arg2;
6154             wfd_addr = arg3;
6155             efd_addr = arg4;
6156             ts_addr = arg5;
6157 
6158             ret = copy_from_user_fdset_ptr(&rfds, &rfds_ptr, rfd_addr, n);
6159             if (ret) {
6160                 goto fail;
6161             }
6162             ret = copy_from_user_fdset_ptr(&wfds, &wfds_ptr, wfd_addr, n);
6163             if (ret) {
6164                 goto fail;
6165             }
6166             ret = copy_from_user_fdset_ptr(&efds, &efds_ptr, efd_addr, n);
6167             if (ret) {
6168                 goto fail;
6169             }
6170 
6171             /*
6172              * This takes a timespec, and not a timeval, so we cannot
6173              * use the do_select() helper ...
6174              */
6175             if (ts_addr) {
6176                 if (target_to_host_timespec(&ts, ts_addr)) {
6177                     goto efault;
6178                 }
6179                 ts_ptr = &ts;
6180             } else {
6181                 ts_ptr = NULL;
6182             }
6183 
6184             /* Extract the two packed args for the sigset */
6185             if (arg6) {
6186                 sig_ptr = &sig;
6187                 sig.size = _NSIG / 8;
6188 
6189                 arg7 = lock_user(VERIFY_READ, arg6, sizeof(*arg7) * 2, 1);
6190                 if (!arg7) {
6191                     goto efault;
6192                 }
6193                 arg_sigset = tswapal(arg7[0]);
6194                 arg_sigsize = tswapal(arg7[1]);
6195                 unlock_user(arg7, arg6, 0);
6196 
6197                 if (arg_sigset) {
6198                     sig.set = &set;
6199                     if (arg_sigsize != sizeof(*target_sigset)) {
6200                         /* Like the kernel, we enforce correct size sigsets */
6201                         ret = -TARGET_EINVAL;
6202                         goto fail;
6203                     }
6204                     target_sigset = lock_user(VERIFY_READ, arg_sigset,
6205                                               sizeof(*target_sigset), 1);
6206                     if (!target_sigset) {
6207                         goto efault;
6208                     }
6209                     target_to_host_sigset(&set, target_sigset);
6210                     unlock_user(target_sigset, arg_sigset, 0);
6211                 } else {
6212                     sig.set = NULL;
6213                 }
6214             } else {
6215                 sig_ptr = NULL;
6216             }
6217 
6218             ret = get_errno(sys_pselect6(n, rfds_ptr, wfds_ptr, efds_ptr,
6219                                          ts_ptr, sig_ptr));
6220 
6221             if (!is_error(ret)) {
6222                 if (rfd_addr && copy_to_user_fdset(rfd_addr, &rfds, n))
6223                     goto efault;
6224                 if (wfd_addr && copy_to_user_fdset(wfd_addr, &wfds, n))
6225                     goto efault;
6226                 if (efd_addr && copy_to_user_fdset(efd_addr, &efds, n))
6227                     goto efault;
6228 
6229                 if (ts_addr && host_to_target_timespec(ts_addr, &ts))
6230                     goto efault;
6231             }
6232         }
6233         break;
6234 #endif
6235     case TARGET_NR_symlink:
6236         {
6237             void *p2;
6238             p = lock_user_string(arg1);
6239             p2 = lock_user_string(arg2);
6240             if (!p || !p2)
6241                 ret = -TARGET_EFAULT;
6242             else
6243                 ret = get_errno(symlink(p, p2));
6244             unlock_user(p2, arg2, 0);
6245             unlock_user(p, arg1, 0);
6246         }
6247         break;
6248 #if defined(TARGET_NR_symlinkat)
6249     case TARGET_NR_symlinkat:
6250         {
6251             void *p2;
6252             p  = lock_user_string(arg1);
6253             p2 = lock_user_string(arg3);
6254             if (!p || !p2)
6255                 ret = -TARGET_EFAULT;
6256             else
6257                 ret = get_errno(symlinkat(p, arg2, p2));
6258             unlock_user(p2, arg3, 0);
6259             unlock_user(p, arg1, 0);
6260         }
6261         break;
6262 #endif
6263 #ifdef TARGET_NR_oldlstat
6264     case TARGET_NR_oldlstat:
6265         goto unimplemented;
6266 #endif
6267     case TARGET_NR_readlink:
6268         {
6269             void *p2, *temp;
6270             p = lock_user_string(arg1);
6271             p2 = lock_user(VERIFY_WRITE, arg2, arg3, 0);
6272             if (!p || !p2)
6273                 ret = -TARGET_EFAULT;
6274             else {
6275                 if (strncmp((const char *)p, "/proc/self/exe", 14) == 0) {
6276                     char real[PATH_MAX];
6277                     temp = realpath(exec_path,real);
6278                     ret = (temp==NULL) ? get_errno(-1) : strlen(real) ;
6279                     snprintf((char *)p2, arg3, "%s", real);
6280                     }
6281                 else
6282                     ret = get_errno(readlink(path(p), p2, arg3));
6283             }
6284             unlock_user(p2, arg2, ret);
6285             unlock_user(p, arg1, 0);
6286         }
6287         break;
6288 #if defined(TARGET_NR_readlinkat)
6289     case TARGET_NR_readlinkat:
6290         {
6291             void *p2;
6292             p  = lock_user_string(arg2);
6293             p2 = lock_user(VERIFY_WRITE, arg3, arg4, 0);
6294             if (!p || !p2)
6295         	ret = -TARGET_EFAULT;
6296             else
6297                 ret = get_errno(readlinkat(arg1, path(p), p2, arg4));
6298             unlock_user(p2, arg3, ret);
6299             unlock_user(p, arg2, 0);
6300         }
6301         break;
6302 #endif
6303 #ifdef TARGET_NR_uselib
6304     case TARGET_NR_uselib:
6305         goto unimplemented;
6306 #endif
6307 #ifdef TARGET_NR_swapon
6308     case TARGET_NR_swapon:
6309         if (!(p = lock_user_string(arg1)))
6310             goto efault;
6311         ret = get_errno(swapon(p, arg2));
6312         unlock_user(p, arg1, 0);
6313         break;
6314 #endif
6315     case TARGET_NR_reboot:
6316         if (arg3 == LINUX_REBOOT_CMD_RESTART2) {
6317            /* arg4 must be ignored in all other cases */
6318            p = lock_user_string(arg4);
6319            if (!p) {
6320               goto efault;
6321            }
6322            ret = get_errno(reboot(arg1, arg2, arg3, p));
6323            unlock_user(p, arg4, 0);
6324         } else {
6325            ret = get_errno(reboot(arg1, arg2, arg3, NULL));
6326         }
6327         break;
6328 #ifdef TARGET_NR_readdir
6329     case TARGET_NR_readdir:
6330         goto unimplemented;
6331 #endif
6332 #ifdef TARGET_NR_mmap
6333     case TARGET_NR_mmap:
6334 #if (defined(TARGET_I386) && defined(TARGET_ABI32)) || defined(TARGET_ARM) || \
6335     defined(TARGET_M68K) || defined(TARGET_CRIS) || defined(TARGET_MICROBLAZE) \
6336     || defined(TARGET_S390X)
6337         {
6338             abi_ulong *v;
6339             abi_ulong v1, v2, v3, v4, v5, v6;
6340             if (!(v = lock_user(VERIFY_READ, arg1, 6 * sizeof(abi_ulong), 1)))
6341                 goto efault;
6342             v1 = tswapal(v[0]);
6343             v2 = tswapal(v[1]);
6344             v3 = tswapal(v[2]);
6345             v4 = tswapal(v[3]);
6346             v5 = tswapal(v[4]);
6347             v6 = tswapal(v[5]);
6348             unlock_user(v, arg1, 0);
6349             ret = get_errno(target_mmap(v1, v2, v3,
6350                                         target_to_host_bitmask(v4, mmap_flags_tbl),
6351                                         v5, v6));
6352         }
6353 #else
6354         ret = get_errno(target_mmap(arg1, arg2, arg3,
6355                                     target_to_host_bitmask(arg4, mmap_flags_tbl),
6356                                     arg5,
6357                                     arg6));
6358 #endif
6359         break;
6360 #endif
6361 #ifdef TARGET_NR_mmap2
6362     case TARGET_NR_mmap2:
6363 #ifndef MMAP_SHIFT
6364 #define MMAP_SHIFT 12
6365 #endif
6366         ret = get_errno(target_mmap(arg1, arg2, arg3,
6367                                     target_to_host_bitmask(arg4, mmap_flags_tbl),
6368                                     arg5,
6369                                     arg6 << MMAP_SHIFT));
6370         break;
6371 #endif
6372     case TARGET_NR_munmap:
6373         ret = get_errno(target_munmap(arg1, arg2));
6374         break;
6375     case TARGET_NR_mprotect:
6376         {
6377             TaskState *ts = ((CPUArchState *)cpu_env)->opaque;
6378             /* Special hack to detect libc making the stack executable.  */
6379             if ((arg3 & PROT_GROWSDOWN)
6380                 && arg1 >= ts->info->stack_limit
6381                 && arg1 <= ts->info->start_stack) {
6382                 arg3 &= ~PROT_GROWSDOWN;
6383                 arg2 = arg2 + arg1 - ts->info->stack_limit;
6384                 arg1 = ts->info->stack_limit;
6385             }
6386         }
6387         ret = get_errno(target_mprotect(arg1, arg2, arg3));
6388         break;
6389 #ifdef TARGET_NR_mremap
6390     case TARGET_NR_mremap:
6391         ret = get_errno(target_mremap(arg1, arg2, arg3, arg4, arg5));
6392         break;
6393 #endif
6394         /* ??? msync/mlock/munlock are broken for softmmu.  */
6395 #ifdef TARGET_NR_msync
6396     case TARGET_NR_msync:
6397         ret = get_errno(msync(g2h(arg1), arg2, arg3));
6398         break;
6399 #endif
6400 #ifdef TARGET_NR_mlock
6401     case TARGET_NR_mlock:
6402         ret = get_errno(mlock(g2h(arg1), arg2));
6403         break;
6404 #endif
6405 #ifdef TARGET_NR_munlock
6406     case TARGET_NR_munlock:
6407         ret = get_errno(munlock(g2h(arg1), arg2));
6408         break;
6409 #endif
6410 #ifdef TARGET_NR_mlockall
6411     case TARGET_NR_mlockall:
6412         ret = get_errno(mlockall(arg1));
6413         break;
6414 #endif
6415 #ifdef TARGET_NR_munlockall
6416     case TARGET_NR_munlockall:
6417         ret = get_errno(munlockall());
6418         break;
6419 #endif
6420     case TARGET_NR_truncate:
6421         if (!(p = lock_user_string(arg1)))
6422             goto efault;
6423         ret = get_errno(truncate(p, arg2));
6424         unlock_user(p, arg1, 0);
6425         break;
6426     case TARGET_NR_ftruncate:
6427         ret = get_errno(ftruncate(arg1, arg2));
6428         break;
6429     case TARGET_NR_fchmod:
6430         ret = get_errno(fchmod(arg1, arg2));
6431         break;
6432 #if defined(TARGET_NR_fchmodat)
6433     case TARGET_NR_fchmodat:
6434         if (!(p = lock_user_string(arg2)))
6435             goto efault;
6436         ret = get_errno(fchmodat(arg1, p, arg3, 0));
6437         unlock_user(p, arg2, 0);
6438         break;
6439 #endif
6440     case TARGET_NR_getpriority:
6441         /* Note that negative values are valid for getpriority, so we must
6442            differentiate based on errno settings.  */
6443         errno = 0;
6444         ret = getpriority(arg1, arg2);
6445         if (ret == -1 && errno != 0) {
6446             ret = -host_to_target_errno(errno);
6447             break;
6448         }
6449 #ifdef TARGET_ALPHA
6450         /* Return value is the unbiased priority.  Signal no error.  */
6451         ((CPUAlphaState *)cpu_env)->ir[IR_V0] = 0;
6452 #else
6453         /* Return value is a biased priority to avoid negative numbers.  */
6454         ret = 20 - ret;
6455 #endif
6456         break;
6457     case TARGET_NR_setpriority:
6458         ret = get_errno(setpriority(arg1, arg2, arg3));
6459         break;
6460 #ifdef TARGET_NR_profil
6461     case TARGET_NR_profil:
6462         goto unimplemented;
6463 #endif
6464     case TARGET_NR_statfs:
6465         if (!(p = lock_user_string(arg1)))
6466             goto efault;
6467         ret = get_errno(statfs(path(p), &stfs));
6468         unlock_user(p, arg1, 0);
6469     convert_statfs:
6470         if (!is_error(ret)) {
6471             struct target_statfs *target_stfs;
6472 
6473             if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg2, 0))
6474                 goto efault;
6475             __put_user(stfs.f_type, &target_stfs->f_type);
6476             __put_user(stfs.f_bsize, &target_stfs->f_bsize);
6477             __put_user(stfs.f_blocks, &target_stfs->f_blocks);
6478             __put_user(stfs.f_bfree, &target_stfs->f_bfree);
6479             __put_user(stfs.f_bavail, &target_stfs->f_bavail);
6480             __put_user(stfs.f_files, &target_stfs->f_files);
6481             __put_user(stfs.f_ffree, &target_stfs->f_ffree);
6482             __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
6483             __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
6484             __put_user(stfs.f_namelen, &target_stfs->f_namelen);
6485             __put_user(stfs.f_frsize, &target_stfs->f_frsize);
6486             memset(target_stfs->f_spare, 0, sizeof(target_stfs->f_spare));
6487             unlock_user_struct(target_stfs, arg2, 1);
6488         }
6489         break;
6490     case TARGET_NR_fstatfs:
6491         ret = get_errno(fstatfs(arg1, &stfs));
6492         goto convert_statfs;
6493 #ifdef TARGET_NR_statfs64
6494     case TARGET_NR_statfs64:
6495         if (!(p = lock_user_string(arg1)))
6496             goto efault;
6497         ret = get_errno(statfs(path(p), &stfs));
6498         unlock_user(p, arg1, 0);
6499     convert_statfs64:
6500         if (!is_error(ret)) {
6501             struct target_statfs64 *target_stfs;
6502 
6503             if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg3, 0))
6504                 goto efault;
6505             __put_user(stfs.f_type, &target_stfs->f_type);
6506             __put_user(stfs.f_bsize, &target_stfs->f_bsize);
6507             __put_user(stfs.f_blocks, &target_stfs->f_blocks);
6508             __put_user(stfs.f_bfree, &target_stfs->f_bfree);
6509             __put_user(stfs.f_bavail, &target_stfs->f_bavail);
6510             __put_user(stfs.f_files, &target_stfs->f_files);
6511             __put_user(stfs.f_ffree, &target_stfs->f_ffree);
6512             __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
6513             __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
6514             __put_user(stfs.f_namelen, &target_stfs->f_namelen);
6515             __put_user(stfs.f_frsize, &target_stfs->f_frsize);
6516             memset(target_stfs->f_spare, 0, sizeof(target_stfs->f_spare));
6517             unlock_user_struct(target_stfs, arg3, 1);
6518         }
6519         break;
6520     case TARGET_NR_fstatfs64:
6521         ret = get_errno(fstatfs(arg1, &stfs));
6522         goto convert_statfs64;
6523 #endif
6524 #ifdef TARGET_NR_ioperm
6525     case TARGET_NR_ioperm:
6526         goto unimplemented;
6527 #endif
6528 #ifdef TARGET_NR_socketcall
6529     case TARGET_NR_socketcall:
6530         ret = do_socketcall(arg1, arg2);
6531         break;
6532 #endif
6533 #ifdef TARGET_NR_accept
6534     case TARGET_NR_accept:
6535         ret = do_accept4(arg1, arg2, arg3, 0);
6536         break;
6537 #endif
6538 #ifdef TARGET_NR_accept4
6539     case TARGET_NR_accept4:
6540 #ifdef CONFIG_ACCEPT4
6541         ret = do_accept4(arg1, arg2, arg3, arg4);
6542 #else
6543         goto unimplemented;
6544 #endif
6545         break;
6546 #endif
6547 #ifdef TARGET_NR_bind
6548     case TARGET_NR_bind:
6549         ret = do_bind(arg1, arg2, arg3);
6550         break;
6551 #endif
6552 #ifdef TARGET_NR_connect
6553     case TARGET_NR_connect:
6554         ret = do_connect(arg1, arg2, arg3);
6555         break;
6556 #endif
6557 #ifdef TARGET_NR_getpeername
6558     case TARGET_NR_getpeername:
6559         ret = do_getpeername(arg1, arg2, arg3);
6560         break;
6561 #endif
6562 #ifdef TARGET_NR_getsockname
6563     case TARGET_NR_getsockname:
6564         ret = do_getsockname(arg1, arg2, arg3);
6565         break;
6566 #endif
6567 #ifdef TARGET_NR_getsockopt
6568     case TARGET_NR_getsockopt:
6569         ret = do_getsockopt(arg1, arg2, arg3, arg4, arg5);
6570         break;
6571 #endif
6572 #ifdef TARGET_NR_listen
6573     case TARGET_NR_listen:
6574         ret = get_errno(listen(arg1, arg2));
6575         break;
6576 #endif
6577 #ifdef TARGET_NR_recv
6578     case TARGET_NR_recv:
6579         ret = do_recvfrom(arg1, arg2, arg3, arg4, 0, 0);
6580         break;
6581 #endif
6582 #ifdef TARGET_NR_recvfrom
6583     case TARGET_NR_recvfrom:
6584         ret = do_recvfrom(arg1, arg2, arg3, arg4, arg5, arg6);
6585         break;
6586 #endif
6587 #ifdef TARGET_NR_recvmsg
6588     case TARGET_NR_recvmsg:
6589         ret = do_sendrecvmsg(arg1, arg2, arg3, 0);
6590         break;
6591 #endif
6592 #ifdef TARGET_NR_send
6593     case TARGET_NR_send:
6594         ret = do_sendto(arg1, arg2, arg3, arg4, 0, 0);
6595         break;
6596 #endif
6597 #ifdef TARGET_NR_sendmsg
6598     case TARGET_NR_sendmsg:
6599         ret = do_sendrecvmsg(arg1, arg2, arg3, 1);
6600         break;
6601 #endif
6602 #ifdef TARGET_NR_sendto
6603     case TARGET_NR_sendto:
6604         ret = do_sendto(arg1, arg2, arg3, arg4, arg5, arg6);
6605         break;
6606 #endif
6607 #ifdef TARGET_NR_shutdown
6608     case TARGET_NR_shutdown:
6609         ret = get_errno(shutdown(arg1, arg2));
6610         break;
6611 #endif
6612 #ifdef TARGET_NR_socket
6613     case TARGET_NR_socket:
6614         ret = do_socket(arg1, arg2, arg3);
6615         break;
6616 #endif
6617 #ifdef TARGET_NR_socketpair
6618     case TARGET_NR_socketpair:
6619         ret = do_socketpair(arg1, arg2, arg3, arg4);
6620         break;
6621 #endif
6622 #ifdef TARGET_NR_setsockopt
6623     case TARGET_NR_setsockopt:
6624         ret = do_setsockopt(arg1, arg2, arg3, arg4, (socklen_t) arg5);
6625         break;
6626 #endif
6627 
6628     case TARGET_NR_syslog:
6629         if (!(p = lock_user_string(arg2)))
6630             goto efault;
6631         ret = get_errno(sys_syslog((int)arg1, p, (int)arg3));
6632         unlock_user(p, arg2, 0);
6633         break;
6634 
6635     case TARGET_NR_setitimer:
6636         {
6637             struct itimerval value, ovalue, *pvalue;
6638 
6639             if (arg2) {
6640                 pvalue = &value;
6641                 if (copy_from_user_timeval(&pvalue->it_interval, arg2)
6642                     || copy_from_user_timeval(&pvalue->it_value,
6643                                               arg2 + sizeof(struct target_timeval)))
6644                     goto efault;
6645             } else {
6646                 pvalue = NULL;
6647             }
6648             ret = get_errno(setitimer(arg1, pvalue, &ovalue));
6649             if (!is_error(ret) && arg3) {
6650                 if (copy_to_user_timeval(arg3,
6651                                          &ovalue.it_interval)
6652                     || copy_to_user_timeval(arg3 + sizeof(struct target_timeval),
6653                                             &ovalue.it_value))
6654                     goto efault;
6655             }
6656         }
6657         break;
6658     case TARGET_NR_getitimer:
6659         {
6660             struct itimerval value;
6661 
6662             ret = get_errno(getitimer(arg1, &value));
6663             if (!is_error(ret) && arg2) {
6664                 if (copy_to_user_timeval(arg2,
6665                                          &value.it_interval)
6666                     || copy_to_user_timeval(arg2 + sizeof(struct target_timeval),
6667                                             &value.it_value))
6668                     goto efault;
6669             }
6670         }
6671         break;
6672     case TARGET_NR_stat:
6673         if (!(p = lock_user_string(arg1)))
6674             goto efault;
6675         ret = get_errno(stat(path(p), &st));
6676         unlock_user(p, arg1, 0);
6677         goto do_stat;
6678     case TARGET_NR_lstat:
6679         if (!(p = lock_user_string(arg1)))
6680             goto efault;
6681         ret = get_errno(lstat(path(p), &st));
6682         unlock_user(p, arg1, 0);
6683         goto do_stat;
6684     case TARGET_NR_fstat:
6685         {
6686             ret = get_errno(fstat(arg1, &st));
6687         do_stat:
6688             if (!is_error(ret)) {
6689                 struct target_stat *target_st;
6690 
6691                 if (!lock_user_struct(VERIFY_WRITE, target_st, arg2, 0))
6692                     goto efault;
6693                 memset(target_st, 0, sizeof(*target_st));
6694                 __put_user(st.st_dev, &target_st->st_dev);
6695                 __put_user(st.st_ino, &target_st->st_ino);
6696                 __put_user(st.st_mode, &target_st->st_mode);
6697                 __put_user(st.st_uid, &target_st->st_uid);
6698                 __put_user(st.st_gid, &target_st->st_gid);
6699                 __put_user(st.st_nlink, &target_st->st_nlink);
6700                 __put_user(st.st_rdev, &target_st->st_rdev);
6701                 __put_user(st.st_size, &target_st->st_size);
6702                 __put_user(st.st_blksize, &target_st->st_blksize);
6703                 __put_user(st.st_blocks, &target_st->st_blocks);
6704                 __put_user(st.st_atime, &target_st->target_st_atime);
6705                 __put_user(st.st_mtime, &target_st->target_st_mtime);
6706                 __put_user(st.st_ctime, &target_st->target_st_ctime);
6707                 unlock_user_struct(target_st, arg2, 1);
6708             }
6709         }
6710         break;
6711 #ifdef TARGET_NR_olduname
6712     case TARGET_NR_olduname:
6713         goto unimplemented;
6714 #endif
6715 #ifdef TARGET_NR_iopl
6716     case TARGET_NR_iopl:
6717         goto unimplemented;
6718 #endif
6719     case TARGET_NR_vhangup:
6720         ret = get_errno(vhangup());
6721         break;
6722 #ifdef TARGET_NR_idle
6723     case TARGET_NR_idle:
6724         goto unimplemented;
6725 #endif
6726 #ifdef TARGET_NR_syscall
6727     case TARGET_NR_syscall:
6728         ret = do_syscall(cpu_env, arg1 & 0xffff, arg2, arg3, arg4, arg5,
6729                          arg6, arg7, arg8, 0);
6730         break;
6731 #endif
6732     case TARGET_NR_wait4:
6733         {
6734             int status;
6735             abi_long status_ptr = arg2;
6736             struct rusage rusage, *rusage_ptr;
6737             abi_ulong target_rusage = arg4;
6738             if (target_rusage)
6739                 rusage_ptr = &rusage;
6740             else
6741                 rusage_ptr = NULL;
6742             ret = get_errno(wait4(arg1, &status, arg3, rusage_ptr));
6743             if (!is_error(ret)) {
6744                 if (status_ptr && ret) {
6745                     status = host_to_target_waitstatus(status);
6746                     if (put_user_s32(status, status_ptr))
6747                         goto efault;
6748                 }
6749                 if (target_rusage)
6750                     host_to_target_rusage(target_rusage, &rusage);
6751             }
6752         }
6753         break;
6754 #ifdef TARGET_NR_swapoff
6755     case TARGET_NR_swapoff:
6756         if (!(p = lock_user_string(arg1)))
6757             goto efault;
6758         ret = get_errno(swapoff(p));
6759         unlock_user(p, arg1, 0);
6760         break;
6761 #endif
6762     case TARGET_NR_sysinfo:
6763         {
6764             struct target_sysinfo *target_value;
6765             struct sysinfo value;
6766             ret = get_errno(sysinfo(&value));
6767             if (!is_error(ret) && arg1)
6768             {
6769                 if (!lock_user_struct(VERIFY_WRITE, target_value, arg1, 0))
6770                     goto efault;
6771                 __put_user(value.uptime, &target_value->uptime);
6772                 __put_user(value.loads[0], &target_value->loads[0]);
6773                 __put_user(value.loads[1], &target_value->loads[1]);
6774                 __put_user(value.loads[2], &target_value->loads[2]);
6775                 __put_user(value.totalram, &target_value->totalram);
6776                 __put_user(value.freeram, &target_value->freeram);
6777                 __put_user(value.sharedram, &target_value->sharedram);
6778                 __put_user(value.bufferram, &target_value->bufferram);
6779                 __put_user(value.totalswap, &target_value->totalswap);
6780                 __put_user(value.freeswap, &target_value->freeswap);
6781                 __put_user(value.procs, &target_value->procs);
6782                 __put_user(value.totalhigh, &target_value->totalhigh);
6783                 __put_user(value.freehigh, &target_value->freehigh);
6784                 __put_user(value.mem_unit, &target_value->mem_unit);
6785                 unlock_user_struct(target_value, arg1, 1);
6786             }
6787         }
6788         break;
6789 #ifdef TARGET_NR_ipc
6790     case TARGET_NR_ipc:
6791 	ret = do_ipc(arg1, arg2, arg3, arg4, arg5, arg6);
6792 	break;
6793 #endif
6794 #ifdef TARGET_NR_semget
6795     case TARGET_NR_semget:
6796         ret = get_errno(semget(arg1, arg2, arg3));
6797         break;
6798 #endif
6799 #ifdef TARGET_NR_semop
6800     case TARGET_NR_semop:
6801         ret = do_semop(arg1, arg2, arg3);
6802         break;
6803 #endif
6804 #ifdef TARGET_NR_semctl
6805     case TARGET_NR_semctl:
6806         ret = do_semctl(arg1, arg2, arg3, (union target_semun)(abi_ulong)arg4);
6807         break;
6808 #endif
6809 #ifdef TARGET_NR_msgctl
6810     case TARGET_NR_msgctl:
6811         ret = do_msgctl(arg1, arg2, arg3);
6812         break;
6813 #endif
6814 #ifdef TARGET_NR_msgget
6815     case TARGET_NR_msgget:
6816         ret = get_errno(msgget(arg1, arg2));
6817         break;
6818 #endif
6819 #ifdef TARGET_NR_msgrcv
6820     case TARGET_NR_msgrcv:
6821         ret = do_msgrcv(arg1, arg2, arg3, arg4, arg5);
6822         break;
6823 #endif
6824 #ifdef TARGET_NR_msgsnd
6825     case TARGET_NR_msgsnd:
6826         ret = do_msgsnd(arg1, arg2, arg3, arg4);
6827         break;
6828 #endif
6829 #ifdef TARGET_NR_shmget
6830     case TARGET_NR_shmget:
6831         ret = get_errno(shmget(arg1, arg2, arg3));
6832         break;
6833 #endif
6834 #ifdef TARGET_NR_shmctl
6835     case TARGET_NR_shmctl:
6836         ret = do_shmctl(arg1, arg2, arg3);
6837         break;
6838 #endif
6839 #ifdef TARGET_NR_shmat
6840     case TARGET_NR_shmat:
6841         ret = do_shmat(arg1, arg2, arg3);
6842         break;
6843 #endif
6844 #ifdef TARGET_NR_shmdt
6845     case TARGET_NR_shmdt:
6846         ret = do_shmdt(arg1);
6847         break;
6848 #endif
6849     case TARGET_NR_fsync:
6850         ret = get_errno(fsync(arg1));
6851         break;
6852     case TARGET_NR_clone:
6853 #if defined(TARGET_SH4) || defined(TARGET_ALPHA)
6854         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg5, arg4));
6855 #elif defined(TARGET_CRIS)
6856         ret = get_errno(do_fork(cpu_env, arg2, arg1, arg3, arg4, arg5));
6857 #elif defined(TARGET_MICROBLAZE)
6858         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg4, arg6, arg5));
6859 #elif defined(TARGET_S390X)
6860         ret = get_errno(do_fork(cpu_env, arg2, arg1, arg3, arg5, arg4));
6861 #else
6862         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg4, arg5));
6863 #endif
6864         break;
6865 #ifdef __NR_exit_group
6866         /* new thread calls */
6867     case TARGET_NR_exit_group:
6868 #ifdef TARGET_GPROF
6869         _mcleanup();
6870 #endif
6871         gdb_exit(cpu_env, arg1);
6872         ret = get_errno(exit_group(arg1));
6873         break;
6874 #endif
6875     case TARGET_NR_setdomainname:
6876         if (!(p = lock_user_string(arg1)))
6877             goto efault;
6878         ret = get_errno(setdomainname(p, arg2));
6879         unlock_user(p, arg1, 0);
6880         break;
6881     case TARGET_NR_uname:
6882         /* no need to transcode because we use the linux syscall */
6883         {
6884             struct new_utsname * buf;
6885 
6886             if (!lock_user_struct(VERIFY_WRITE, buf, arg1, 0))
6887                 goto efault;
6888             ret = get_errno(sys_uname(buf));
6889             if (!is_error(ret)) {
6890                 /* Overrite the native machine name with whatever is being
6891                    emulated. */
6892                 strcpy (buf->machine, cpu_to_uname_machine(cpu_env));
6893                 /* Allow the user to override the reported release.  */
6894                 if (qemu_uname_release && *qemu_uname_release)
6895                   strcpy (buf->release, qemu_uname_release);
6896             }
6897             unlock_user_struct(buf, arg1, 1);
6898         }
6899         break;
6900 #ifdef TARGET_I386
6901     case TARGET_NR_modify_ldt:
6902         ret = do_modify_ldt(cpu_env, arg1, arg2, arg3);
6903         break;
6904 #if !defined(TARGET_X86_64)
6905     case TARGET_NR_vm86old:
6906         goto unimplemented;
6907     case TARGET_NR_vm86:
6908         ret = do_vm86(cpu_env, arg1, arg2);
6909         break;
6910 #endif
6911 #endif
6912     case TARGET_NR_adjtimex:
6913         goto unimplemented;
6914 #ifdef TARGET_NR_create_module
6915     case TARGET_NR_create_module:
6916 #endif
6917     case TARGET_NR_init_module:
6918     case TARGET_NR_delete_module:
6919 #ifdef TARGET_NR_get_kernel_syms
6920     case TARGET_NR_get_kernel_syms:
6921 #endif
6922         goto unimplemented;
6923     case TARGET_NR_quotactl:
6924         goto unimplemented;
6925     case TARGET_NR_getpgid:
6926         ret = get_errno(getpgid(arg1));
6927         break;
6928     case TARGET_NR_fchdir:
6929         ret = get_errno(fchdir(arg1));
6930         break;
6931 #ifdef TARGET_NR_bdflush /* not on x86_64 */
6932     case TARGET_NR_bdflush:
6933         goto unimplemented;
6934 #endif
6935 #ifdef TARGET_NR_sysfs
6936     case TARGET_NR_sysfs:
6937         goto unimplemented;
6938 #endif
6939     case TARGET_NR_personality:
6940         ret = get_errno(personality(arg1));
6941         break;
6942 #ifdef TARGET_NR_afs_syscall
6943     case TARGET_NR_afs_syscall:
6944         goto unimplemented;
6945 #endif
6946 #ifdef TARGET_NR__llseek /* Not on alpha */
6947     case TARGET_NR__llseek:
6948         {
6949             int64_t res;
6950 #if !defined(__NR_llseek)
6951             res = lseek(arg1, ((uint64_t)arg2 << 32) | arg3, arg5);
6952             if (res == -1) {
6953                 ret = get_errno(res);
6954             } else {
6955                 ret = 0;
6956             }
6957 #else
6958             ret = get_errno(_llseek(arg1, arg2, arg3, &res, arg5));
6959 #endif
6960             if ((ret == 0) && put_user_s64(res, arg4)) {
6961                 goto efault;
6962             }
6963         }
6964         break;
6965 #endif
6966     case TARGET_NR_getdents:
6967 #ifdef __NR_getdents
6968 #if TARGET_ABI_BITS == 32 && HOST_LONG_BITS == 64
6969         {
6970             struct target_dirent *target_dirp;
6971             struct linux_dirent *dirp;
6972             abi_long count = arg3;
6973 
6974 	    dirp = malloc(count);
6975 	    if (!dirp) {
6976                 ret = -TARGET_ENOMEM;
6977                 goto fail;
6978             }
6979 
6980             ret = get_errno(sys_getdents(arg1, dirp, count));
6981             if (!is_error(ret)) {
6982                 struct linux_dirent *de;
6983 		struct target_dirent *tde;
6984                 int len = ret;
6985                 int reclen, treclen;
6986 		int count1, tnamelen;
6987 
6988 		count1 = 0;
6989                 de = dirp;
6990                 if (!(target_dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
6991                     goto efault;
6992 		tde = target_dirp;
6993                 while (len > 0) {
6994                     reclen = de->d_reclen;
6995                     tnamelen = reclen - offsetof(struct linux_dirent, d_name);
6996                     assert(tnamelen >= 0);
6997                     treclen = tnamelen + offsetof(struct target_dirent, d_name);
6998                     assert(count1 + treclen <= count);
6999                     tde->d_reclen = tswap16(treclen);
7000                     tde->d_ino = tswapal(de->d_ino);
7001                     tde->d_off = tswapal(de->d_off);
7002                     memcpy(tde->d_name, de->d_name, tnamelen);
7003                     de = (struct linux_dirent *)((char *)de + reclen);
7004                     len -= reclen;
7005                     tde = (struct target_dirent *)((char *)tde + treclen);
7006 		    count1 += treclen;
7007                 }
7008 		ret = count1;
7009                 unlock_user(target_dirp, arg2, ret);
7010             }
7011 	    free(dirp);
7012         }
7013 #else
7014         {
7015             struct linux_dirent *dirp;
7016             abi_long count = arg3;
7017 
7018             if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
7019                 goto efault;
7020             ret = get_errno(sys_getdents(arg1, dirp, count));
7021             if (!is_error(ret)) {
7022                 struct linux_dirent *de;
7023                 int len = ret;
7024                 int reclen;
7025                 de = dirp;
7026                 while (len > 0) {
7027                     reclen = de->d_reclen;
7028                     if (reclen > len)
7029                         break;
7030                     de->d_reclen = tswap16(reclen);
7031                     tswapls(&de->d_ino);
7032                     tswapls(&de->d_off);
7033                     de = (struct linux_dirent *)((char *)de + reclen);
7034                     len -= reclen;
7035                 }
7036             }
7037             unlock_user(dirp, arg2, ret);
7038         }
7039 #endif
7040 #else
7041         /* Implement getdents in terms of getdents64 */
7042         {
7043             struct linux_dirent64 *dirp;
7044             abi_long count = arg3;
7045 
7046             dirp = lock_user(VERIFY_WRITE, arg2, count, 0);
7047             if (!dirp) {
7048                 goto efault;
7049             }
7050             ret = get_errno(sys_getdents64(arg1, dirp, count));
7051             if (!is_error(ret)) {
7052                 /* Convert the dirent64 structs to target dirent.  We do this
7053                  * in-place, since we can guarantee that a target_dirent is no
7054                  * larger than a dirent64; however this means we have to be
7055                  * careful to read everything before writing in the new format.
7056                  */
7057                 struct linux_dirent64 *de;
7058                 struct target_dirent *tde;
7059                 int len = ret;
7060                 int tlen = 0;
7061 
7062                 de = dirp;
7063                 tde = (struct target_dirent *)dirp;
7064                 while (len > 0) {
7065                     int namelen, treclen;
7066                     int reclen = de->d_reclen;
7067                     uint64_t ino = de->d_ino;
7068                     int64_t off = de->d_off;
7069                     uint8_t type = de->d_type;
7070 
7071                     namelen = strlen(de->d_name);
7072                     treclen = offsetof(struct target_dirent, d_name)
7073                         + namelen + 2;
7074                     treclen = QEMU_ALIGN_UP(treclen, sizeof(abi_long));
7075 
7076                     memmove(tde->d_name, de->d_name, namelen + 1);
7077                     tde->d_ino = tswapal(ino);
7078                     tde->d_off = tswapal(off);
7079                     tde->d_reclen = tswap16(treclen);
7080                     /* The target_dirent type is in what was formerly a padding
7081                      * byte at the end of the structure:
7082                      */
7083                     *(((char *)tde) + treclen - 1) = type;
7084 
7085                     de = (struct linux_dirent64 *)((char *)de + reclen);
7086                     tde = (struct target_dirent *)((char *)tde + treclen);
7087                     len -= reclen;
7088                     tlen += treclen;
7089                 }
7090                 ret = tlen;
7091             }
7092             unlock_user(dirp, arg2, ret);
7093         }
7094 #endif
7095         break;
7096 #if defined(TARGET_NR_getdents64) && defined(__NR_getdents64)
7097     case TARGET_NR_getdents64:
7098         {
7099             struct linux_dirent64 *dirp;
7100             abi_long count = arg3;
7101             if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
7102                 goto efault;
7103             ret = get_errno(sys_getdents64(arg1, dirp, count));
7104             if (!is_error(ret)) {
7105                 struct linux_dirent64 *de;
7106                 int len = ret;
7107                 int reclen;
7108                 de = dirp;
7109                 while (len > 0) {
7110                     reclen = de->d_reclen;
7111                     if (reclen > len)
7112                         break;
7113                     de->d_reclen = tswap16(reclen);
7114                     tswap64s((uint64_t *)&de->d_ino);
7115                     tswap64s((uint64_t *)&de->d_off);
7116                     de = (struct linux_dirent64 *)((char *)de + reclen);
7117                     len -= reclen;
7118                 }
7119             }
7120             unlock_user(dirp, arg2, ret);
7121         }
7122         break;
7123 #endif /* TARGET_NR_getdents64 */
7124 #if defined(TARGET_NR__newselect)
7125     case TARGET_NR__newselect:
7126         ret = do_select(arg1, arg2, arg3, arg4, arg5);
7127         break;
7128 #endif
7129 #if defined(TARGET_NR_poll) || defined(TARGET_NR_ppoll)
7130 # ifdef TARGET_NR_poll
7131     case TARGET_NR_poll:
7132 # endif
7133 # ifdef TARGET_NR_ppoll
7134     case TARGET_NR_ppoll:
7135 # endif
7136         {
7137             struct target_pollfd *target_pfd;
7138             unsigned int nfds = arg2;
7139             int timeout = arg3;
7140             struct pollfd *pfd;
7141             unsigned int i;
7142 
7143             target_pfd = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_pollfd) * nfds, 1);
7144             if (!target_pfd)
7145                 goto efault;
7146 
7147             pfd = alloca(sizeof(struct pollfd) * nfds);
7148             for(i = 0; i < nfds; i++) {
7149                 pfd[i].fd = tswap32(target_pfd[i].fd);
7150                 pfd[i].events = tswap16(target_pfd[i].events);
7151             }
7152 
7153 # ifdef TARGET_NR_ppoll
7154             if (num == TARGET_NR_ppoll) {
7155                 struct timespec _timeout_ts, *timeout_ts = &_timeout_ts;
7156                 target_sigset_t *target_set;
7157                 sigset_t _set, *set = &_set;
7158 
7159                 if (arg3) {
7160                     if (target_to_host_timespec(timeout_ts, arg3)) {
7161                         unlock_user(target_pfd, arg1, 0);
7162                         goto efault;
7163                     }
7164                 } else {
7165                     timeout_ts = NULL;
7166                 }
7167 
7168                 if (arg4) {
7169                     target_set = lock_user(VERIFY_READ, arg4, sizeof(target_sigset_t), 1);
7170                     if (!target_set) {
7171                         unlock_user(target_pfd, arg1, 0);
7172                         goto efault;
7173                     }
7174                     target_to_host_sigset(set, target_set);
7175                 } else {
7176                     set = NULL;
7177                 }
7178 
7179                 ret = get_errno(sys_ppoll(pfd, nfds, timeout_ts, set, _NSIG/8));
7180 
7181                 if (!is_error(ret) && arg3) {
7182                     host_to_target_timespec(arg3, timeout_ts);
7183                 }
7184                 if (arg4) {
7185                     unlock_user(target_set, arg4, 0);
7186                 }
7187             } else
7188 # endif
7189                 ret = get_errno(poll(pfd, nfds, timeout));
7190 
7191             if (!is_error(ret)) {
7192                 for(i = 0; i < nfds; i++) {
7193                     target_pfd[i].revents = tswap16(pfd[i].revents);
7194                 }
7195             }
7196             unlock_user(target_pfd, arg1, sizeof(struct target_pollfd) * nfds);
7197         }
7198         break;
7199 #endif
7200     case TARGET_NR_flock:
7201         /* NOTE: the flock constant seems to be the same for every
7202            Linux platform */
7203         ret = get_errno(flock(arg1, arg2));
7204         break;
7205     case TARGET_NR_readv:
7206         {
7207             struct iovec *vec = lock_iovec(VERIFY_WRITE, arg2, arg3, 0);
7208             if (vec != NULL) {
7209                 ret = get_errno(readv(arg1, vec, arg3));
7210                 unlock_iovec(vec, arg2, arg3, 1);
7211             } else {
7212                 ret = -host_to_target_errno(errno);
7213             }
7214         }
7215         break;
7216     case TARGET_NR_writev:
7217         {
7218             struct iovec *vec = lock_iovec(VERIFY_READ, arg2, arg3, 1);
7219             if (vec != NULL) {
7220                 ret = get_errno(writev(arg1, vec, arg3));
7221                 unlock_iovec(vec, arg2, arg3, 0);
7222             } else {
7223                 ret = -host_to_target_errno(errno);
7224             }
7225         }
7226         break;
7227     case TARGET_NR_getsid:
7228         ret = get_errno(getsid(arg1));
7229         break;
7230 #if defined(TARGET_NR_fdatasync) /* Not on alpha (osf_datasync ?) */
7231     case TARGET_NR_fdatasync:
7232         ret = get_errno(fdatasync(arg1));
7233         break;
7234 #endif
7235     case TARGET_NR__sysctl:
7236         /* We don't implement this, but ENOTDIR is always a safe
7237            return value. */
7238         ret = -TARGET_ENOTDIR;
7239         break;
7240     case TARGET_NR_sched_getaffinity:
7241         {
7242             unsigned int mask_size;
7243             unsigned long *mask;
7244 
7245             /*
7246              * sched_getaffinity needs multiples of ulong, so need to take
7247              * care of mismatches between target ulong and host ulong sizes.
7248              */
7249             if (arg2 & (sizeof(abi_ulong) - 1)) {
7250                 ret = -TARGET_EINVAL;
7251                 break;
7252             }
7253             mask_size = (arg2 + (sizeof(*mask) - 1)) & ~(sizeof(*mask) - 1);
7254 
7255             mask = alloca(mask_size);
7256             ret = get_errno(sys_sched_getaffinity(arg1, mask_size, mask));
7257 
7258             if (!is_error(ret)) {
7259                 if (copy_to_user(arg3, mask, ret)) {
7260                     goto efault;
7261                 }
7262             }
7263         }
7264         break;
7265     case TARGET_NR_sched_setaffinity:
7266         {
7267             unsigned int mask_size;
7268             unsigned long *mask;
7269 
7270             /*
7271              * sched_setaffinity needs multiples of ulong, so need to take
7272              * care of mismatches between target ulong and host ulong sizes.
7273              */
7274             if (arg2 & (sizeof(abi_ulong) - 1)) {
7275                 ret = -TARGET_EINVAL;
7276                 break;
7277             }
7278             mask_size = (arg2 + (sizeof(*mask) - 1)) & ~(sizeof(*mask) - 1);
7279 
7280             mask = alloca(mask_size);
7281             if (!lock_user_struct(VERIFY_READ, p, arg3, 1)) {
7282                 goto efault;
7283             }
7284             memcpy(mask, p, arg2);
7285             unlock_user_struct(p, arg2, 0);
7286 
7287             ret = get_errno(sys_sched_setaffinity(arg1, mask_size, mask));
7288         }
7289         break;
7290     case TARGET_NR_sched_setparam:
7291         {
7292             struct sched_param *target_schp;
7293             struct sched_param schp;
7294 
7295             if (!lock_user_struct(VERIFY_READ, target_schp, arg2, 1))
7296                 goto efault;
7297             schp.sched_priority = tswap32(target_schp->sched_priority);
7298             unlock_user_struct(target_schp, arg2, 0);
7299             ret = get_errno(sched_setparam(arg1, &schp));
7300         }
7301         break;
7302     case TARGET_NR_sched_getparam:
7303         {
7304             struct sched_param *target_schp;
7305             struct sched_param schp;
7306             ret = get_errno(sched_getparam(arg1, &schp));
7307             if (!is_error(ret)) {
7308                 if (!lock_user_struct(VERIFY_WRITE, target_schp, arg2, 0))
7309                     goto efault;
7310                 target_schp->sched_priority = tswap32(schp.sched_priority);
7311                 unlock_user_struct(target_schp, arg2, 1);
7312             }
7313         }
7314         break;
7315     case TARGET_NR_sched_setscheduler:
7316         {
7317             struct sched_param *target_schp;
7318             struct sched_param schp;
7319             if (!lock_user_struct(VERIFY_READ, target_schp, arg3, 1))
7320                 goto efault;
7321             schp.sched_priority = tswap32(target_schp->sched_priority);
7322             unlock_user_struct(target_schp, arg3, 0);
7323             ret = get_errno(sched_setscheduler(arg1, arg2, &schp));
7324         }
7325         break;
7326     case TARGET_NR_sched_getscheduler:
7327         ret = get_errno(sched_getscheduler(arg1));
7328         break;
7329     case TARGET_NR_sched_yield:
7330         ret = get_errno(sched_yield());
7331         break;
7332     case TARGET_NR_sched_get_priority_max:
7333         ret = get_errno(sched_get_priority_max(arg1));
7334         break;
7335     case TARGET_NR_sched_get_priority_min:
7336         ret = get_errno(sched_get_priority_min(arg1));
7337         break;
7338     case TARGET_NR_sched_rr_get_interval:
7339         {
7340             struct timespec ts;
7341             ret = get_errno(sched_rr_get_interval(arg1, &ts));
7342             if (!is_error(ret)) {
7343                 host_to_target_timespec(arg2, &ts);
7344             }
7345         }
7346         break;
7347     case TARGET_NR_nanosleep:
7348         {
7349             struct timespec req, rem;
7350             target_to_host_timespec(&req, arg1);
7351             ret = get_errno(nanosleep(&req, &rem));
7352             if (is_error(ret) && arg2) {
7353                 host_to_target_timespec(arg2, &rem);
7354             }
7355         }
7356         break;
7357 #ifdef TARGET_NR_query_module
7358     case TARGET_NR_query_module:
7359         goto unimplemented;
7360 #endif
7361 #ifdef TARGET_NR_nfsservctl
7362     case TARGET_NR_nfsservctl:
7363         goto unimplemented;
7364 #endif
7365     case TARGET_NR_prctl:
7366         switch (arg1) {
7367         case PR_GET_PDEATHSIG:
7368         {
7369             int deathsig;
7370             ret = get_errno(prctl(arg1, &deathsig, arg3, arg4, arg5));
7371             if (!is_error(ret) && arg2
7372                 && put_user_ual(deathsig, arg2)) {
7373                 goto efault;
7374             }
7375             break;
7376         }
7377 #ifdef PR_GET_NAME
7378         case PR_GET_NAME:
7379         {
7380             void *name = lock_user(VERIFY_WRITE, arg2, 16, 1);
7381             if (!name) {
7382                 goto efault;
7383             }
7384             ret = get_errno(prctl(arg1, (unsigned long)name,
7385                                   arg3, arg4, arg5));
7386             unlock_user(name, arg2, 16);
7387             break;
7388         }
7389         case PR_SET_NAME:
7390         {
7391             void *name = lock_user(VERIFY_READ, arg2, 16, 1);
7392             if (!name) {
7393                 goto efault;
7394             }
7395             ret = get_errno(prctl(arg1, (unsigned long)name,
7396                                   arg3, arg4, arg5));
7397             unlock_user(name, arg2, 0);
7398             break;
7399         }
7400 #endif
7401         default:
7402             /* Most prctl options have no pointer arguments */
7403             ret = get_errno(prctl(arg1, arg2, arg3, arg4, arg5));
7404             break;
7405         }
7406         break;
7407 #ifdef TARGET_NR_arch_prctl
7408     case TARGET_NR_arch_prctl:
7409 #if defined(TARGET_I386) && !defined(TARGET_ABI32)
7410         ret = do_arch_prctl(cpu_env, arg1, arg2);
7411         break;
7412 #else
7413         goto unimplemented;
7414 #endif
7415 #endif
7416 #ifdef TARGET_NR_pread64
7417     case TARGET_NR_pread64:
7418         if (regpairs_aligned(cpu_env)) {
7419             arg4 = arg5;
7420             arg5 = arg6;
7421         }
7422         if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
7423             goto efault;
7424         ret = get_errno(pread64(arg1, p, arg3, target_offset64(arg4, arg5)));
7425         unlock_user(p, arg2, ret);
7426         break;
7427     case TARGET_NR_pwrite64:
7428         if (regpairs_aligned(cpu_env)) {
7429             arg4 = arg5;
7430             arg5 = arg6;
7431         }
7432         if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
7433             goto efault;
7434         ret = get_errno(pwrite64(arg1, p, arg3, target_offset64(arg4, arg5)));
7435         unlock_user(p, arg2, 0);
7436         break;
7437 #endif
7438     case TARGET_NR_getcwd:
7439         if (!(p = lock_user(VERIFY_WRITE, arg1, arg2, 0)))
7440             goto efault;
7441         ret = get_errno(sys_getcwd1(p, arg2));
7442         unlock_user(p, arg1, ret);
7443         break;
7444     case TARGET_NR_capget:
7445         goto unimplemented;
7446     case TARGET_NR_capset:
7447         goto unimplemented;
7448     case TARGET_NR_sigaltstack:
7449 #if defined(TARGET_I386) || defined(TARGET_ARM) || defined(TARGET_MIPS) || \
7450     defined(TARGET_SPARC) || defined(TARGET_PPC) || defined(TARGET_ALPHA) || \
7451     defined(TARGET_M68K) || defined(TARGET_S390X) || defined(TARGET_OPENRISC)
7452         ret = do_sigaltstack(arg1, arg2, get_sp_from_cpustate((CPUArchState *)cpu_env));
7453         break;
7454 #else
7455         goto unimplemented;
7456 #endif
7457 
7458 #ifdef CONFIG_SENDFILE
7459     case TARGET_NR_sendfile:
7460     {
7461         off_t *offp = NULL;
7462         off_t off;
7463         if (arg3) {
7464             ret = get_user_sal(off, arg3);
7465             if (is_error(ret)) {
7466                 break;
7467             }
7468             offp = &off;
7469         }
7470         ret = get_errno(sendfile(arg1, arg2, offp, arg4));
7471         if (!is_error(ret) && arg3) {
7472             abi_long ret2 = put_user_sal(off, arg3);
7473             if (is_error(ret2)) {
7474                 ret = ret2;
7475             }
7476         }
7477         break;
7478     }
7479 #ifdef TARGET_NR_sendfile64
7480     case TARGET_NR_sendfile64:
7481     {
7482         off_t *offp = NULL;
7483         off_t off;
7484         if (arg3) {
7485             ret = get_user_s64(off, arg3);
7486             if (is_error(ret)) {
7487                 break;
7488             }
7489             offp = &off;
7490         }
7491         ret = get_errno(sendfile(arg1, arg2, offp, arg4));
7492         if (!is_error(ret) && arg3) {
7493             abi_long ret2 = put_user_s64(off, arg3);
7494             if (is_error(ret2)) {
7495                 ret = ret2;
7496             }
7497         }
7498         break;
7499     }
7500 #endif
7501 #else
7502     case TARGET_NR_sendfile:
7503 #ifdef TARGET_NR_sendfile64
7504     case TARGET_NR_sendfile64:
7505 #endif
7506         goto unimplemented;
7507 #endif
7508 
7509 #ifdef TARGET_NR_getpmsg
7510     case TARGET_NR_getpmsg:
7511         goto unimplemented;
7512 #endif
7513 #ifdef TARGET_NR_putpmsg
7514     case TARGET_NR_putpmsg:
7515         goto unimplemented;
7516 #endif
7517 #ifdef TARGET_NR_vfork
7518     case TARGET_NR_vfork:
7519         ret = get_errno(do_fork(cpu_env, CLONE_VFORK | CLONE_VM | SIGCHLD,
7520                         0, 0, 0, 0));
7521         break;
7522 #endif
7523 #ifdef TARGET_NR_ugetrlimit
7524     case TARGET_NR_ugetrlimit:
7525     {
7526 	struct rlimit rlim;
7527 	int resource = target_to_host_resource(arg1);
7528 	ret = get_errno(getrlimit(resource, &rlim));
7529 	if (!is_error(ret)) {
7530 	    struct target_rlimit *target_rlim;
7531             if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
7532                 goto efault;
7533 	    target_rlim->rlim_cur = host_to_target_rlim(rlim.rlim_cur);
7534 	    target_rlim->rlim_max = host_to_target_rlim(rlim.rlim_max);
7535             unlock_user_struct(target_rlim, arg2, 1);
7536 	}
7537 	break;
7538     }
7539 #endif
7540 #ifdef TARGET_NR_truncate64
7541     case TARGET_NR_truncate64:
7542         if (!(p = lock_user_string(arg1)))
7543             goto efault;
7544 	ret = target_truncate64(cpu_env, p, arg2, arg3, arg4);
7545         unlock_user(p, arg1, 0);
7546 	break;
7547 #endif
7548 #ifdef TARGET_NR_ftruncate64
7549     case TARGET_NR_ftruncate64:
7550 	ret = target_ftruncate64(cpu_env, arg1, arg2, arg3, arg4);
7551 	break;
7552 #endif
7553 #ifdef TARGET_NR_stat64
7554     case TARGET_NR_stat64:
7555         if (!(p = lock_user_string(arg1)))
7556             goto efault;
7557         ret = get_errno(stat(path(p), &st));
7558         unlock_user(p, arg1, 0);
7559         if (!is_error(ret))
7560             ret = host_to_target_stat64(cpu_env, arg2, &st);
7561         break;
7562 #endif
7563 #ifdef TARGET_NR_lstat64
7564     case TARGET_NR_lstat64:
7565         if (!(p = lock_user_string(arg1)))
7566             goto efault;
7567         ret = get_errno(lstat(path(p), &st));
7568         unlock_user(p, arg1, 0);
7569         if (!is_error(ret))
7570             ret = host_to_target_stat64(cpu_env, arg2, &st);
7571         break;
7572 #endif
7573 #ifdef TARGET_NR_fstat64
7574     case TARGET_NR_fstat64:
7575         ret = get_errno(fstat(arg1, &st));
7576         if (!is_error(ret))
7577             ret = host_to_target_stat64(cpu_env, arg2, &st);
7578         break;
7579 #endif
7580 #if (defined(TARGET_NR_fstatat64) || defined(TARGET_NR_newfstatat))
7581 #ifdef TARGET_NR_fstatat64
7582     case TARGET_NR_fstatat64:
7583 #endif
7584 #ifdef TARGET_NR_newfstatat
7585     case TARGET_NR_newfstatat:
7586 #endif
7587         if (!(p = lock_user_string(arg2)))
7588             goto efault;
7589         ret = get_errno(fstatat(arg1, path(p), &st, arg4));
7590         if (!is_error(ret))
7591             ret = host_to_target_stat64(cpu_env, arg3, &st);
7592         break;
7593 #endif
7594     case TARGET_NR_lchown:
7595         if (!(p = lock_user_string(arg1)))
7596             goto efault;
7597         ret = get_errno(lchown(p, low2highuid(arg2), low2highgid(arg3)));
7598         unlock_user(p, arg1, 0);
7599         break;
7600 #ifdef TARGET_NR_getuid
7601     case TARGET_NR_getuid:
7602         ret = get_errno(high2lowuid(getuid()));
7603         break;
7604 #endif
7605 #ifdef TARGET_NR_getgid
7606     case TARGET_NR_getgid:
7607         ret = get_errno(high2lowgid(getgid()));
7608         break;
7609 #endif
7610 #ifdef TARGET_NR_geteuid
7611     case TARGET_NR_geteuid:
7612         ret = get_errno(high2lowuid(geteuid()));
7613         break;
7614 #endif
7615 #ifdef TARGET_NR_getegid
7616     case TARGET_NR_getegid:
7617         ret = get_errno(high2lowgid(getegid()));
7618         break;
7619 #endif
7620     case TARGET_NR_setreuid:
7621         ret = get_errno(setreuid(low2highuid(arg1), low2highuid(arg2)));
7622         break;
7623     case TARGET_NR_setregid:
7624         ret = get_errno(setregid(low2highgid(arg1), low2highgid(arg2)));
7625         break;
7626     case TARGET_NR_getgroups:
7627         {
7628             int gidsetsize = arg1;
7629             target_id *target_grouplist;
7630             gid_t *grouplist;
7631             int i;
7632 
7633             grouplist = alloca(gidsetsize * sizeof(gid_t));
7634             ret = get_errno(getgroups(gidsetsize, grouplist));
7635             if (gidsetsize == 0)
7636                 break;
7637             if (!is_error(ret)) {
7638                 target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * sizeof(target_id), 0);
7639                 if (!target_grouplist)
7640                     goto efault;
7641                 for(i = 0;i < ret; i++)
7642                     target_grouplist[i] = tswapid(high2lowgid(grouplist[i]));
7643                 unlock_user(target_grouplist, arg2, gidsetsize * sizeof(target_id));
7644             }
7645         }
7646         break;
7647     case TARGET_NR_setgroups:
7648         {
7649             int gidsetsize = arg1;
7650             target_id *target_grouplist;
7651             gid_t *grouplist = NULL;
7652             int i;
7653             if (gidsetsize) {
7654                 grouplist = alloca(gidsetsize * sizeof(gid_t));
7655                 target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * sizeof(target_id), 1);
7656                 if (!target_grouplist) {
7657                     ret = -TARGET_EFAULT;
7658                     goto fail;
7659                 }
7660                 for (i = 0; i < gidsetsize; i++) {
7661                     grouplist[i] = low2highgid(tswapid(target_grouplist[i]));
7662                 }
7663                 unlock_user(target_grouplist, arg2, 0);
7664             }
7665             ret = get_errno(setgroups(gidsetsize, grouplist));
7666         }
7667         break;
7668     case TARGET_NR_fchown:
7669         ret = get_errno(fchown(arg1, low2highuid(arg2), low2highgid(arg3)));
7670         break;
7671 #if defined(TARGET_NR_fchownat)
7672     case TARGET_NR_fchownat:
7673         if (!(p = lock_user_string(arg2)))
7674             goto efault;
7675         ret = get_errno(fchownat(arg1, p, low2highuid(arg3),
7676                                  low2highgid(arg4), arg5));
7677         unlock_user(p, arg2, 0);
7678         break;
7679 #endif
7680 #ifdef TARGET_NR_setresuid
7681     case TARGET_NR_setresuid:
7682         ret = get_errno(setresuid(low2highuid(arg1),
7683                                   low2highuid(arg2),
7684                                   low2highuid(arg3)));
7685         break;
7686 #endif
7687 #ifdef TARGET_NR_getresuid
7688     case TARGET_NR_getresuid:
7689         {
7690             uid_t ruid, euid, suid;
7691             ret = get_errno(getresuid(&ruid, &euid, &suid));
7692             if (!is_error(ret)) {
7693                 if (put_user_u16(high2lowuid(ruid), arg1)
7694                     || put_user_u16(high2lowuid(euid), arg2)
7695                     || put_user_u16(high2lowuid(suid), arg3))
7696                     goto efault;
7697             }
7698         }
7699         break;
7700 #endif
7701 #ifdef TARGET_NR_getresgid
7702     case TARGET_NR_setresgid:
7703         ret = get_errno(setresgid(low2highgid(arg1),
7704                                   low2highgid(arg2),
7705                                   low2highgid(arg3)));
7706         break;
7707 #endif
7708 #ifdef TARGET_NR_getresgid
7709     case TARGET_NR_getresgid:
7710         {
7711             gid_t rgid, egid, sgid;
7712             ret = get_errno(getresgid(&rgid, &egid, &sgid));
7713             if (!is_error(ret)) {
7714                 if (put_user_u16(high2lowgid(rgid), arg1)
7715                     || put_user_u16(high2lowgid(egid), arg2)
7716                     || put_user_u16(high2lowgid(sgid), arg3))
7717                     goto efault;
7718             }
7719         }
7720         break;
7721 #endif
7722     case TARGET_NR_chown:
7723         if (!(p = lock_user_string(arg1)))
7724             goto efault;
7725         ret = get_errno(chown(p, low2highuid(arg2), low2highgid(arg3)));
7726         unlock_user(p, arg1, 0);
7727         break;
7728     case TARGET_NR_setuid:
7729         ret = get_errno(setuid(low2highuid(arg1)));
7730         break;
7731     case TARGET_NR_setgid:
7732         ret = get_errno(setgid(low2highgid(arg1)));
7733         break;
7734     case TARGET_NR_setfsuid:
7735         ret = get_errno(setfsuid(arg1));
7736         break;
7737     case TARGET_NR_setfsgid:
7738         ret = get_errno(setfsgid(arg1));
7739         break;
7740 
7741 #ifdef TARGET_NR_lchown32
7742     case TARGET_NR_lchown32:
7743         if (!(p = lock_user_string(arg1)))
7744             goto efault;
7745         ret = get_errno(lchown(p, arg2, arg3));
7746         unlock_user(p, arg1, 0);
7747         break;
7748 #endif
7749 #ifdef TARGET_NR_getuid32
7750     case TARGET_NR_getuid32:
7751         ret = get_errno(getuid());
7752         break;
7753 #endif
7754 
7755 #if defined(TARGET_NR_getxuid) && defined(TARGET_ALPHA)
7756    /* Alpha specific */
7757     case TARGET_NR_getxuid:
7758          {
7759             uid_t euid;
7760             euid=geteuid();
7761             ((CPUAlphaState *)cpu_env)->ir[IR_A4]=euid;
7762          }
7763         ret = get_errno(getuid());
7764         break;
7765 #endif
7766 #if defined(TARGET_NR_getxgid) && defined(TARGET_ALPHA)
7767    /* Alpha specific */
7768     case TARGET_NR_getxgid:
7769          {
7770             uid_t egid;
7771             egid=getegid();
7772             ((CPUAlphaState *)cpu_env)->ir[IR_A4]=egid;
7773          }
7774         ret = get_errno(getgid());
7775         break;
7776 #endif
7777 #if defined(TARGET_NR_osf_getsysinfo) && defined(TARGET_ALPHA)
7778     /* Alpha specific */
7779     case TARGET_NR_osf_getsysinfo:
7780         ret = -TARGET_EOPNOTSUPP;
7781         switch (arg1) {
7782           case TARGET_GSI_IEEE_FP_CONTROL:
7783             {
7784                 uint64_t swcr, fpcr = cpu_alpha_load_fpcr (cpu_env);
7785 
7786                 /* Copied from linux ieee_fpcr_to_swcr.  */
7787                 swcr = (fpcr >> 35) & SWCR_STATUS_MASK;
7788                 swcr |= (fpcr >> 36) & SWCR_MAP_DMZ;
7789                 swcr |= (~fpcr >> 48) & (SWCR_TRAP_ENABLE_INV
7790                                         | SWCR_TRAP_ENABLE_DZE
7791                                         | SWCR_TRAP_ENABLE_OVF);
7792                 swcr |= (~fpcr >> 57) & (SWCR_TRAP_ENABLE_UNF
7793                                         | SWCR_TRAP_ENABLE_INE);
7794                 swcr |= (fpcr >> 47) & SWCR_MAP_UMZ;
7795                 swcr |= (~fpcr >> 41) & SWCR_TRAP_ENABLE_DNO;
7796 
7797                 if (put_user_u64 (swcr, arg2))
7798                         goto efault;
7799                 ret = 0;
7800             }
7801             break;
7802 
7803           /* case GSI_IEEE_STATE_AT_SIGNAL:
7804              -- Not implemented in linux kernel.
7805              case GSI_UACPROC:
7806              -- Retrieves current unaligned access state; not much used.
7807              case GSI_PROC_TYPE:
7808              -- Retrieves implver information; surely not used.
7809              case GSI_GET_HWRPB:
7810              -- Grabs a copy of the HWRPB; surely not used.
7811           */
7812         }
7813         break;
7814 #endif
7815 #if defined(TARGET_NR_osf_setsysinfo) && defined(TARGET_ALPHA)
7816     /* Alpha specific */
7817     case TARGET_NR_osf_setsysinfo:
7818         ret = -TARGET_EOPNOTSUPP;
7819         switch (arg1) {
7820           case TARGET_SSI_IEEE_FP_CONTROL:
7821             {
7822                 uint64_t swcr, fpcr, orig_fpcr;
7823 
7824                 if (get_user_u64 (swcr, arg2)) {
7825                     goto efault;
7826                 }
7827                 orig_fpcr = cpu_alpha_load_fpcr(cpu_env);
7828                 fpcr = orig_fpcr & FPCR_DYN_MASK;
7829 
7830                 /* Copied from linux ieee_swcr_to_fpcr.  */
7831                 fpcr |= (swcr & SWCR_STATUS_MASK) << 35;
7832                 fpcr |= (swcr & SWCR_MAP_DMZ) << 36;
7833                 fpcr |= (~swcr & (SWCR_TRAP_ENABLE_INV
7834                                   | SWCR_TRAP_ENABLE_DZE
7835                                   | SWCR_TRAP_ENABLE_OVF)) << 48;
7836                 fpcr |= (~swcr & (SWCR_TRAP_ENABLE_UNF
7837                                   | SWCR_TRAP_ENABLE_INE)) << 57;
7838                 fpcr |= (swcr & SWCR_MAP_UMZ ? FPCR_UNDZ | FPCR_UNFD : 0);
7839                 fpcr |= (~swcr & SWCR_TRAP_ENABLE_DNO) << 41;
7840 
7841                 cpu_alpha_store_fpcr(cpu_env, fpcr);
7842                 ret = 0;
7843             }
7844             break;
7845 
7846           case TARGET_SSI_IEEE_RAISE_EXCEPTION:
7847             {
7848                 uint64_t exc, fpcr, orig_fpcr;
7849                 int si_code;
7850 
7851                 if (get_user_u64(exc, arg2)) {
7852                     goto efault;
7853                 }
7854 
7855                 orig_fpcr = cpu_alpha_load_fpcr(cpu_env);
7856 
7857                 /* We only add to the exception status here.  */
7858                 fpcr = orig_fpcr | ((exc & SWCR_STATUS_MASK) << 35);
7859 
7860                 cpu_alpha_store_fpcr(cpu_env, fpcr);
7861                 ret = 0;
7862 
7863                 /* Old exceptions are not signaled.  */
7864                 fpcr &= ~(orig_fpcr & FPCR_STATUS_MASK);
7865 
7866                 /* If any exceptions set by this call,
7867                    and are unmasked, send a signal.  */
7868                 si_code = 0;
7869                 if ((fpcr & (FPCR_INE | FPCR_INED)) == FPCR_INE) {
7870                     si_code = TARGET_FPE_FLTRES;
7871                 }
7872                 if ((fpcr & (FPCR_UNF | FPCR_UNFD)) == FPCR_UNF) {
7873                     si_code = TARGET_FPE_FLTUND;
7874                 }
7875                 if ((fpcr & (FPCR_OVF | FPCR_OVFD)) == FPCR_OVF) {
7876                     si_code = TARGET_FPE_FLTOVF;
7877                 }
7878                 if ((fpcr & (FPCR_DZE | FPCR_DZED)) == FPCR_DZE) {
7879                     si_code = TARGET_FPE_FLTDIV;
7880                 }
7881                 if ((fpcr & (FPCR_INV | FPCR_INVD)) == FPCR_INV) {
7882                     si_code = TARGET_FPE_FLTINV;
7883                 }
7884                 if (si_code != 0) {
7885                     target_siginfo_t info;
7886                     info.si_signo = SIGFPE;
7887                     info.si_errno = 0;
7888                     info.si_code = si_code;
7889                     info._sifields._sigfault._addr
7890                         = ((CPUArchState *)cpu_env)->pc;
7891                     queue_signal((CPUArchState *)cpu_env, info.si_signo, &info);
7892                 }
7893             }
7894             break;
7895 
7896           /* case SSI_NVPAIRS:
7897              -- Used with SSIN_UACPROC to enable unaligned accesses.
7898              case SSI_IEEE_STATE_AT_SIGNAL:
7899              case SSI_IEEE_IGNORE_STATE_AT_SIGNAL:
7900              -- Not implemented in linux kernel
7901           */
7902         }
7903         break;
7904 #endif
7905 #ifdef TARGET_NR_osf_sigprocmask
7906     /* Alpha specific.  */
7907     case TARGET_NR_osf_sigprocmask:
7908         {
7909             abi_ulong mask;
7910             int how;
7911             sigset_t set, oldset;
7912 
7913             switch(arg1) {
7914             case TARGET_SIG_BLOCK:
7915                 how = SIG_BLOCK;
7916                 break;
7917             case TARGET_SIG_UNBLOCK:
7918                 how = SIG_UNBLOCK;
7919                 break;
7920             case TARGET_SIG_SETMASK:
7921                 how = SIG_SETMASK;
7922                 break;
7923             default:
7924                 ret = -TARGET_EINVAL;
7925                 goto fail;
7926             }
7927             mask = arg2;
7928             target_to_host_old_sigset(&set, &mask);
7929             sigprocmask(how, &set, &oldset);
7930             host_to_target_old_sigset(&mask, &oldset);
7931             ret = mask;
7932         }
7933         break;
7934 #endif
7935 
7936 #ifdef TARGET_NR_getgid32
7937     case TARGET_NR_getgid32:
7938         ret = get_errno(getgid());
7939         break;
7940 #endif
7941 #ifdef TARGET_NR_geteuid32
7942     case TARGET_NR_geteuid32:
7943         ret = get_errno(geteuid());
7944         break;
7945 #endif
7946 #ifdef TARGET_NR_getegid32
7947     case TARGET_NR_getegid32:
7948         ret = get_errno(getegid());
7949         break;
7950 #endif
7951 #ifdef TARGET_NR_setreuid32
7952     case TARGET_NR_setreuid32:
7953         ret = get_errno(setreuid(arg1, arg2));
7954         break;
7955 #endif
7956 #ifdef TARGET_NR_setregid32
7957     case TARGET_NR_setregid32:
7958         ret = get_errno(setregid(arg1, arg2));
7959         break;
7960 #endif
7961 #ifdef TARGET_NR_getgroups32
7962     case TARGET_NR_getgroups32:
7963         {
7964             int gidsetsize = arg1;
7965             uint32_t *target_grouplist;
7966             gid_t *grouplist;
7967             int i;
7968 
7969             grouplist = alloca(gidsetsize * sizeof(gid_t));
7970             ret = get_errno(getgroups(gidsetsize, grouplist));
7971             if (gidsetsize == 0)
7972                 break;
7973             if (!is_error(ret)) {
7974                 target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * 4, 0);
7975                 if (!target_grouplist) {
7976                     ret = -TARGET_EFAULT;
7977                     goto fail;
7978                 }
7979                 for(i = 0;i < ret; i++)
7980                     target_grouplist[i] = tswap32(grouplist[i]);
7981                 unlock_user(target_grouplist, arg2, gidsetsize * 4);
7982             }
7983         }
7984         break;
7985 #endif
7986 #ifdef TARGET_NR_setgroups32
7987     case TARGET_NR_setgroups32:
7988         {
7989             int gidsetsize = arg1;
7990             uint32_t *target_grouplist;
7991             gid_t *grouplist;
7992             int i;
7993 
7994             grouplist = alloca(gidsetsize * sizeof(gid_t));
7995             target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * 4, 1);
7996             if (!target_grouplist) {
7997                 ret = -TARGET_EFAULT;
7998                 goto fail;
7999             }
8000             for(i = 0;i < gidsetsize; i++)
8001                 grouplist[i] = tswap32(target_grouplist[i]);
8002             unlock_user(target_grouplist, arg2, 0);
8003             ret = get_errno(setgroups(gidsetsize, grouplist));
8004         }
8005         break;
8006 #endif
8007 #ifdef TARGET_NR_fchown32
8008     case TARGET_NR_fchown32:
8009         ret = get_errno(fchown(arg1, arg2, arg3));
8010         break;
8011 #endif
8012 #ifdef TARGET_NR_setresuid32
8013     case TARGET_NR_setresuid32:
8014         ret = get_errno(setresuid(arg1, arg2, arg3));
8015         break;
8016 #endif
8017 #ifdef TARGET_NR_getresuid32
8018     case TARGET_NR_getresuid32:
8019         {
8020             uid_t ruid, euid, suid;
8021             ret = get_errno(getresuid(&ruid, &euid, &suid));
8022             if (!is_error(ret)) {
8023                 if (put_user_u32(ruid, arg1)
8024                     || put_user_u32(euid, arg2)
8025                     || put_user_u32(suid, arg3))
8026                     goto efault;
8027             }
8028         }
8029         break;
8030 #endif
8031 #ifdef TARGET_NR_setresgid32
8032     case TARGET_NR_setresgid32:
8033         ret = get_errno(setresgid(arg1, arg2, arg3));
8034         break;
8035 #endif
8036 #ifdef TARGET_NR_getresgid32
8037     case TARGET_NR_getresgid32:
8038         {
8039             gid_t rgid, egid, sgid;
8040             ret = get_errno(getresgid(&rgid, &egid, &sgid));
8041             if (!is_error(ret)) {
8042                 if (put_user_u32(rgid, arg1)
8043                     || put_user_u32(egid, arg2)
8044                     || put_user_u32(sgid, arg3))
8045                     goto efault;
8046             }
8047         }
8048         break;
8049 #endif
8050 #ifdef TARGET_NR_chown32
8051     case TARGET_NR_chown32:
8052         if (!(p = lock_user_string(arg1)))
8053             goto efault;
8054         ret = get_errno(chown(p, arg2, arg3));
8055         unlock_user(p, arg1, 0);
8056         break;
8057 #endif
8058 #ifdef TARGET_NR_setuid32
8059     case TARGET_NR_setuid32:
8060         ret = get_errno(setuid(arg1));
8061         break;
8062 #endif
8063 #ifdef TARGET_NR_setgid32
8064     case TARGET_NR_setgid32:
8065         ret = get_errno(setgid(arg1));
8066         break;
8067 #endif
8068 #ifdef TARGET_NR_setfsuid32
8069     case TARGET_NR_setfsuid32:
8070         ret = get_errno(setfsuid(arg1));
8071         break;
8072 #endif
8073 #ifdef TARGET_NR_setfsgid32
8074     case TARGET_NR_setfsgid32:
8075         ret = get_errno(setfsgid(arg1));
8076         break;
8077 #endif
8078 
8079     case TARGET_NR_pivot_root:
8080         goto unimplemented;
8081 #ifdef TARGET_NR_mincore
8082     case TARGET_NR_mincore:
8083         {
8084             void *a;
8085             ret = -TARGET_EFAULT;
8086             if (!(a = lock_user(VERIFY_READ, arg1,arg2, 0)))
8087                 goto efault;
8088             if (!(p = lock_user_string(arg3)))
8089                 goto mincore_fail;
8090             ret = get_errno(mincore(a, arg2, p));
8091             unlock_user(p, arg3, ret);
8092             mincore_fail:
8093             unlock_user(a, arg1, 0);
8094         }
8095         break;
8096 #endif
8097 #ifdef TARGET_NR_arm_fadvise64_64
8098     case TARGET_NR_arm_fadvise64_64:
8099 	{
8100 		/*
8101 		 * arm_fadvise64_64 looks like fadvise64_64 but
8102 		 * with different argument order
8103 		 */
8104 		abi_long temp;
8105 		temp = arg3;
8106 		arg3 = arg4;
8107 		arg4 = temp;
8108 	}
8109 #endif
8110 #if defined(TARGET_NR_fadvise64_64) || defined(TARGET_NR_arm_fadvise64_64) || defined(TARGET_NR_fadvise64)
8111 #ifdef TARGET_NR_fadvise64_64
8112     case TARGET_NR_fadvise64_64:
8113 #endif
8114 #ifdef TARGET_NR_fadvise64
8115     case TARGET_NR_fadvise64:
8116 #endif
8117 #ifdef TARGET_S390X
8118         switch (arg4) {
8119         case 4: arg4 = POSIX_FADV_NOREUSE + 1; break; /* make sure it's an invalid value */
8120         case 5: arg4 = POSIX_FADV_NOREUSE + 2; break; /* ditto */
8121         case 6: arg4 = POSIX_FADV_DONTNEED; break;
8122         case 7: arg4 = POSIX_FADV_NOREUSE; break;
8123         default: break;
8124         }
8125 #endif
8126         ret = -posix_fadvise(arg1, arg2, arg3, arg4);
8127 	break;
8128 #endif
8129 #ifdef TARGET_NR_madvise
8130     case TARGET_NR_madvise:
8131         /* A straight passthrough may not be safe because qemu sometimes
8132            turns private file-backed mappings into anonymous mappings.
8133            This will break MADV_DONTNEED.
8134            This is a hint, so ignoring and returning success is ok.  */
8135         ret = get_errno(0);
8136         break;
8137 #endif
8138 #if TARGET_ABI_BITS == 32
8139     case TARGET_NR_fcntl64:
8140     {
8141 	int cmd;
8142 	struct flock64 fl;
8143 	struct target_flock64 *target_fl;
8144 #ifdef TARGET_ARM
8145 	struct target_eabi_flock64 *target_efl;
8146 #endif
8147 
8148 	cmd = target_to_host_fcntl_cmd(arg2);
8149         if (cmd == -TARGET_EINVAL) {
8150             ret = cmd;
8151             break;
8152         }
8153 
8154         switch(arg2) {
8155         case TARGET_F_GETLK64:
8156 #ifdef TARGET_ARM
8157             if (((CPUARMState *)cpu_env)->eabi) {
8158                 if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
8159                     goto efault;
8160                 fl.l_type = tswap16(target_efl->l_type);
8161                 fl.l_whence = tswap16(target_efl->l_whence);
8162                 fl.l_start = tswap64(target_efl->l_start);
8163                 fl.l_len = tswap64(target_efl->l_len);
8164                 fl.l_pid = tswap32(target_efl->l_pid);
8165                 unlock_user_struct(target_efl, arg3, 0);
8166             } else
8167 #endif
8168             {
8169                 if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
8170                     goto efault;
8171                 fl.l_type = tswap16(target_fl->l_type);
8172                 fl.l_whence = tswap16(target_fl->l_whence);
8173                 fl.l_start = tswap64(target_fl->l_start);
8174                 fl.l_len = tswap64(target_fl->l_len);
8175                 fl.l_pid = tswap32(target_fl->l_pid);
8176                 unlock_user_struct(target_fl, arg3, 0);
8177             }
8178             ret = get_errno(fcntl(arg1, cmd, &fl));
8179 	    if (ret == 0) {
8180 #ifdef TARGET_ARM
8181                 if (((CPUARMState *)cpu_env)->eabi) {
8182                     if (!lock_user_struct(VERIFY_WRITE, target_efl, arg3, 0))
8183                         goto efault;
8184                     target_efl->l_type = tswap16(fl.l_type);
8185                     target_efl->l_whence = tswap16(fl.l_whence);
8186                     target_efl->l_start = tswap64(fl.l_start);
8187                     target_efl->l_len = tswap64(fl.l_len);
8188                     target_efl->l_pid = tswap32(fl.l_pid);
8189                     unlock_user_struct(target_efl, arg3, 1);
8190                 } else
8191 #endif
8192                 {
8193                     if (!lock_user_struct(VERIFY_WRITE, target_fl, arg3, 0))
8194                         goto efault;
8195                     target_fl->l_type = tswap16(fl.l_type);
8196                     target_fl->l_whence = tswap16(fl.l_whence);
8197                     target_fl->l_start = tswap64(fl.l_start);
8198                     target_fl->l_len = tswap64(fl.l_len);
8199                     target_fl->l_pid = tswap32(fl.l_pid);
8200                     unlock_user_struct(target_fl, arg3, 1);
8201                 }
8202 	    }
8203 	    break;
8204 
8205         case TARGET_F_SETLK64:
8206         case TARGET_F_SETLKW64:
8207 #ifdef TARGET_ARM
8208             if (((CPUARMState *)cpu_env)->eabi) {
8209                 if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
8210                     goto efault;
8211                 fl.l_type = tswap16(target_efl->l_type);
8212                 fl.l_whence = tswap16(target_efl->l_whence);
8213                 fl.l_start = tswap64(target_efl->l_start);
8214                 fl.l_len = tswap64(target_efl->l_len);
8215                 fl.l_pid = tswap32(target_efl->l_pid);
8216                 unlock_user_struct(target_efl, arg3, 0);
8217             } else
8218 #endif
8219             {
8220                 if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
8221                     goto efault;
8222                 fl.l_type = tswap16(target_fl->l_type);
8223                 fl.l_whence = tswap16(target_fl->l_whence);
8224                 fl.l_start = tswap64(target_fl->l_start);
8225                 fl.l_len = tswap64(target_fl->l_len);
8226                 fl.l_pid = tswap32(target_fl->l_pid);
8227                 unlock_user_struct(target_fl, arg3, 0);
8228             }
8229             ret = get_errno(fcntl(arg1, cmd, &fl));
8230 	    break;
8231         default:
8232             ret = do_fcntl(arg1, arg2, arg3);
8233             break;
8234         }
8235 	break;
8236     }
8237 #endif
8238 #ifdef TARGET_NR_cacheflush
8239     case TARGET_NR_cacheflush:
8240         /* self-modifying code is handled automatically, so nothing needed */
8241         ret = 0;
8242         break;
8243 #endif
8244 #ifdef TARGET_NR_security
8245     case TARGET_NR_security:
8246         goto unimplemented;
8247 #endif
8248 #ifdef TARGET_NR_getpagesize
8249     case TARGET_NR_getpagesize:
8250         ret = TARGET_PAGE_SIZE;
8251         break;
8252 #endif
8253     case TARGET_NR_gettid:
8254         ret = get_errno(gettid());
8255         break;
8256 #ifdef TARGET_NR_readahead
8257     case TARGET_NR_readahead:
8258 #if TARGET_ABI_BITS == 32
8259         if (regpairs_aligned(cpu_env)) {
8260             arg2 = arg3;
8261             arg3 = arg4;
8262             arg4 = arg5;
8263         }
8264         ret = get_errno(readahead(arg1, ((off64_t)arg3 << 32) | arg2, arg4));
8265 #else
8266         ret = get_errno(readahead(arg1, arg2, arg3));
8267 #endif
8268         break;
8269 #endif
8270 #ifdef CONFIG_ATTR
8271 #ifdef TARGET_NR_setxattr
8272     case TARGET_NR_listxattr:
8273     case TARGET_NR_llistxattr:
8274     {
8275         void *p, *b = 0;
8276         if (arg2) {
8277             b = lock_user(VERIFY_WRITE, arg2, arg3, 0);
8278             if (!b) {
8279                 ret = -TARGET_EFAULT;
8280                 break;
8281             }
8282         }
8283         p = lock_user_string(arg1);
8284         if (p) {
8285             if (num == TARGET_NR_listxattr) {
8286                 ret = get_errno(listxattr(p, b, arg3));
8287             } else {
8288                 ret = get_errno(llistxattr(p, b, arg3));
8289             }
8290         } else {
8291             ret = -TARGET_EFAULT;
8292         }
8293         unlock_user(p, arg1, 0);
8294         unlock_user(b, arg2, arg3);
8295         break;
8296     }
8297     case TARGET_NR_flistxattr:
8298     {
8299         void *b = 0;
8300         if (arg2) {
8301             b = lock_user(VERIFY_WRITE, arg2, arg3, 0);
8302             if (!b) {
8303                 ret = -TARGET_EFAULT;
8304                 break;
8305             }
8306         }
8307         ret = get_errno(flistxattr(arg1, b, arg3));
8308         unlock_user(b, arg2, arg3);
8309         break;
8310     }
8311     case TARGET_NR_setxattr:
8312     case TARGET_NR_lsetxattr:
8313         {
8314             void *p, *n, *v = 0;
8315             if (arg3) {
8316                 v = lock_user(VERIFY_READ, arg3, arg4, 1);
8317                 if (!v) {
8318                     ret = -TARGET_EFAULT;
8319                     break;
8320                 }
8321             }
8322             p = lock_user_string(arg1);
8323             n = lock_user_string(arg2);
8324             if (p && n) {
8325                 if (num == TARGET_NR_setxattr) {
8326                     ret = get_errno(setxattr(p, n, v, arg4, arg5));
8327                 } else {
8328                     ret = get_errno(lsetxattr(p, n, v, arg4, arg5));
8329                 }
8330             } else {
8331                 ret = -TARGET_EFAULT;
8332             }
8333             unlock_user(p, arg1, 0);
8334             unlock_user(n, arg2, 0);
8335             unlock_user(v, arg3, 0);
8336         }
8337         break;
8338     case TARGET_NR_fsetxattr:
8339         {
8340             void *n, *v = 0;
8341             if (arg3) {
8342                 v = lock_user(VERIFY_READ, arg3, arg4, 1);
8343                 if (!v) {
8344                     ret = -TARGET_EFAULT;
8345                     break;
8346                 }
8347             }
8348             n = lock_user_string(arg2);
8349             if (n) {
8350                 ret = get_errno(fsetxattr(arg1, n, v, arg4, arg5));
8351             } else {
8352                 ret = -TARGET_EFAULT;
8353             }
8354             unlock_user(n, arg2, 0);
8355             unlock_user(v, arg3, 0);
8356         }
8357         break;
8358     case TARGET_NR_getxattr:
8359     case TARGET_NR_lgetxattr:
8360         {
8361             void *p, *n, *v = 0;
8362             if (arg3) {
8363                 v = lock_user(VERIFY_WRITE, arg3, arg4, 0);
8364                 if (!v) {
8365                     ret = -TARGET_EFAULT;
8366                     break;
8367                 }
8368             }
8369             p = lock_user_string(arg1);
8370             n = lock_user_string(arg2);
8371             if (p && n) {
8372                 if (num == TARGET_NR_getxattr) {
8373                     ret = get_errno(getxattr(p, n, v, arg4));
8374                 } else {
8375                     ret = get_errno(lgetxattr(p, n, v, arg4));
8376                 }
8377             } else {
8378                 ret = -TARGET_EFAULT;
8379             }
8380             unlock_user(p, arg1, 0);
8381             unlock_user(n, arg2, 0);
8382             unlock_user(v, arg3, arg4);
8383         }
8384         break;
8385     case TARGET_NR_fgetxattr:
8386         {
8387             void *n, *v = 0;
8388             if (arg3) {
8389                 v = lock_user(VERIFY_WRITE, arg3, arg4, 0);
8390                 if (!v) {
8391                     ret = -TARGET_EFAULT;
8392                     break;
8393                 }
8394             }
8395             n = lock_user_string(arg2);
8396             if (n) {
8397                 ret = get_errno(fgetxattr(arg1, n, v, arg4));
8398             } else {
8399                 ret = -TARGET_EFAULT;
8400             }
8401             unlock_user(n, arg2, 0);
8402             unlock_user(v, arg3, arg4);
8403         }
8404         break;
8405     case TARGET_NR_removexattr:
8406     case TARGET_NR_lremovexattr:
8407         {
8408             void *p, *n;
8409             p = lock_user_string(arg1);
8410             n = lock_user_string(arg2);
8411             if (p && n) {
8412                 if (num == TARGET_NR_removexattr) {
8413                     ret = get_errno(removexattr(p, n));
8414                 } else {
8415                     ret = get_errno(lremovexattr(p, n));
8416                 }
8417             } else {
8418                 ret = -TARGET_EFAULT;
8419             }
8420             unlock_user(p, arg1, 0);
8421             unlock_user(n, arg2, 0);
8422         }
8423         break;
8424     case TARGET_NR_fremovexattr:
8425         {
8426             void *n;
8427             n = lock_user_string(arg2);
8428             if (n) {
8429                 ret = get_errno(fremovexattr(arg1, n));
8430             } else {
8431                 ret = -TARGET_EFAULT;
8432             }
8433             unlock_user(n, arg2, 0);
8434         }
8435         break;
8436 #endif
8437 #endif /* CONFIG_ATTR */
8438 #ifdef TARGET_NR_set_thread_area
8439     case TARGET_NR_set_thread_area:
8440 #if defined(TARGET_MIPS)
8441       ((CPUMIPSState *) cpu_env)->tls_value = arg1;
8442       ret = 0;
8443       break;
8444 #elif defined(TARGET_CRIS)
8445       if (arg1 & 0xff)
8446           ret = -TARGET_EINVAL;
8447       else {
8448           ((CPUCRISState *) cpu_env)->pregs[PR_PID] = arg1;
8449           ret = 0;
8450       }
8451       break;
8452 #elif defined(TARGET_I386) && defined(TARGET_ABI32)
8453       ret = do_set_thread_area(cpu_env, arg1);
8454       break;
8455 #else
8456       goto unimplemented_nowarn;
8457 #endif
8458 #endif
8459 #ifdef TARGET_NR_get_thread_area
8460     case TARGET_NR_get_thread_area:
8461 #if defined(TARGET_I386) && defined(TARGET_ABI32)
8462         ret = do_get_thread_area(cpu_env, arg1);
8463 #else
8464         goto unimplemented_nowarn;
8465 #endif
8466 #endif
8467 #ifdef TARGET_NR_getdomainname
8468     case TARGET_NR_getdomainname:
8469         goto unimplemented_nowarn;
8470 #endif
8471 
8472 #ifdef TARGET_NR_clock_gettime
8473     case TARGET_NR_clock_gettime:
8474     {
8475         struct timespec ts;
8476         ret = get_errno(clock_gettime(arg1, &ts));
8477         if (!is_error(ret)) {
8478             host_to_target_timespec(arg2, &ts);
8479         }
8480         break;
8481     }
8482 #endif
8483 #ifdef TARGET_NR_clock_getres
8484     case TARGET_NR_clock_getres:
8485     {
8486         struct timespec ts;
8487         ret = get_errno(clock_getres(arg1, &ts));
8488         if (!is_error(ret)) {
8489             host_to_target_timespec(arg2, &ts);
8490         }
8491         break;
8492     }
8493 #endif
8494 #ifdef TARGET_NR_clock_nanosleep
8495     case TARGET_NR_clock_nanosleep:
8496     {
8497         struct timespec ts;
8498         target_to_host_timespec(&ts, arg3);
8499         ret = get_errno(clock_nanosleep(arg1, arg2, &ts, arg4 ? &ts : NULL));
8500         if (arg4)
8501             host_to_target_timespec(arg4, &ts);
8502         break;
8503     }
8504 #endif
8505 
8506 #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
8507     case TARGET_NR_set_tid_address:
8508         ret = get_errno(set_tid_address((int *)g2h(arg1)));
8509         break;
8510 #endif
8511 
8512 #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
8513     case TARGET_NR_tkill:
8514         ret = get_errno(sys_tkill((int)arg1, target_to_host_signal(arg2)));
8515         break;
8516 #endif
8517 
8518 #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
8519     case TARGET_NR_tgkill:
8520 	ret = get_errno(sys_tgkill((int)arg1, (int)arg2,
8521                         target_to_host_signal(arg3)));
8522 	break;
8523 #endif
8524 
8525 #ifdef TARGET_NR_set_robust_list
8526     case TARGET_NR_set_robust_list:
8527     case TARGET_NR_get_robust_list:
8528         /* The ABI for supporting robust futexes has userspace pass
8529          * the kernel a pointer to a linked list which is updated by
8530          * userspace after the syscall; the list is walked by the kernel
8531          * when the thread exits. Since the linked list in QEMU guest
8532          * memory isn't a valid linked list for the host and we have
8533          * no way to reliably intercept the thread-death event, we can't
8534          * support these. Silently return ENOSYS so that guest userspace
8535          * falls back to a non-robust futex implementation (which should
8536          * be OK except in the corner case of the guest crashing while
8537          * holding a mutex that is shared with another process via
8538          * shared memory).
8539          */
8540         goto unimplemented_nowarn;
8541 #endif
8542 
8543 #if defined(TARGET_NR_utimensat) && defined(__NR_utimensat)
8544     case TARGET_NR_utimensat:
8545         {
8546             struct timespec *tsp, ts[2];
8547             if (!arg3) {
8548                 tsp = NULL;
8549             } else {
8550                 target_to_host_timespec(ts, arg3);
8551                 target_to_host_timespec(ts+1, arg3+sizeof(struct target_timespec));
8552                 tsp = ts;
8553             }
8554             if (!arg2)
8555                 ret = get_errno(sys_utimensat(arg1, NULL, tsp, arg4));
8556             else {
8557                 if (!(p = lock_user_string(arg2))) {
8558                     ret = -TARGET_EFAULT;
8559                     goto fail;
8560                 }
8561                 ret = get_errno(sys_utimensat(arg1, path(p), tsp, arg4));
8562                 unlock_user(p, arg2, 0);
8563             }
8564         }
8565 	break;
8566 #endif
8567 #if defined(CONFIG_USE_NPTL)
8568     case TARGET_NR_futex:
8569         ret = do_futex(arg1, arg2, arg3, arg4, arg5, arg6);
8570         break;
8571 #endif
8572 #if defined(TARGET_NR_inotify_init) && defined(__NR_inotify_init)
8573     case TARGET_NR_inotify_init:
8574         ret = get_errno(sys_inotify_init());
8575         break;
8576 #endif
8577 #ifdef CONFIG_INOTIFY1
8578 #if defined(TARGET_NR_inotify_init1) && defined(__NR_inotify_init1)
8579     case TARGET_NR_inotify_init1:
8580         ret = get_errno(sys_inotify_init1(arg1));
8581         break;
8582 #endif
8583 #endif
8584 #if defined(TARGET_NR_inotify_add_watch) && defined(__NR_inotify_add_watch)
8585     case TARGET_NR_inotify_add_watch:
8586         p = lock_user_string(arg2);
8587         ret = get_errno(sys_inotify_add_watch(arg1, path(p), arg3));
8588         unlock_user(p, arg2, 0);
8589         break;
8590 #endif
8591 #if defined(TARGET_NR_inotify_rm_watch) && defined(__NR_inotify_rm_watch)
8592     case TARGET_NR_inotify_rm_watch:
8593         ret = get_errno(sys_inotify_rm_watch(arg1, arg2));
8594         break;
8595 #endif
8596 
8597 #if defined(TARGET_NR_mq_open) && defined(__NR_mq_open)
8598     case TARGET_NR_mq_open:
8599         {
8600             struct mq_attr posix_mq_attr;
8601 
8602             p = lock_user_string(arg1 - 1);
8603             if (arg4 != 0)
8604                 copy_from_user_mq_attr (&posix_mq_attr, arg4);
8605             ret = get_errno(mq_open(p, arg2, arg3, &posix_mq_attr));
8606             unlock_user (p, arg1, 0);
8607         }
8608         break;
8609 
8610     case TARGET_NR_mq_unlink:
8611         p = lock_user_string(arg1 - 1);
8612         ret = get_errno(mq_unlink(p));
8613         unlock_user (p, arg1, 0);
8614         break;
8615 
8616     case TARGET_NR_mq_timedsend:
8617         {
8618             struct timespec ts;
8619 
8620             p = lock_user (VERIFY_READ, arg2, arg3, 1);
8621             if (arg5 != 0) {
8622                 target_to_host_timespec(&ts, arg5);
8623                 ret = get_errno(mq_timedsend(arg1, p, arg3, arg4, &ts));
8624                 host_to_target_timespec(arg5, &ts);
8625             }
8626             else
8627                 ret = get_errno(mq_send(arg1, p, arg3, arg4));
8628             unlock_user (p, arg2, arg3);
8629         }
8630         break;
8631 
8632     case TARGET_NR_mq_timedreceive:
8633         {
8634             struct timespec ts;
8635             unsigned int prio;
8636 
8637             p = lock_user (VERIFY_READ, arg2, arg3, 1);
8638             if (arg5 != 0) {
8639                 target_to_host_timespec(&ts, arg5);
8640                 ret = get_errno(mq_timedreceive(arg1, p, arg3, &prio, &ts));
8641                 host_to_target_timespec(arg5, &ts);
8642             }
8643             else
8644                 ret = get_errno(mq_receive(arg1, p, arg3, &prio));
8645             unlock_user (p, arg2, arg3);
8646             if (arg4 != 0)
8647                 put_user_u32(prio, arg4);
8648         }
8649         break;
8650 
8651     /* Not implemented for now... */
8652 /*     case TARGET_NR_mq_notify: */
8653 /*         break; */
8654 
8655     case TARGET_NR_mq_getsetattr:
8656         {
8657             struct mq_attr posix_mq_attr_in, posix_mq_attr_out;
8658             ret = 0;
8659             if (arg3 != 0) {
8660                 ret = mq_getattr(arg1, &posix_mq_attr_out);
8661                 copy_to_user_mq_attr(arg3, &posix_mq_attr_out);
8662             }
8663             if (arg2 != 0) {
8664                 copy_from_user_mq_attr(&posix_mq_attr_in, arg2);
8665                 ret |= mq_setattr(arg1, &posix_mq_attr_in, &posix_mq_attr_out);
8666             }
8667 
8668         }
8669         break;
8670 #endif
8671 
8672 #ifdef CONFIG_SPLICE
8673 #ifdef TARGET_NR_tee
8674     case TARGET_NR_tee:
8675         {
8676             ret = get_errno(tee(arg1,arg2,arg3,arg4));
8677         }
8678         break;
8679 #endif
8680 #ifdef TARGET_NR_splice
8681     case TARGET_NR_splice:
8682         {
8683             loff_t loff_in, loff_out;
8684             loff_t *ploff_in = NULL, *ploff_out = NULL;
8685             if(arg2) {
8686                 get_user_u64(loff_in, arg2);
8687                 ploff_in = &loff_in;
8688             }
8689             if(arg4) {
8690                 get_user_u64(loff_out, arg2);
8691                 ploff_out = &loff_out;
8692             }
8693             ret = get_errno(splice(arg1, ploff_in, arg3, ploff_out, arg5, arg6));
8694         }
8695         break;
8696 #endif
8697 #ifdef TARGET_NR_vmsplice
8698 	case TARGET_NR_vmsplice:
8699         {
8700             struct iovec *vec = lock_iovec(VERIFY_READ, arg2, arg3, 1);
8701             if (vec != NULL) {
8702                 ret = get_errno(vmsplice(arg1, vec, arg3, arg4));
8703                 unlock_iovec(vec, arg2, arg3, 0);
8704             } else {
8705                 ret = -host_to_target_errno(errno);
8706             }
8707         }
8708         break;
8709 #endif
8710 #endif /* CONFIG_SPLICE */
8711 #ifdef CONFIG_EVENTFD
8712 #if defined(TARGET_NR_eventfd)
8713     case TARGET_NR_eventfd:
8714         ret = get_errno(eventfd(arg1, 0));
8715         break;
8716 #endif
8717 #if defined(TARGET_NR_eventfd2)
8718     case TARGET_NR_eventfd2:
8719     {
8720         int host_flags = arg2 & (~(TARGET_O_NONBLOCK | TARGET_O_CLOEXEC));
8721         if (arg2 & TARGET_O_NONBLOCK) {
8722             host_flags |= O_NONBLOCK;
8723         }
8724         if (arg2 & TARGET_O_CLOEXEC) {
8725             host_flags |= O_CLOEXEC;
8726         }
8727         ret = get_errno(eventfd(arg1, host_flags));
8728         break;
8729     }
8730 #endif
8731 #endif /* CONFIG_EVENTFD  */
8732 #if defined(CONFIG_FALLOCATE) && defined(TARGET_NR_fallocate)
8733     case TARGET_NR_fallocate:
8734 #if TARGET_ABI_BITS == 32
8735         ret = get_errno(fallocate(arg1, arg2, target_offset64(arg3, arg4),
8736                                   target_offset64(arg5, arg6)));
8737 #else
8738         ret = get_errno(fallocate(arg1, arg2, arg3, arg4));
8739 #endif
8740         break;
8741 #endif
8742 #if defined(CONFIG_SYNC_FILE_RANGE)
8743 #if defined(TARGET_NR_sync_file_range)
8744     case TARGET_NR_sync_file_range:
8745 #if TARGET_ABI_BITS == 32
8746 #if defined(TARGET_MIPS)
8747         ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
8748                                         target_offset64(arg5, arg6), arg7));
8749 #else
8750         ret = get_errno(sync_file_range(arg1, target_offset64(arg2, arg3),
8751                                         target_offset64(arg4, arg5), arg6));
8752 #endif /* !TARGET_MIPS */
8753 #else
8754         ret = get_errno(sync_file_range(arg1, arg2, arg3, arg4));
8755 #endif
8756         break;
8757 #endif
8758 #if defined(TARGET_NR_sync_file_range2)
8759     case TARGET_NR_sync_file_range2:
8760         /* This is like sync_file_range but the arguments are reordered */
8761 #if TARGET_ABI_BITS == 32
8762         ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
8763                                         target_offset64(arg5, arg6), arg2));
8764 #else
8765         ret = get_errno(sync_file_range(arg1, arg3, arg4, arg2));
8766 #endif
8767         break;
8768 #endif
8769 #endif
8770 #if defined(CONFIG_EPOLL)
8771 #if defined(TARGET_NR_epoll_create)
8772     case TARGET_NR_epoll_create:
8773         ret = get_errno(epoll_create(arg1));
8774         break;
8775 #endif
8776 #if defined(TARGET_NR_epoll_create1) && defined(CONFIG_EPOLL_CREATE1)
8777     case TARGET_NR_epoll_create1:
8778         ret = get_errno(epoll_create1(arg1));
8779         break;
8780 #endif
8781 #if defined(TARGET_NR_epoll_ctl)
8782     case TARGET_NR_epoll_ctl:
8783     {
8784         struct epoll_event ep;
8785         struct epoll_event *epp = 0;
8786         if (arg4) {
8787             struct target_epoll_event *target_ep;
8788             if (!lock_user_struct(VERIFY_READ, target_ep, arg4, 1)) {
8789                 goto efault;
8790             }
8791             ep.events = tswap32(target_ep->events);
8792             /* The epoll_data_t union is just opaque data to the kernel,
8793              * so we transfer all 64 bits across and need not worry what
8794              * actual data type it is.
8795              */
8796             ep.data.u64 = tswap64(target_ep->data.u64);
8797             unlock_user_struct(target_ep, arg4, 0);
8798             epp = &ep;
8799         }
8800         ret = get_errno(epoll_ctl(arg1, arg2, arg3, epp));
8801         break;
8802     }
8803 #endif
8804 
8805 #if defined(TARGET_NR_epoll_pwait) && defined(CONFIG_EPOLL_PWAIT)
8806 #define IMPLEMENT_EPOLL_PWAIT
8807 #endif
8808 #if defined(TARGET_NR_epoll_wait) || defined(IMPLEMENT_EPOLL_PWAIT)
8809 #if defined(TARGET_NR_epoll_wait)
8810     case TARGET_NR_epoll_wait:
8811 #endif
8812 #if defined(IMPLEMENT_EPOLL_PWAIT)
8813     case TARGET_NR_epoll_pwait:
8814 #endif
8815     {
8816         struct target_epoll_event *target_ep;
8817         struct epoll_event *ep;
8818         int epfd = arg1;
8819         int maxevents = arg3;
8820         int timeout = arg4;
8821 
8822         target_ep = lock_user(VERIFY_WRITE, arg2,
8823                               maxevents * sizeof(struct target_epoll_event), 1);
8824         if (!target_ep) {
8825             goto efault;
8826         }
8827 
8828         ep = alloca(maxevents * sizeof(struct epoll_event));
8829 
8830         switch (num) {
8831 #if defined(IMPLEMENT_EPOLL_PWAIT)
8832         case TARGET_NR_epoll_pwait:
8833         {
8834             target_sigset_t *target_set;
8835             sigset_t _set, *set = &_set;
8836 
8837             if (arg5) {
8838                 target_set = lock_user(VERIFY_READ, arg5,
8839                                        sizeof(target_sigset_t), 1);
8840                 if (!target_set) {
8841                     unlock_user(target_ep, arg2, 0);
8842                     goto efault;
8843                 }
8844                 target_to_host_sigset(set, target_set);
8845                 unlock_user(target_set, arg5, 0);
8846             } else {
8847                 set = NULL;
8848             }
8849 
8850             ret = get_errno(epoll_pwait(epfd, ep, maxevents, timeout, set));
8851             break;
8852         }
8853 #endif
8854 #if defined(TARGET_NR_epoll_wait)
8855         case TARGET_NR_epoll_wait:
8856             ret = get_errno(epoll_wait(epfd, ep, maxevents, timeout));
8857             break;
8858 #endif
8859         default:
8860             ret = -TARGET_ENOSYS;
8861         }
8862         if (!is_error(ret)) {
8863             int i;
8864             for (i = 0; i < ret; i++) {
8865                 target_ep[i].events = tswap32(ep[i].events);
8866                 target_ep[i].data.u64 = tswap64(ep[i].data.u64);
8867             }
8868         }
8869         unlock_user(target_ep, arg2, ret * sizeof(struct target_epoll_event));
8870         break;
8871     }
8872 #endif
8873 #endif
8874 #ifdef TARGET_NR_prlimit64
8875     case TARGET_NR_prlimit64:
8876     {
8877         /* args: pid, resource number, ptr to new rlimit, ptr to old rlimit */
8878         struct target_rlimit64 *target_rnew, *target_rold;
8879         struct host_rlimit64 rnew, rold, *rnewp = 0;
8880         if (arg3) {
8881             if (!lock_user_struct(VERIFY_READ, target_rnew, arg3, 1)) {
8882                 goto efault;
8883             }
8884             rnew.rlim_cur = tswap64(target_rnew->rlim_cur);
8885             rnew.rlim_max = tswap64(target_rnew->rlim_max);
8886             unlock_user_struct(target_rnew, arg3, 0);
8887             rnewp = &rnew;
8888         }
8889 
8890         ret = get_errno(sys_prlimit64(arg1, arg2, rnewp, arg4 ? &rold : 0));
8891         if (!is_error(ret) && arg4) {
8892             if (!lock_user_struct(VERIFY_WRITE, target_rold, arg4, 1)) {
8893                 goto efault;
8894             }
8895             target_rold->rlim_cur = tswap64(rold.rlim_cur);
8896             target_rold->rlim_max = tswap64(rold.rlim_max);
8897             unlock_user_struct(target_rold, arg4, 1);
8898         }
8899         break;
8900     }
8901 #endif
8902 #ifdef TARGET_NR_gethostname
8903     case TARGET_NR_gethostname:
8904     {
8905         char *name = lock_user(VERIFY_WRITE, arg1, arg2, 0);
8906         if (name) {
8907             ret = get_errno(gethostname(name, arg2));
8908             unlock_user(name, arg1, arg2);
8909         } else {
8910             ret = -TARGET_EFAULT;
8911         }
8912         break;
8913     }
8914 #endif
8915     default:
8916     unimplemented:
8917         gemu_log("qemu: Unsupported syscall: %d\n", num);
8918 #if defined(TARGET_NR_setxattr) || defined(TARGET_NR_get_thread_area) || defined(TARGET_NR_getdomainname) || defined(TARGET_NR_set_robust_list)
8919     unimplemented_nowarn:
8920 #endif
8921         ret = -TARGET_ENOSYS;
8922         break;
8923     }
8924 fail:
8925 #ifdef DEBUG
8926     gemu_log(" = " TARGET_ABI_FMT_ld "\n", ret);
8927 #endif
8928     if(do_strace)
8929         print_syscall_ret(num, ret);
8930     return ret;
8931 efault:
8932     ret = -TARGET_EFAULT;
8933     goto fail;
8934 }
8935