xref: /openbmc/qemu/linux-user/syscall.c (revision 2c9b15ca)
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_env = env;
4175     ts = (TaskState *)thread_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     abi_long ret;
5034     struct stat st;
5035     struct statfs stfs;
5036     void *p;
5037 
5038 #ifdef DEBUG
5039     gemu_log("syscall %d", num);
5040 #endif
5041     if(do_strace)
5042         print_syscall(num, arg1, arg2, arg3, arg4, arg5, arg6);
5043 
5044     switch(num) {
5045     case TARGET_NR_exit:
5046 #ifdef CONFIG_USE_NPTL
5047       /* In old applications this may be used to implement _exit(2).
5048          However in threaded applictions it is used for thread termination,
5049          and _exit_group is used for application termination.
5050          Do thread termination if we have more then one thread.  */
5051       /* FIXME: This probably breaks if a signal arrives.  We should probably
5052          be disabling signals.  */
5053       if (first_cpu->next_cpu) {
5054           TaskState *ts;
5055           CPUArchState **lastp;
5056           CPUArchState *p;
5057 
5058           cpu_list_lock();
5059           lastp = &first_cpu;
5060           p = first_cpu;
5061           while (p && p != (CPUArchState *)cpu_env) {
5062               lastp = &p->next_cpu;
5063               p = p->next_cpu;
5064           }
5065           /* If we didn't find the CPU for this thread then something is
5066              horribly wrong.  */
5067           if (!p)
5068               abort();
5069           /* Remove the CPU from the list.  */
5070           *lastp = p->next_cpu;
5071           cpu_list_unlock();
5072           ts = ((CPUArchState *)cpu_env)->opaque;
5073           if (ts->child_tidptr) {
5074               put_user_u32(0, ts->child_tidptr);
5075               sys_futex(g2h(ts->child_tidptr), FUTEX_WAKE, INT_MAX,
5076                         NULL, NULL, 0);
5077           }
5078           thread_env = NULL;
5079           object_unref(OBJECT(ENV_GET_CPU(cpu_env)));
5080           g_free(ts);
5081           pthread_exit(NULL);
5082       }
5083 #endif
5084 #ifdef TARGET_GPROF
5085         _mcleanup();
5086 #endif
5087         gdb_exit(cpu_env, arg1);
5088         _exit(arg1);
5089         ret = 0; /* avoid warning */
5090         break;
5091     case TARGET_NR_read:
5092         if (arg3 == 0)
5093             ret = 0;
5094         else {
5095             if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
5096                 goto efault;
5097             ret = get_errno(read(arg1, p, arg3));
5098             unlock_user(p, arg2, ret);
5099         }
5100         break;
5101     case TARGET_NR_write:
5102         if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
5103             goto efault;
5104         ret = get_errno(write(arg1, p, arg3));
5105         unlock_user(p, arg2, 0);
5106         break;
5107     case TARGET_NR_open:
5108         if (!(p = lock_user_string(arg1)))
5109             goto efault;
5110         ret = get_errno(do_open(cpu_env, p,
5111                                 target_to_host_bitmask(arg2, fcntl_flags_tbl),
5112                                 arg3));
5113         unlock_user(p, arg1, 0);
5114         break;
5115 #if defined(TARGET_NR_openat) && defined(__NR_openat)
5116     case TARGET_NR_openat:
5117         if (!(p = lock_user_string(arg2)))
5118             goto efault;
5119         ret = get_errno(sys_openat(arg1,
5120                                    path(p),
5121                                    target_to_host_bitmask(arg3, fcntl_flags_tbl),
5122                                    arg4));
5123         unlock_user(p, arg2, 0);
5124         break;
5125 #endif
5126     case TARGET_NR_close:
5127         ret = get_errno(close(arg1));
5128         break;
5129     case TARGET_NR_brk:
5130         ret = do_brk(arg1);
5131         break;
5132     case TARGET_NR_fork:
5133         ret = get_errno(do_fork(cpu_env, SIGCHLD, 0, 0, 0, 0));
5134         break;
5135 #ifdef TARGET_NR_waitpid
5136     case TARGET_NR_waitpid:
5137         {
5138             int status;
5139             ret = get_errno(waitpid(arg1, &status, arg3));
5140             if (!is_error(ret) && arg2 && ret
5141                 && put_user_s32(host_to_target_waitstatus(status), arg2))
5142                 goto efault;
5143         }
5144         break;
5145 #endif
5146 #ifdef TARGET_NR_waitid
5147     case TARGET_NR_waitid:
5148         {
5149             siginfo_t info;
5150             info.si_pid = 0;
5151             ret = get_errno(waitid(arg1, arg2, &info, arg4));
5152             if (!is_error(ret) && arg3 && info.si_pid != 0) {
5153                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_siginfo_t), 0)))
5154                     goto efault;
5155                 host_to_target_siginfo(p, &info);
5156                 unlock_user(p, arg3, sizeof(target_siginfo_t));
5157             }
5158         }
5159         break;
5160 #endif
5161 #ifdef TARGET_NR_creat /* not on alpha */
5162     case TARGET_NR_creat:
5163         if (!(p = lock_user_string(arg1)))
5164             goto efault;
5165         ret = get_errno(creat(p, arg2));
5166         unlock_user(p, arg1, 0);
5167         break;
5168 #endif
5169     case TARGET_NR_link:
5170         {
5171             void * p2;
5172             p = lock_user_string(arg1);
5173             p2 = lock_user_string(arg2);
5174             if (!p || !p2)
5175                 ret = -TARGET_EFAULT;
5176             else
5177                 ret = get_errno(link(p, p2));
5178             unlock_user(p2, arg2, 0);
5179             unlock_user(p, arg1, 0);
5180         }
5181         break;
5182 #if defined(TARGET_NR_linkat)
5183     case TARGET_NR_linkat:
5184         {
5185             void * p2 = NULL;
5186             if (!arg2 || !arg4)
5187                 goto efault;
5188             p  = lock_user_string(arg2);
5189             p2 = lock_user_string(arg4);
5190             if (!p || !p2)
5191                 ret = -TARGET_EFAULT;
5192             else
5193                 ret = get_errno(linkat(arg1, p, arg3, p2, arg5));
5194             unlock_user(p, arg2, 0);
5195             unlock_user(p2, arg4, 0);
5196         }
5197         break;
5198 #endif
5199     case TARGET_NR_unlink:
5200         if (!(p = lock_user_string(arg1)))
5201             goto efault;
5202         ret = get_errno(unlink(p));
5203         unlock_user(p, arg1, 0);
5204         break;
5205 #if defined(TARGET_NR_unlinkat)
5206     case TARGET_NR_unlinkat:
5207         if (!(p = lock_user_string(arg2)))
5208             goto efault;
5209         ret = get_errno(unlinkat(arg1, p, arg3));
5210         unlock_user(p, arg2, 0);
5211         break;
5212 #endif
5213     case TARGET_NR_execve:
5214         {
5215             char **argp, **envp;
5216             int argc, envc;
5217             abi_ulong gp;
5218             abi_ulong guest_argp;
5219             abi_ulong guest_envp;
5220             abi_ulong addr;
5221             char **q;
5222             int total_size = 0;
5223 
5224             argc = 0;
5225             guest_argp = arg2;
5226             for (gp = guest_argp; gp; gp += sizeof(abi_ulong)) {
5227                 if (get_user_ual(addr, gp))
5228                     goto efault;
5229                 if (!addr)
5230                     break;
5231                 argc++;
5232             }
5233             envc = 0;
5234             guest_envp = arg3;
5235             for (gp = guest_envp; gp; gp += sizeof(abi_ulong)) {
5236                 if (get_user_ual(addr, gp))
5237                     goto efault;
5238                 if (!addr)
5239                     break;
5240                 envc++;
5241             }
5242 
5243             argp = alloca((argc + 1) * sizeof(void *));
5244             envp = alloca((envc + 1) * sizeof(void *));
5245 
5246             for (gp = guest_argp, q = argp; gp;
5247                   gp += sizeof(abi_ulong), q++) {
5248                 if (get_user_ual(addr, gp))
5249                     goto execve_efault;
5250                 if (!addr)
5251                     break;
5252                 if (!(*q = lock_user_string(addr)))
5253                     goto execve_efault;
5254                 total_size += strlen(*q) + 1;
5255             }
5256             *q = NULL;
5257 
5258             for (gp = guest_envp, q = envp; gp;
5259                   gp += sizeof(abi_ulong), q++) {
5260                 if (get_user_ual(addr, gp))
5261                     goto execve_efault;
5262                 if (!addr)
5263                     break;
5264                 if (!(*q = lock_user_string(addr)))
5265                     goto execve_efault;
5266                 total_size += strlen(*q) + 1;
5267             }
5268             *q = NULL;
5269 
5270             /* This case will not be caught by the host's execve() if its
5271                page size is bigger than the target's. */
5272             if (total_size > MAX_ARG_PAGES * TARGET_PAGE_SIZE) {
5273                 ret = -TARGET_E2BIG;
5274                 goto execve_end;
5275             }
5276             if (!(p = lock_user_string(arg1)))
5277                 goto execve_efault;
5278             ret = get_errno(execve(p, argp, envp));
5279             unlock_user(p, arg1, 0);
5280 
5281             goto execve_end;
5282 
5283         execve_efault:
5284             ret = -TARGET_EFAULT;
5285 
5286         execve_end:
5287             for (gp = guest_argp, q = argp; *q;
5288                   gp += sizeof(abi_ulong), q++) {
5289                 if (get_user_ual(addr, gp)
5290                     || !addr)
5291                     break;
5292                 unlock_user(*q, addr, 0);
5293             }
5294             for (gp = guest_envp, q = envp; *q;
5295                   gp += sizeof(abi_ulong), q++) {
5296                 if (get_user_ual(addr, gp)
5297                     || !addr)
5298                     break;
5299                 unlock_user(*q, addr, 0);
5300             }
5301         }
5302         break;
5303     case TARGET_NR_chdir:
5304         if (!(p = lock_user_string(arg1)))
5305             goto efault;
5306         ret = get_errno(chdir(p));
5307         unlock_user(p, arg1, 0);
5308         break;
5309 #ifdef TARGET_NR_time
5310     case TARGET_NR_time:
5311         {
5312             time_t host_time;
5313             ret = get_errno(time(&host_time));
5314             if (!is_error(ret)
5315                 && arg1
5316                 && put_user_sal(host_time, arg1))
5317                 goto efault;
5318         }
5319         break;
5320 #endif
5321     case TARGET_NR_mknod:
5322         if (!(p = lock_user_string(arg1)))
5323             goto efault;
5324         ret = get_errno(mknod(p, arg2, arg3));
5325         unlock_user(p, arg1, 0);
5326         break;
5327 #if defined(TARGET_NR_mknodat)
5328     case TARGET_NR_mknodat:
5329         if (!(p = lock_user_string(arg2)))
5330             goto efault;
5331         ret = get_errno(mknodat(arg1, p, arg3, arg4));
5332         unlock_user(p, arg2, 0);
5333         break;
5334 #endif
5335     case TARGET_NR_chmod:
5336         if (!(p = lock_user_string(arg1)))
5337             goto efault;
5338         ret = get_errno(chmod(p, arg2));
5339         unlock_user(p, arg1, 0);
5340         break;
5341 #ifdef TARGET_NR_break
5342     case TARGET_NR_break:
5343         goto unimplemented;
5344 #endif
5345 #ifdef TARGET_NR_oldstat
5346     case TARGET_NR_oldstat:
5347         goto unimplemented;
5348 #endif
5349     case TARGET_NR_lseek:
5350         ret = get_errno(lseek(arg1, arg2, arg3));
5351         break;
5352 #if defined(TARGET_NR_getxpid) && defined(TARGET_ALPHA)
5353     /* Alpha specific */
5354     case TARGET_NR_getxpid:
5355         ((CPUAlphaState *)cpu_env)->ir[IR_A4] = getppid();
5356         ret = get_errno(getpid());
5357         break;
5358 #endif
5359 #ifdef TARGET_NR_getpid
5360     case TARGET_NR_getpid:
5361         ret = get_errno(getpid());
5362         break;
5363 #endif
5364     case TARGET_NR_mount:
5365 		{
5366 			/* need to look at the data field */
5367 			void *p2, *p3;
5368 			p = lock_user_string(arg1);
5369 			p2 = lock_user_string(arg2);
5370 			p3 = lock_user_string(arg3);
5371                         if (!p || !p2 || !p3)
5372                             ret = -TARGET_EFAULT;
5373                         else {
5374                             /* FIXME - arg5 should be locked, but it isn't clear how to
5375                              * do that since it's not guaranteed to be a NULL-terminated
5376                              * string.
5377                              */
5378                             if ( ! arg5 )
5379                                 ret = get_errno(mount(p, p2, p3, (unsigned long)arg4, NULL));
5380                             else
5381                                 ret = get_errno(mount(p, p2, p3, (unsigned long)arg4, g2h(arg5)));
5382                         }
5383                         unlock_user(p, arg1, 0);
5384                         unlock_user(p2, arg2, 0);
5385                         unlock_user(p3, arg3, 0);
5386 			break;
5387 		}
5388 #ifdef TARGET_NR_umount
5389     case TARGET_NR_umount:
5390         if (!(p = lock_user_string(arg1)))
5391             goto efault;
5392         ret = get_errno(umount(p));
5393         unlock_user(p, arg1, 0);
5394         break;
5395 #endif
5396 #ifdef TARGET_NR_stime /* not on alpha */
5397     case TARGET_NR_stime:
5398         {
5399             time_t host_time;
5400             if (get_user_sal(host_time, arg1))
5401                 goto efault;
5402             ret = get_errno(stime(&host_time));
5403         }
5404         break;
5405 #endif
5406     case TARGET_NR_ptrace:
5407         goto unimplemented;
5408 #ifdef TARGET_NR_alarm /* not on alpha */
5409     case TARGET_NR_alarm:
5410         ret = alarm(arg1);
5411         break;
5412 #endif
5413 #ifdef TARGET_NR_oldfstat
5414     case TARGET_NR_oldfstat:
5415         goto unimplemented;
5416 #endif
5417 #ifdef TARGET_NR_pause /* not on alpha */
5418     case TARGET_NR_pause:
5419         ret = get_errno(pause());
5420         break;
5421 #endif
5422 #ifdef TARGET_NR_utime
5423     case TARGET_NR_utime:
5424         {
5425             struct utimbuf tbuf, *host_tbuf;
5426             struct target_utimbuf *target_tbuf;
5427             if (arg2) {
5428                 if (!lock_user_struct(VERIFY_READ, target_tbuf, arg2, 1))
5429                     goto efault;
5430                 tbuf.actime = tswapal(target_tbuf->actime);
5431                 tbuf.modtime = tswapal(target_tbuf->modtime);
5432                 unlock_user_struct(target_tbuf, arg2, 0);
5433                 host_tbuf = &tbuf;
5434             } else {
5435                 host_tbuf = NULL;
5436             }
5437             if (!(p = lock_user_string(arg1)))
5438                 goto efault;
5439             ret = get_errno(utime(p, host_tbuf));
5440             unlock_user(p, arg1, 0);
5441         }
5442         break;
5443 #endif
5444     case TARGET_NR_utimes:
5445         {
5446             struct timeval *tvp, tv[2];
5447             if (arg2) {
5448                 if (copy_from_user_timeval(&tv[0], arg2)
5449                     || copy_from_user_timeval(&tv[1],
5450                                               arg2 + sizeof(struct target_timeval)))
5451                     goto efault;
5452                 tvp = tv;
5453             } else {
5454                 tvp = NULL;
5455             }
5456             if (!(p = lock_user_string(arg1)))
5457                 goto efault;
5458             ret = get_errno(utimes(p, tvp));
5459             unlock_user(p, arg1, 0);
5460         }
5461         break;
5462 #if defined(TARGET_NR_futimesat)
5463     case TARGET_NR_futimesat:
5464         {
5465             struct timeval *tvp, tv[2];
5466             if (arg3) {
5467                 if (copy_from_user_timeval(&tv[0], arg3)
5468                     || copy_from_user_timeval(&tv[1],
5469                                               arg3 + sizeof(struct target_timeval)))
5470                     goto efault;
5471                 tvp = tv;
5472             } else {
5473                 tvp = NULL;
5474             }
5475             if (!(p = lock_user_string(arg2)))
5476                 goto efault;
5477             ret = get_errno(futimesat(arg1, path(p), tvp));
5478             unlock_user(p, arg2, 0);
5479         }
5480         break;
5481 #endif
5482 #ifdef TARGET_NR_stty
5483     case TARGET_NR_stty:
5484         goto unimplemented;
5485 #endif
5486 #ifdef TARGET_NR_gtty
5487     case TARGET_NR_gtty:
5488         goto unimplemented;
5489 #endif
5490     case TARGET_NR_access:
5491         if (!(p = lock_user_string(arg1)))
5492             goto efault;
5493         ret = get_errno(access(path(p), arg2));
5494         unlock_user(p, arg1, 0);
5495         break;
5496 #if defined(TARGET_NR_faccessat) && defined(__NR_faccessat)
5497     case TARGET_NR_faccessat:
5498         if (!(p = lock_user_string(arg2)))
5499             goto efault;
5500         ret = get_errno(faccessat(arg1, p, arg3, 0));
5501         unlock_user(p, arg2, 0);
5502         break;
5503 #endif
5504 #ifdef TARGET_NR_nice /* not on alpha */
5505     case TARGET_NR_nice:
5506         ret = get_errno(nice(arg1));
5507         break;
5508 #endif
5509 #ifdef TARGET_NR_ftime
5510     case TARGET_NR_ftime:
5511         goto unimplemented;
5512 #endif
5513     case TARGET_NR_sync:
5514         sync();
5515         ret = 0;
5516         break;
5517     case TARGET_NR_kill:
5518         ret = get_errno(kill(arg1, target_to_host_signal(arg2)));
5519         break;
5520     case TARGET_NR_rename:
5521         {
5522             void *p2;
5523             p = lock_user_string(arg1);
5524             p2 = lock_user_string(arg2);
5525             if (!p || !p2)
5526                 ret = -TARGET_EFAULT;
5527             else
5528                 ret = get_errno(rename(p, p2));
5529             unlock_user(p2, arg2, 0);
5530             unlock_user(p, arg1, 0);
5531         }
5532         break;
5533 #if defined(TARGET_NR_renameat)
5534     case TARGET_NR_renameat:
5535         {
5536             void *p2;
5537             p  = lock_user_string(arg2);
5538             p2 = lock_user_string(arg4);
5539             if (!p || !p2)
5540                 ret = -TARGET_EFAULT;
5541             else
5542                 ret = get_errno(renameat(arg1, p, arg3, p2));
5543             unlock_user(p2, arg4, 0);
5544             unlock_user(p, arg2, 0);
5545         }
5546         break;
5547 #endif
5548     case TARGET_NR_mkdir:
5549         if (!(p = lock_user_string(arg1)))
5550             goto efault;
5551         ret = get_errno(mkdir(p, arg2));
5552         unlock_user(p, arg1, 0);
5553         break;
5554 #if defined(TARGET_NR_mkdirat)
5555     case TARGET_NR_mkdirat:
5556         if (!(p = lock_user_string(arg2)))
5557             goto efault;
5558         ret = get_errno(mkdirat(arg1, p, arg3));
5559         unlock_user(p, arg2, 0);
5560         break;
5561 #endif
5562     case TARGET_NR_rmdir:
5563         if (!(p = lock_user_string(arg1)))
5564             goto efault;
5565         ret = get_errno(rmdir(p));
5566         unlock_user(p, arg1, 0);
5567         break;
5568     case TARGET_NR_dup:
5569         ret = get_errno(dup(arg1));
5570         break;
5571     case TARGET_NR_pipe:
5572         ret = do_pipe(cpu_env, arg1, 0, 0);
5573         break;
5574 #ifdef TARGET_NR_pipe2
5575     case TARGET_NR_pipe2:
5576         ret = do_pipe(cpu_env, arg1,
5577                       target_to_host_bitmask(arg2, fcntl_flags_tbl), 1);
5578         break;
5579 #endif
5580     case TARGET_NR_times:
5581         {
5582             struct target_tms *tmsp;
5583             struct tms tms;
5584             ret = get_errno(times(&tms));
5585             if (arg1) {
5586                 tmsp = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_tms), 0);
5587                 if (!tmsp)
5588                     goto efault;
5589                 tmsp->tms_utime = tswapal(host_to_target_clock_t(tms.tms_utime));
5590                 tmsp->tms_stime = tswapal(host_to_target_clock_t(tms.tms_stime));
5591                 tmsp->tms_cutime = tswapal(host_to_target_clock_t(tms.tms_cutime));
5592                 tmsp->tms_cstime = tswapal(host_to_target_clock_t(tms.tms_cstime));
5593             }
5594             if (!is_error(ret))
5595                 ret = host_to_target_clock_t(ret);
5596         }
5597         break;
5598 #ifdef TARGET_NR_prof
5599     case TARGET_NR_prof:
5600         goto unimplemented;
5601 #endif
5602 #ifdef TARGET_NR_signal
5603     case TARGET_NR_signal:
5604         goto unimplemented;
5605 #endif
5606     case TARGET_NR_acct:
5607         if (arg1 == 0) {
5608             ret = get_errno(acct(NULL));
5609         } else {
5610             if (!(p = lock_user_string(arg1)))
5611                 goto efault;
5612             ret = get_errno(acct(path(p)));
5613             unlock_user(p, arg1, 0);
5614         }
5615         break;
5616 #ifdef TARGET_NR_umount2 /* not on alpha */
5617     case TARGET_NR_umount2:
5618         if (!(p = lock_user_string(arg1)))
5619             goto efault;
5620         ret = get_errno(umount2(p, arg2));
5621         unlock_user(p, arg1, 0);
5622         break;
5623 #endif
5624 #ifdef TARGET_NR_lock
5625     case TARGET_NR_lock:
5626         goto unimplemented;
5627 #endif
5628     case TARGET_NR_ioctl:
5629         ret = do_ioctl(arg1, arg2, arg3);
5630         break;
5631     case TARGET_NR_fcntl:
5632         ret = do_fcntl(arg1, arg2, arg3);
5633         break;
5634 #ifdef TARGET_NR_mpx
5635     case TARGET_NR_mpx:
5636         goto unimplemented;
5637 #endif
5638     case TARGET_NR_setpgid:
5639         ret = get_errno(setpgid(arg1, arg2));
5640         break;
5641 #ifdef TARGET_NR_ulimit
5642     case TARGET_NR_ulimit:
5643         goto unimplemented;
5644 #endif
5645 #ifdef TARGET_NR_oldolduname
5646     case TARGET_NR_oldolduname:
5647         goto unimplemented;
5648 #endif
5649     case TARGET_NR_umask:
5650         ret = get_errno(umask(arg1));
5651         break;
5652     case TARGET_NR_chroot:
5653         if (!(p = lock_user_string(arg1)))
5654             goto efault;
5655         ret = get_errno(chroot(p));
5656         unlock_user(p, arg1, 0);
5657         break;
5658     case TARGET_NR_ustat:
5659         goto unimplemented;
5660     case TARGET_NR_dup2:
5661         ret = get_errno(dup2(arg1, arg2));
5662         break;
5663 #if defined(CONFIG_DUP3) && defined(TARGET_NR_dup3)
5664     case TARGET_NR_dup3:
5665         ret = get_errno(dup3(arg1, arg2, arg3));
5666         break;
5667 #endif
5668 #ifdef TARGET_NR_getppid /* not on alpha */
5669     case TARGET_NR_getppid:
5670         ret = get_errno(getppid());
5671         break;
5672 #endif
5673     case TARGET_NR_getpgrp:
5674         ret = get_errno(getpgrp());
5675         break;
5676     case TARGET_NR_setsid:
5677         ret = get_errno(setsid());
5678         break;
5679 #ifdef TARGET_NR_sigaction
5680     case TARGET_NR_sigaction:
5681         {
5682 #if defined(TARGET_ALPHA)
5683             struct target_sigaction act, oact, *pact = 0;
5684             struct target_old_sigaction *old_act;
5685             if (arg2) {
5686                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5687                     goto efault;
5688                 act._sa_handler = old_act->_sa_handler;
5689                 target_siginitset(&act.sa_mask, old_act->sa_mask);
5690                 act.sa_flags = old_act->sa_flags;
5691                 act.sa_restorer = 0;
5692                 unlock_user_struct(old_act, arg2, 0);
5693                 pact = &act;
5694             }
5695             ret = get_errno(do_sigaction(arg1, pact, &oact));
5696             if (!is_error(ret) && arg3) {
5697                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5698                     goto efault;
5699                 old_act->_sa_handler = oact._sa_handler;
5700                 old_act->sa_mask = oact.sa_mask.sig[0];
5701                 old_act->sa_flags = oact.sa_flags;
5702                 unlock_user_struct(old_act, arg3, 1);
5703             }
5704 #elif defined(TARGET_MIPS)
5705 	    struct target_sigaction act, oact, *pact, *old_act;
5706 
5707 	    if (arg2) {
5708                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5709                     goto efault;
5710 		act._sa_handler = old_act->_sa_handler;
5711 		target_siginitset(&act.sa_mask, old_act->sa_mask.sig[0]);
5712 		act.sa_flags = old_act->sa_flags;
5713 		unlock_user_struct(old_act, arg2, 0);
5714 		pact = &act;
5715 	    } else {
5716 		pact = NULL;
5717 	    }
5718 
5719 	    ret = get_errno(do_sigaction(arg1, pact, &oact));
5720 
5721 	    if (!is_error(ret) && arg3) {
5722                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5723                     goto efault;
5724 		old_act->_sa_handler = oact._sa_handler;
5725 		old_act->sa_flags = oact.sa_flags;
5726 		old_act->sa_mask.sig[0] = oact.sa_mask.sig[0];
5727 		old_act->sa_mask.sig[1] = 0;
5728 		old_act->sa_mask.sig[2] = 0;
5729 		old_act->sa_mask.sig[3] = 0;
5730 		unlock_user_struct(old_act, arg3, 1);
5731 	    }
5732 #else
5733             struct target_old_sigaction *old_act;
5734             struct target_sigaction act, oact, *pact;
5735             if (arg2) {
5736                 if (!lock_user_struct(VERIFY_READ, old_act, arg2, 1))
5737                     goto efault;
5738                 act._sa_handler = old_act->_sa_handler;
5739                 target_siginitset(&act.sa_mask, old_act->sa_mask);
5740                 act.sa_flags = old_act->sa_flags;
5741                 act.sa_restorer = old_act->sa_restorer;
5742                 unlock_user_struct(old_act, arg2, 0);
5743                 pact = &act;
5744             } else {
5745                 pact = NULL;
5746             }
5747             ret = get_errno(do_sigaction(arg1, pact, &oact));
5748             if (!is_error(ret) && arg3) {
5749                 if (!lock_user_struct(VERIFY_WRITE, old_act, arg3, 0))
5750                     goto efault;
5751                 old_act->_sa_handler = oact._sa_handler;
5752                 old_act->sa_mask = oact.sa_mask.sig[0];
5753                 old_act->sa_flags = oact.sa_flags;
5754                 old_act->sa_restorer = oact.sa_restorer;
5755                 unlock_user_struct(old_act, arg3, 1);
5756             }
5757 #endif
5758         }
5759         break;
5760 #endif
5761     case TARGET_NR_rt_sigaction:
5762         {
5763 #if defined(TARGET_ALPHA)
5764             struct target_sigaction act, oact, *pact = 0;
5765             struct target_rt_sigaction *rt_act;
5766             /* ??? arg4 == sizeof(sigset_t).  */
5767             if (arg2) {
5768                 if (!lock_user_struct(VERIFY_READ, rt_act, arg2, 1))
5769                     goto efault;
5770                 act._sa_handler = rt_act->_sa_handler;
5771                 act.sa_mask = rt_act->sa_mask;
5772                 act.sa_flags = rt_act->sa_flags;
5773                 act.sa_restorer = arg5;
5774                 unlock_user_struct(rt_act, arg2, 0);
5775                 pact = &act;
5776             }
5777             ret = get_errno(do_sigaction(arg1, pact, &oact));
5778             if (!is_error(ret) && arg3) {
5779                 if (!lock_user_struct(VERIFY_WRITE, rt_act, arg3, 0))
5780                     goto efault;
5781                 rt_act->_sa_handler = oact._sa_handler;
5782                 rt_act->sa_mask = oact.sa_mask;
5783                 rt_act->sa_flags = oact.sa_flags;
5784                 unlock_user_struct(rt_act, arg3, 1);
5785             }
5786 #else
5787             struct target_sigaction *act;
5788             struct target_sigaction *oact;
5789 
5790             if (arg2) {
5791                 if (!lock_user_struct(VERIFY_READ, act, arg2, 1))
5792                     goto efault;
5793             } else
5794                 act = NULL;
5795             if (arg3) {
5796                 if (!lock_user_struct(VERIFY_WRITE, oact, arg3, 0)) {
5797                     ret = -TARGET_EFAULT;
5798                     goto rt_sigaction_fail;
5799                 }
5800             } else
5801                 oact = NULL;
5802             ret = get_errno(do_sigaction(arg1, act, oact));
5803 	rt_sigaction_fail:
5804             if (act)
5805                 unlock_user_struct(act, arg2, 0);
5806             if (oact)
5807                 unlock_user_struct(oact, arg3, 1);
5808 #endif
5809         }
5810         break;
5811 #ifdef TARGET_NR_sgetmask /* not on alpha */
5812     case TARGET_NR_sgetmask:
5813         {
5814             sigset_t cur_set;
5815             abi_ulong target_set;
5816             sigprocmask(0, NULL, &cur_set);
5817             host_to_target_old_sigset(&target_set, &cur_set);
5818             ret = target_set;
5819         }
5820         break;
5821 #endif
5822 #ifdef TARGET_NR_ssetmask /* not on alpha */
5823     case TARGET_NR_ssetmask:
5824         {
5825             sigset_t set, oset, cur_set;
5826             abi_ulong target_set = arg1;
5827             sigprocmask(0, NULL, &cur_set);
5828             target_to_host_old_sigset(&set, &target_set);
5829             sigorset(&set, &set, &cur_set);
5830             sigprocmask(SIG_SETMASK, &set, &oset);
5831             host_to_target_old_sigset(&target_set, &oset);
5832             ret = target_set;
5833         }
5834         break;
5835 #endif
5836 #ifdef TARGET_NR_sigprocmask
5837     case TARGET_NR_sigprocmask:
5838         {
5839 #if defined(TARGET_ALPHA)
5840             sigset_t set, oldset;
5841             abi_ulong mask;
5842             int how;
5843 
5844             switch (arg1) {
5845             case TARGET_SIG_BLOCK:
5846                 how = SIG_BLOCK;
5847                 break;
5848             case TARGET_SIG_UNBLOCK:
5849                 how = SIG_UNBLOCK;
5850                 break;
5851             case TARGET_SIG_SETMASK:
5852                 how = SIG_SETMASK;
5853                 break;
5854             default:
5855                 ret = -TARGET_EINVAL;
5856                 goto fail;
5857             }
5858             mask = arg2;
5859             target_to_host_old_sigset(&set, &mask);
5860 
5861             ret = get_errno(sigprocmask(how, &set, &oldset));
5862             if (!is_error(ret)) {
5863                 host_to_target_old_sigset(&mask, &oldset);
5864                 ret = mask;
5865                 ((CPUAlphaState *)cpu_env)->ir[IR_V0] = 0; /* force no error */
5866             }
5867 #else
5868             sigset_t set, oldset, *set_ptr;
5869             int how;
5870 
5871             if (arg2) {
5872                 switch (arg1) {
5873                 case TARGET_SIG_BLOCK:
5874                     how = SIG_BLOCK;
5875                     break;
5876                 case TARGET_SIG_UNBLOCK:
5877                     how = SIG_UNBLOCK;
5878                     break;
5879                 case TARGET_SIG_SETMASK:
5880                     how = SIG_SETMASK;
5881                     break;
5882                 default:
5883                     ret = -TARGET_EINVAL;
5884                     goto fail;
5885                 }
5886                 if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
5887                     goto efault;
5888                 target_to_host_old_sigset(&set, p);
5889                 unlock_user(p, arg2, 0);
5890                 set_ptr = &set;
5891             } else {
5892                 how = 0;
5893                 set_ptr = NULL;
5894             }
5895             ret = get_errno(sigprocmask(how, set_ptr, &oldset));
5896             if (!is_error(ret) && arg3) {
5897                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
5898                     goto efault;
5899                 host_to_target_old_sigset(p, &oldset);
5900                 unlock_user(p, arg3, sizeof(target_sigset_t));
5901             }
5902 #endif
5903         }
5904         break;
5905 #endif
5906     case TARGET_NR_rt_sigprocmask:
5907         {
5908             int how = arg1;
5909             sigset_t set, oldset, *set_ptr;
5910 
5911             if (arg2) {
5912                 switch(how) {
5913                 case TARGET_SIG_BLOCK:
5914                     how = SIG_BLOCK;
5915                     break;
5916                 case TARGET_SIG_UNBLOCK:
5917                     how = SIG_UNBLOCK;
5918                     break;
5919                 case TARGET_SIG_SETMASK:
5920                     how = SIG_SETMASK;
5921                     break;
5922                 default:
5923                     ret = -TARGET_EINVAL;
5924                     goto fail;
5925                 }
5926                 if (!(p = lock_user(VERIFY_READ, arg2, sizeof(target_sigset_t), 1)))
5927                     goto efault;
5928                 target_to_host_sigset(&set, p);
5929                 unlock_user(p, arg2, 0);
5930                 set_ptr = &set;
5931             } else {
5932                 how = 0;
5933                 set_ptr = NULL;
5934             }
5935             ret = get_errno(sigprocmask(how, set_ptr, &oldset));
5936             if (!is_error(ret) && arg3) {
5937                 if (!(p = lock_user(VERIFY_WRITE, arg3, sizeof(target_sigset_t), 0)))
5938                     goto efault;
5939                 host_to_target_sigset(p, &oldset);
5940                 unlock_user(p, arg3, sizeof(target_sigset_t));
5941             }
5942         }
5943         break;
5944 #ifdef TARGET_NR_sigpending
5945     case TARGET_NR_sigpending:
5946         {
5947             sigset_t set;
5948             ret = get_errno(sigpending(&set));
5949             if (!is_error(ret)) {
5950                 if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
5951                     goto efault;
5952                 host_to_target_old_sigset(p, &set);
5953                 unlock_user(p, arg1, sizeof(target_sigset_t));
5954             }
5955         }
5956         break;
5957 #endif
5958     case TARGET_NR_rt_sigpending:
5959         {
5960             sigset_t set;
5961             ret = get_errno(sigpending(&set));
5962             if (!is_error(ret)) {
5963                 if (!(p = lock_user(VERIFY_WRITE, arg1, sizeof(target_sigset_t), 0)))
5964                     goto efault;
5965                 host_to_target_sigset(p, &set);
5966                 unlock_user(p, arg1, sizeof(target_sigset_t));
5967             }
5968         }
5969         break;
5970 #ifdef TARGET_NR_sigsuspend
5971     case TARGET_NR_sigsuspend:
5972         {
5973             sigset_t set;
5974 #if defined(TARGET_ALPHA)
5975             abi_ulong mask = arg1;
5976             target_to_host_old_sigset(&set, &mask);
5977 #else
5978             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
5979                 goto efault;
5980             target_to_host_old_sigset(&set, p);
5981             unlock_user(p, arg1, 0);
5982 #endif
5983             ret = get_errno(sigsuspend(&set));
5984         }
5985         break;
5986 #endif
5987     case TARGET_NR_rt_sigsuspend:
5988         {
5989             sigset_t set;
5990             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
5991                 goto efault;
5992             target_to_host_sigset(&set, p);
5993             unlock_user(p, arg1, 0);
5994             ret = get_errno(sigsuspend(&set));
5995         }
5996         break;
5997     case TARGET_NR_rt_sigtimedwait:
5998         {
5999             sigset_t set;
6000             struct timespec uts, *puts;
6001             siginfo_t uinfo;
6002 
6003             if (!(p = lock_user(VERIFY_READ, arg1, sizeof(target_sigset_t), 1)))
6004                 goto efault;
6005             target_to_host_sigset(&set, p);
6006             unlock_user(p, arg1, 0);
6007             if (arg3) {
6008                 puts = &uts;
6009                 target_to_host_timespec(puts, arg3);
6010             } else {
6011                 puts = NULL;
6012             }
6013             ret = get_errno(sigtimedwait(&set, &uinfo, puts));
6014             if (!is_error(ret) && arg2) {
6015                 if (!(p = lock_user(VERIFY_WRITE, arg2, sizeof(target_siginfo_t), 0)))
6016                     goto efault;
6017                 host_to_target_siginfo(p, &uinfo);
6018                 unlock_user(p, arg2, sizeof(target_siginfo_t));
6019             }
6020         }
6021         break;
6022     case TARGET_NR_rt_sigqueueinfo:
6023         {
6024             siginfo_t uinfo;
6025             if (!(p = lock_user(VERIFY_READ, arg3, sizeof(target_sigset_t), 1)))
6026                 goto efault;
6027             target_to_host_siginfo(&uinfo, p);
6028             unlock_user(p, arg1, 0);
6029             ret = get_errno(sys_rt_sigqueueinfo(arg1, arg2, &uinfo));
6030         }
6031         break;
6032 #ifdef TARGET_NR_sigreturn
6033     case TARGET_NR_sigreturn:
6034         /* NOTE: ret is eax, so not transcoding must be done */
6035         ret = do_sigreturn(cpu_env);
6036         break;
6037 #endif
6038     case TARGET_NR_rt_sigreturn:
6039         /* NOTE: ret is eax, so not transcoding must be done */
6040         ret = do_rt_sigreturn(cpu_env);
6041         break;
6042     case TARGET_NR_sethostname:
6043         if (!(p = lock_user_string(arg1)))
6044             goto efault;
6045         ret = get_errno(sethostname(p, arg2));
6046         unlock_user(p, arg1, 0);
6047         break;
6048     case TARGET_NR_setrlimit:
6049         {
6050             int resource = target_to_host_resource(arg1);
6051             struct target_rlimit *target_rlim;
6052             struct rlimit rlim;
6053             if (!lock_user_struct(VERIFY_READ, target_rlim, arg2, 1))
6054                 goto efault;
6055             rlim.rlim_cur = target_to_host_rlim(target_rlim->rlim_cur);
6056             rlim.rlim_max = target_to_host_rlim(target_rlim->rlim_max);
6057             unlock_user_struct(target_rlim, arg2, 0);
6058             ret = get_errno(setrlimit(resource, &rlim));
6059         }
6060         break;
6061     case TARGET_NR_getrlimit:
6062         {
6063             int resource = target_to_host_resource(arg1);
6064             struct target_rlimit *target_rlim;
6065             struct rlimit rlim;
6066 
6067             ret = get_errno(getrlimit(resource, &rlim));
6068             if (!is_error(ret)) {
6069                 if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
6070                     goto efault;
6071                 target_rlim->rlim_cur = host_to_target_rlim(rlim.rlim_cur);
6072                 target_rlim->rlim_max = host_to_target_rlim(rlim.rlim_max);
6073                 unlock_user_struct(target_rlim, arg2, 1);
6074             }
6075         }
6076         break;
6077     case TARGET_NR_getrusage:
6078         {
6079             struct rusage rusage;
6080             ret = get_errno(getrusage(arg1, &rusage));
6081             if (!is_error(ret)) {
6082                 host_to_target_rusage(arg2, &rusage);
6083             }
6084         }
6085         break;
6086     case TARGET_NR_gettimeofday:
6087         {
6088             struct timeval tv;
6089             ret = get_errno(gettimeofday(&tv, NULL));
6090             if (!is_error(ret)) {
6091                 if (copy_to_user_timeval(arg1, &tv))
6092                     goto efault;
6093             }
6094         }
6095         break;
6096     case TARGET_NR_settimeofday:
6097         {
6098             struct timeval tv;
6099             if (copy_from_user_timeval(&tv, arg1))
6100                 goto efault;
6101             ret = get_errno(settimeofday(&tv, NULL));
6102         }
6103         break;
6104 #if defined(TARGET_NR_select)
6105     case TARGET_NR_select:
6106 #if defined(TARGET_S390X) || defined(TARGET_ALPHA)
6107         ret = do_select(arg1, arg2, arg3, arg4, arg5);
6108 #else
6109         {
6110             struct target_sel_arg_struct *sel;
6111             abi_ulong inp, outp, exp, tvp;
6112             long nsel;
6113 
6114             if (!lock_user_struct(VERIFY_READ, sel, arg1, 1))
6115                 goto efault;
6116             nsel = tswapal(sel->n);
6117             inp = tswapal(sel->inp);
6118             outp = tswapal(sel->outp);
6119             exp = tswapal(sel->exp);
6120             tvp = tswapal(sel->tvp);
6121             unlock_user_struct(sel, arg1, 0);
6122             ret = do_select(nsel, inp, outp, exp, tvp);
6123         }
6124 #endif
6125         break;
6126 #endif
6127 #ifdef TARGET_NR_pselect6
6128     case TARGET_NR_pselect6:
6129         {
6130             abi_long rfd_addr, wfd_addr, efd_addr, n, ts_addr;
6131             fd_set rfds, wfds, efds;
6132             fd_set *rfds_ptr, *wfds_ptr, *efds_ptr;
6133             struct timespec ts, *ts_ptr;
6134 
6135             /*
6136              * The 6th arg is actually two args smashed together,
6137              * so we cannot use the C library.
6138              */
6139             sigset_t set;
6140             struct {
6141                 sigset_t *set;
6142                 size_t size;
6143             } sig, *sig_ptr;
6144 
6145             abi_ulong arg_sigset, arg_sigsize, *arg7;
6146             target_sigset_t *target_sigset;
6147 
6148             n = arg1;
6149             rfd_addr = arg2;
6150             wfd_addr = arg3;
6151             efd_addr = arg4;
6152             ts_addr = arg5;
6153 
6154             ret = copy_from_user_fdset_ptr(&rfds, &rfds_ptr, rfd_addr, n);
6155             if (ret) {
6156                 goto fail;
6157             }
6158             ret = copy_from_user_fdset_ptr(&wfds, &wfds_ptr, wfd_addr, n);
6159             if (ret) {
6160                 goto fail;
6161             }
6162             ret = copy_from_user_fdset_ptr(&efds, &efds_ptr, efd_addr, n);
6163             if (ret) {
6164                 goto fail;
6165             }
6166 
6167             /*
6168              * This takes a timespec, and not a timeval, so we cannot
6169              * use the do_select() helper ...
6170              */
6171             if (ts_addr) {
6172                 if (target_to_host_timespec(&ts, ts_addr)) {
6173                     goto efault;
6174                 }
6175                 ts_ptr = &ts;
6176             } else {
6177                 ts_ptr = NULL;
6178             }
6179 
6180             /* Extract the two packed args for the sigset */
6181             if (arg6) {
6182                 sig_ptr = &sig;
6183                 sig.size = _NSIG / 8;
6184 
6185                 arg7 = lock_user(VERIFY_READ, arg6, sizeof(*arg7) * 2, 1);
6186                 if (!arg7) {
6187                     goto efault;
6188                 }
6189                 arg_sigset = tswapal(arg7[0]);
6190                 arg_sigsize = tswapal(arg7[1]);
6191                 unlock_user(arg7, arg6, 0);
6192 
6193                 if (arg_sigset) {
6194                     sig.set = &set;
6195                     if (arg_sigsize != sizeof(*target_sigset)) {
6196                         /* Like the kernel, we enforce correct size sigsets */
6197                         ret = -TARGET_EINVAL;
6198                         goto fail;
6199                     }
6200                     target_sigset = lock_user(VERIFY_READ, arg_sigset,
6201                                               sizeof(*target_sigset), 1);
6202                     if (!target_sigset) {
6203                         goto efault;
6204                     }
6205                     target_to_host_sigset(&set, target_sigset);
6206                     unlock_user(target_sigset, arg_sigset, 0);
6207                 } else {
6208                     sig.set = NULL;
6209                 }
6210             } else {
6211                 sig_ptr = NULL;
6212             }
6213 
6214             ret = get_errno(sys_pselect6(n, rfds_ptr, wfds_ptr, efds_ptr,
6215                                          ts_ptr, sig_ptr));
6216 
6217             if (!is_error(ret)) {
6218                 if (rfd_addr && copy_to_user_fdset(rfd_addr, &rfds, n))
6219                     goto efault;
6220                 if (wfd_addr && copy_to_user_fdset(wfd_addr, &wfds, n))
6221                     goto efault;
6222                 if (efd_addr && copy_to_user_fdset(efd_addr, &efds, n))
6223                     goto efault;
6224 
6225                 if (ts_addr && host_to_target_timespec(ts_addr, &ts))
6226                     goto efault;
6227             }
6228         }
6229         break;
6230 #endif
6231     case TARGET_NR_symlink:
6232         {
6233             void *p2;
6234             p = lock_user_string(arg1);
6235             p2 = lock_user_string(arg2);
6236             if (!p || !p2)
6237                 ret = -TARGET_EFAULT;
6238             else
6239                 ret = get_errno(symlink(p, p2));
6240             unlock_user(p2, arg2, 0);
6241             unlock_user(p, arg1, 0);
6242         }
6243         break;
6244 #if defined(TARGET_NR_symlinkat)
6245     case TARGET_NR_symlinkat:
6246         {
6247             void *p2;
6248             p  = lock_user_string(arg1);
6249             p2 = lock_user_string(arg3);
6250             if (!p || !p2)
6251                 ret = -TARGET_EFAULT;
6252             else
6253                 ret = get_errno(symlinkat(p, arg2, p2));
6254             unlock_user(p2, arg3, 0);
6255             unlock_user(p, arg1, 0);
6256         }
6257         break;
6258 #endif
6259 #ifdef TARGET_NR_oldlstat
6260     case TARGET_NR_oldlstat:
6261         goto unimplemented;
6262 #endif
6263     case TARGET_NR_readlink:
6264         {
6265             void *p2, *temp;
6266             p = lock_user_string(arg1);
6267             p2 = lock_user(VERIFY_WRITE, arg2, arg3, 0);
6268             if (!p || !p2)
6269                 ret = -TARGET_EFAULT;
6270             else {
6271                 if (strncmp((const char *)p, "/proc/self/exe", 14) == 0) {
6272                     char real[PATH_MAX];
6273                     temp = realpath(exec_path,real);
6274                     ret = (temp==NULL) ? get_errno(-1) : strlen(real) ;
6275                     snprintf((char *)p2, arg3, "%s", real);
6276                     }
6277                 else
6278                     ret = get_errno(readlink(path(p), p2, arg3));
6279             }
6280             unlock_user(p2, arg2, ret);
6281             unlock_user(p, arg1, 0);
6282         }
6283         break;
6284 #if defined(TARGET_NR_readlinkat)
6285     case TARGET_NR_readlinkat:
6286         {
6287             void *p2;
6288             p  = lock_user_string(arg2);
6289             p2 = lock_user(VERIFY_WRITE, arg3, arg4, 0);
6290             if (!p || !p2)
6291         	ret = -TARGET_EFAULT;
6292             else
6293                 ret = get_errno(readlinkat(arg1, path(p), p2, arg4));
6294             unlock_user(p2, arg3, ret);
6295             unlock_user(p, arg2, 0);
6296         }
6297         break;
6298 #endif
6299 #ifdef TARGET_NR_uselib
6300     case TARGET_NR_uselib:
6301         goto unimplemented;
6302 #endif
6303 #ifdef TARGET_NR_swapon
6304     case TARGET_NR_swapon:
6305         if (!(p = lock_user_string(arg1)))
6306             goto efault;
6307         ret = get_errno(swapon(p, arg2));
6308         unlock_user(p, arg1, 0);
6309         break;
6310 #endif
6311     case TARGET_NR_reboot:
6312         if (arg3 == LINUX_REBOOT_CMD_RESTART2) {
6313            /* arg4 must be ignored in all other cases */
6314            p = lock_user_string(arg4);
6315            if (!p) {
6316               goto efault;
6317            }
6318            ret = get_errno(reboot(arg1, arg2, arg3, p));
6319            unlock_user(p, arg4, 0);
6320         } else {
6321            ret = get_errno(reboot(arg1, arg2, arg3, NULL));
6322         }
6323         break;
6324 #ifdef TARGET_NR_readdir
6325     case TARGET_NR_readdir:
6326         goto unimplemented;
6327 #endif
6328 #ifdef TARGET_NR_mmap
6329     case TARGET_NR_mmap:
6330 #if (defined(TARGET_I386) && defined(TARGET_ABI32)) || defined(TARGET_ARM) || \
6331     defined(TARGET_M68K) || defined(TARGET_CRIS) || defined(TARGET_MICROBLAZE) \
6332     || defined(TARGET_S390X)
6333         {
6334             abi_ulong *v;
6335             abi_ulong v1, v2, v3, v4, v5, v6;
6336             if (!(v = lock_user(VERIFY_READ, arg1, 6 * sizeof(abi_ulong), 1)))
6337                 goto efault;
6338             v1 = tswapal(v[0]);
6339             v2 = tswapal(v[1]);
6340             v3 = tswapal(v[2]);
6341             v4 = tswapal(v[3]);
6342             v5 = tswapal(v[4]);
6343             v6 = tswapal(v[5]);
6344             unlock_user(v, arg1, 0);
6345             ret = get_errno(target_mmap(v1, v2, v3,
6346                                         target_to_host_bitmask(v4, mmap_flags_tbl),
6347                                         v5, v6));
6348         }
6349 #else
6350         ret = get_errno(target_mmap(arg1, arg2, arg3,
6351                                     target_to_host_bitmask(arg4, mmap_flags_tbl),
6352                                     arg5,
6353                                     arg6));
6354 #endif
6355         break;
6356 #endif
6357 #ifdef TARGET_NR_mmap2
6358     case TARGET_NR_mmap2:
6359 #ifndef MMAP_SHIFT
6360 #define MMAP_SHIFT 12
6361 #endif
6362         ret = get_errno(target_mmap(arg1, arg2, arg3,
6363                                     target_to_host_bitmask(arg4, mmap_flags_tbl),
6364                                     arg5,
6365                                     arg6 << MMAP_SHIFT));
6366         break;
6367 #endif
6368     case TARGET_NR_munmap:
6369         ret = get_errno(target_munmap(arg1, arg2));
6370         break;
6371     case TARGET_NR_mprotect:
6372         {
6373             TaskState *ts = ((CPUArchState *)cpu_env)->opaque;
6374             /* Special hack to detect libc making the stack executable.  */
6375             if ((arg3 & PROT_GROWSDOWN)
6376                 && arg1 >= ts->info->stack_limit
6377                 && arg1 <= ts->info->start_stack) {
6378                 arg3 &= ~PROT_GROWSDOWN;
6379                 arg2 = arg2 + arg1 - ts->info->stack_limit;
6380                 arg1 = ts->info->stack_limit;
6381             }
6382         }
6383         ret = get_errno(target_mprotect(arg1, arg2, arg3));
6384         break;
6385 #ifdef TARGET_NR_mremap
6386     case TARGET_NR_mremap:
6387         ret = get_errno(target_mremap(arg1, arg2, arg3, arg4, arg5));
6388         break;
6389 #endif
6390         /* ??? msync/mlock/munlock are broken for softmmu.  */
6391 #ifdef TARGET_NR_msync
6392     case TARGET_NR_msync:
6393         ret = get_errno(msync(g2h(arg1), arg2, arg3));
6394         break;
6395 #endif
6396 #ifdef TARGET_NR_mlock
6397     case TARGET_NR_mlock:
6398         ret = get_errno(mlock(g2h(arg1), arg2));
6399         break;
6400 #endif
6401 #ifdef TARGET_NR_munlock
6402     case TARGET_NR_munlock:
6403         ret = get_errno(munlock(g2h(arg1), arg2));
6404         break;
6405 #endif
6406 #ifdef TARGET_NR_mlockall
6407     case TARGET_NR_mlockall:
6408         ret = get_errno(mlockall(arg1));
6409         break;
6410 #endif
6411 #ifdef TARGET_NR_munlockall
6412     case TARGET_NR_munlockall:
6413         ret = get_errno(munlockall());
6414         break;
6415 #endif
6416     case TARGET_NR_truncate:
6417         if (!(p = lock_user_string(arg1)))
6418             goto efault;
6419         ret = get_errno(truncate(p, arg2));
6420         unlock_user(p, arg1, 0);
6421         break;
6422     case TARGET_NR_ftruncate:
6423         ret = get_errno(ftruncate(arg1, arg2));
6424         break;
6425     case TARGET_NR_fchmod:
6426         ret = get_errno(fchmod(arg1, arg2));
6427         break;
6428 #if defined(TARGET_NR_fchmodat)
6429     case TARGET_NR_fchmodat:
6430         if (!(p = lock_user_string(arg2)))
6431             goto efault;
6432         ret = get_errno(fchmodat(arg1, p, arg3, 0));
6433         unlock_user(p, arg2, 0);
6434         break;
6435 #endif
6436     case TARGET_NR_getpriority:
6437         /* Note that negative values are valid for getpriority, so we must
6438            differentiate based on errno settings.  */
6439         errno = 0;
6440         ret = getpriority(arg1, arg2);
6441         if (ret == -1 && errno != 0) {
6442             ret = -host_to_target_errno(errno);
6443             break;
6444         }
6445 #ifdef TARGET_ALPHA
6446         /* Return value is the unbiased priority.  Signal no error.  */
6447         ((CPUAlphaState *)cpu_env)->ir[IR_V0] = 0;
6448 #else
6449         /* Return value is a biased priority to avoid negative numbers.  */
6450         ret = 20 - ret;
6451 #endif
6452         break;
6453     case TARGET_NR_setpriority:
6454         ret = get_errno(setpriority(arg1, arg2, arg3));
6455         break;
6456 #ifdef TARGET_NR_profil
6457     case TARGET_NR_profil:
6458         goto unimplemented;
6459 #endif
6460     case TARGET_NR_statfs:
6461         if (!(p = lock_user_string(arg1)))
6462             goto efault;
6463         ret = get_errno(statfs(path(p), &stfs));
6464         unlock_user(p, arg1, 0);
6465     convert_statfs:
6466         if (!is_error(ret)) {
6467             struct target_statfs *target_stfs;
6468 
6469             if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg2, 0))
6470                 goto efault;
6471             __put_user(stfs.f_type, &target_stfs->f_type);
6472             __put_user(stfs.f_bsize, &target_stfs->f_bsize);
6473             __put_user(stfs.f_blocks, &target_stfs->f_blocks);
6474             __put_user(stfs.f_bfree, &target_stfs->f_bfree);
6475             __put_user(stfs.f_bavail, &target_stfs->f_bavail);
6476             __put_user(stfs.f_files, &target_stfs->f_files);
6477             __put_user(stfs.f_ffree, &target_stfs->f_ffree);
6478             __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
6479             __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
6480             __put_user(stfs.f_namelen, &target_stfs->f_namelen);
6481             __put_user(stfs.f_frsize, &target_stfs->f_frsize);
6482             memset(target_stfs->f_spare, 0, sizeof(target_stfs->f_spare));
6483             unlock_user_struct(target_stfs, arg2, 1);
6484         }
6485         break;
6486     case TARGET_NR_fstatfs:
6487         ret = get_errno(fstatfs(arg1, &stfs));
6488         goto convert_statfs;
6489 #ifdef TARGET_NR_statfs64
6490     case TARGET_NR_statfs64:
6491         if (!(p = lock_user_string(arg1)))
6492             goto efault;
6493         ret = get_errno(statfs(path(p), &stfs));
6494         unlock_user(p, arg1, 0);
6495     convert_statfs64:
6496         if (!is_error(ret)) {
6497             struct target_statfs64 *target_stfs;
6498 
6499             if (!lock_user_struct(VERIFY_WRITE, target_stfs, arg3, 0))
6500                 goto efault;
6501             __put_user(stfs.f_type, &target_stfs->f_type);
6502             __put_user(stfs.f_bsize, &target_stfs->f_bsize);
6503             __put_user(stfs.f_blocks, &target_stfs->f_blocks);
6504             __put_user(stfs.f_bfree, &target_stfs->f_bfree);
6505             __put_user(stfs.f_bavail, &target_stfs->f_bavail);
6506             __put_user(stfs.f_files, &target_stfs->f_files);
6507             __put_user(stfs.f_ffree, &target_stfs->f_ffree);
6508             __put_user(stfs.f_fsid.__val[0], &target_stfs->f_fsid.val[0]);
6509             __put_user(stfs.f_fsid.__val[1], &target_stfs->f_fsid.val[1]);
6510             __put_user(stfs.f_namelen, &target_stfs->f_namelen);
6511             __put_user(stfs.f_frsize, &target_stfs->f_frsize);
6512             memset(target_stfs->f_spare, 0, sizeof(target_stfs->f_spare));
6513             unlock_user_struct(target_stfs, arg3, 1);
6514         }
6515         break;
6516     case TARGET_NR_fstatfs64:
6517         ret = get_errno(fstatfs(arg1, &stfs));
6518         goto convert_statfs64;
6519 #endif
6520 #ifdef TARGET_NR_ioperm
6521     case TARGET_NR_ioperm:
6522         goto unimplemented;
6523 #endif
6524 #ifdef TARGET_NR_socketcall
6525     case TARGET_NR_socketcall:
6526         ret = do_socketcall(arg1, arg2);
6527         break;
6528 #endif
6529 #ifdef TARGET_NR_accept
6530     case TARGET_NR_accept:
6531         ret = do_accept4(arg1, arg2, arg3, 0);
6532         break;
6533 #endif
6534 #ifdef TARGET_NR_accept4
6535     case TARGET_NR_accept4:
6536 #ifdef CONFIG_ACCEPT4
6537         ret = do_accept4(arg1, arg2, arg3, arg4);
6538 #else
6539         goto unimplemented;
6540 #endif
6541         break;
6542 #endif
6543 #ifdef TARGET_NR_bind
6544     case TARGET_NR_bind:
6545         ret = do_bind(arg1, arg2, arg3);
6546         break;
6547 #endif
6548 #ifdef TARGET_NR_connect
6549     case TARGET_NR_connect:
6550         ret = do_connect(arg1, arg2, arg3);
6551         break;
6552 #endif
6553 #ifdef TARGET_NR_getpeername
6554     case TARGET_NR_getpeername:
6555         ret = do_getpeername(arg1, arg2, arg3);
6556         break;
6557 #endif
6558 #ifdef TARGET_NR_getsockname
6559     case TARGET_NR_getsockname:
6560         ret = do_getsockname(arg1, arg2, arg3);
6561         break;
6562 #endif
6563 #ifdef TARGET_NR_getsockopt
6564     case TARGET_NR_getsockopt:
6565         ret = do_getsockopt(arg1, arg2, arg3, arg4, arg5);
6566         break;
6567 #endif
6568 #ifdef TARGET_NR_listen
6569     case TARGET_NR_listen:
6570         ret = get_errno(listen(arg1, arg2));
6571         break;
6572 #endif
6573 #ifdef TARGET_NR_recv
6574     case TARGET_NR_recv:
6575         ret = do_recvfrom(arg1, arg2, arg3, arg4, 0, 0);
6576         break;
6577 #endif
6578 #ifdef TARGET_NR_recvfrom
6579     case TARGET_NR_recvfrom:
6580         ret = do_recvfrom(arg1, arg2, arg3, arg4, arg5, arg6);
6581         break;
6582 #endif
6583 #ifdef TARGET_NR_recvmsg
6584     case TARGET_NR_recvmsg:
6585         ret = do_sendrecvmsg(arg1, arg2, arg3, 0);
6586         break;
6587 #endif
6588 #ifdef TARGET_NR_send
6589     case TARGET_NR_send:
6590         ret = do_sendto(arg1, arg2, arg3, arg4, 0, 0);
6591         break;
6592 #endif
6593 #ifdef TARGET_NR_sendmsg
6594     case TARGET_NR_sendmsg:
6595         ret = do_sendrecvmsg(arg1, arg2, arg3, 1);
6596         break;
6597 #endif
6598 #ifdef TARGET_NR_sendto
6599     case TARGET_NR_sendto:
6600         ret = do_sendto(arg1, arg2, arg3, arg4, arg5, arg6);
6601         break;
6602 #endif
6603 #ifdef TARGET_NR_shutdown
6604     case TARGET_NR_shutdown:
6605         ret = get_errno(shutdown(arg1, arg2));
6606         break;
6607 #endif
6608 #ifdef TARGET_NR_socket
6609     case TARGET_NR_socket:
6610         ret = do_socket(arg1, arg2, arg3);
6611         break;
6612 #endif
6613 #ifdef TARGET_NR_socketpair
6614     case TARGET_NR_socketpair:
6615         ret = do_socketpair(arg1, arg2, arg3, arg4);
6616         break;
6617 #endif
6618 #ifdef TARGET_NR_setsockopt
6619     case TARGET_NR_setsockopt:
6620         ret = do_setsockopt(arg1, arg2, arg3, arg4, (socklen_t) arg5);
6621         break;
6622 #endif
6623 
6624     case TARGET_NR_syslog:
6625         if (!(p = lock_user_string(arg2)))
6626             goto efault;
6627         ret = get_errno(sys_syslog((int)arg1, p, (int)arg3));
6628         unlock_user(p, arg2, 0);
6629         break;
6630 
6631     case TARGET_NR_setitimer:
6632         {
6633             struct itimerval value, ovalue, *pvalue;
6634 
6635             if (arg2) {
6636                 pvalue = &value;
6637                 if (copy_from_user_timeval(&pvalue->it_interval, arg2)
6638                     || copy_from_user_timeval(&pvalue->it_value,
6639                                               arg2 + sizeof(struct target_timeval)))
6640                     goto efault;
6641             } else {
6642                 pvalue = NULL;
6643             }
6644             ret = get_errno(setitimer(arg1, pvalue, &ovalue));
6645             if (!is_error(ret) && arg3) {
6646                 if (copy_to_user_timeval(arg3,
6647                                          &ovalue.it_interval)
6648                     || copy_to_user_timeval(arg3 + sizeof(struct target_timeval),
6649                                             &ovalue.it_value))
6650                     goto efault;
6651             }
6652         }
6653         break;
6654     case TARGET_NR_getitimer:
6655         {
6656             struct itimerval value;
6657 
6658             ret = get_errno(getitimer(arg1, &value));
6659             if (!is_error(ret) && arg2) {
6660                 if (copy_to_user_timeval(arg2,
6661                                          &value.it_interval)
6662                     || copy_to_user_timeval(arg2 + sizeof(struct target_timeval),
6663                                             &value.it_value))
6664                     goto efault;
6665             }
6666         }
6667         break;
6668     case TARGET_NR_stat:
6669         if (!(p = lock_user_string(arg1)))
6670             goto efault;
6671         ret = get_errno(stat(path(p), &st));
6672         unlock_user(p, arg1, 0);
6673         goto do_stat;
6674     case TARGET_NR_lstat:
6675         if (!(p = lock_user_string(arg1)))
6676             goto efault;
6677         ret = get_errno(lstat(path(p), &st));
6678         unlock_user(p, arg1, 0);
6679         goto do_stat;
6680     case TARGET_NR_fstat:
6681         {
6682             ret = get_errno(fstat(arg1, &st));
6683         do_stat:
6684             if (!is_error(ret)) {
6685                 struct target_stat *target_st;
6686 
6687                 if (!lock_user_struct(VERIFY_WRITE, target_st, arg2, 0))
6688                     goto efault;
6689                 memset(target_st, 0, sizeof(*target_st));
6690                 __put_user(st.st_dev, &target_st->st_dev);
6691                 __put_user(st.st_ino, &target_st->st_ino);
6692                 __put_user(st.st_mode, &target_st->st_mode);
6693                 __put_user(st.st_uid, &target_st->st_uid);
6694                 __put_user(st.st_gid, &target_st->st_gid);
6695                 __put_user(st.st_nlink, &target_st->st_nlink);
6696                 __put_user(st.st_rdev, &target_st->st_rdev);
6697                 __put_user(st.st_size, &target_st->st_size);
6698                 __put_user(st.st_blksize, &target_st->st_blksize);
6699                 __put_user(st.st_blocks, &target_st->st_blocks);
6700                 __put_user(st.st_atime, &target_st->target_st_atime);
6701                 __put_user(st.st_mtime, &target_st->target_st_mtime);
6702                 __put_user(st.st_ctime, &target_st->target_st_ctime);
6703                 unlock_user_struct(target_st, arg2, 1);
6704             }
6705         }
6706         break;
6707 #ifdef TARGET_NR_olduname
6708     case TARGET_NR_olduname:
6709         goto unimplemented;
6710 #endif
6711 #ifdef TARGET_NR_iopl
6712     case TARGET_NR_iopl:
6713         goto unimplemented;
6714 #endif
6715     case TARGET_NR_vhangup:
6716         ret = get_errno(vhangup());
6717         break;
6718 #ifdef TARGET_NR_idle
6719     case TARGET_NR_idle:
6720         goto unimplemented;
6721 #endif
6722 #ifdef TARGET_NR_syscall
6723     case TARGET_NR_syscall:
6724         ret = do_syscall(cpu_env, arg1 & 0xffff, arg2, arg3, arg4, arg5,
6725                          arg6, arg7, arg8, 0);
6726         break;
6727 #endif
6728     case TARGET_NR_wait4:
6729         {
6730             int status;
6731             abi_long status_ptr = arg2;
6732             struct rusage rusage, *rusage_ptr;
6733             abi_ulong target_rusage = arg4;
6734             if (target_rusage)
6735                 rusage_ptr = &rusage;
6736             else
6737                 rusage_ptr = NULL;
6738             ret = get_errno(wait4(arg1, &status, arg3, rusage_ptr));
6739             if (!is_error(ret)) {
6740                 if (status_ptr && ret) {
6741                     status = host_to_target_waitstatus(status);
6742                     if (put_user_s32(status, status_ptr))
6743                         goto efault;
6744                 }
6745                 if (target_rusage)
6746                     host_to_target_rusage(target_rusage, &rusage);
6747             }
6748         }
6749         break;
6750 #ifdef TARGET_NR_swapoff
6751     case TARGET_NR_swapoff:
6752         if (!(p = lock_user_string(arg1)))
6753             goto efault;
6754         ret = get_errno(swapoff(p));
6755         unlock_user(p, arg1, 0);
6756         break;
6757 #endif
6758     case TARGET_NR_sysinfo:
6759         {
6760             struct target_sysinfo *target_value;
6761             struct sysinfo value;
6762             ret = get_errno(sysinfo(&value));
6763             if (!is_error(ret) && arg1)
6764             {
6765                 if (!lock_user_struct(VERIFY_WRITE, target_value, arg1, 0))
6766                     goto efault;
6767                 __put_user(value.uptime, &target_value->uptime);
6768                 __put_user(value.loads[0], &target_value->loads[0]);
6769                 __put_user(value.loads[1], &target_value->loads[1]);
6770                 __put_user(value.loads[2], &target_value->loads[2]);
6771                 __put_user(value.totalram, &target_value->totalram);
6772                 __put_user(value.freeram, &target_value->freeram);
6773                 __put_user(value.sharedram, &target_value->sharedram);
6774                 __put_user(value.bufferram, &target_value->bufferram);
6775                 __put_user(value.totalswap, &target_value->totalswap);
6776                 __put_user(value.freeswap, &target_value->freeswap);
6777                 __put_user(value.procs, &target_value->procs);
6778                 __put_user(value.totalhigh, &target_value->totalhigh);
6779                 __put_user(value.freehigh, &target_value->freehigh);
6780                 __put_user(value.mem_unit, &target_value->mem_unit);
6781                 unlock_user_struct(target_value, arg1, 1);
6782             }
6783         }
6784         break;
6785 #ifdef TARGET_NR_ipc
6786     case TARGET_NR_ipc:
6787 	ret = do_ipc(arg1, arg2, arg3, arg4, arg5, arg6);
6788 	break;
6789 #endif
6790 #ifdef TARGET_NR_semget
6791     case TARGET_NR_semget:
6792         ret = get_errno(semget(arg1, arg2, arg3));
6793         break;
6794 #endif
6795 #ifdef TARGET_NR_semop
6796     case TARGET_NR_semop:
6797         ret = do_semop(arg1, arg2, arg3);
6798         break;
6799 #endif
6800 #ifdef TARGET_NR_semctl
6801     case TARGET_NR_semctl:
6802         ret = do_semctl(arg1, arg2, arg3, (union target_semun)(abi_ulong)arg4);
6803         break;
6804 #endif
6805 #ifdef TARGET_NR_msgctl
6806     case TARGET_NR_msgctl:
6807         ret = do_msgctl(arg1, arg2, arg3);
6808         break;
6809 #endif
6810 #ifdef TARGET_NR_msgget
6811     case TARGET_NR_msgget:
6812         ret = get_errno(msgget(arg1, arg2));
6813         break;
6814 #endif
6815 #ifdef TARGET_NR_msgrcv
6816     case TARGET_NR_msgrcv:
6817         ret = do_msgrcv(arg1, arg2, arg3, arg4, arg5);
6818         break;
6819 #endif
6820 #ifdef TARGET_NR_msgsnd
6821     case TARGET_NR_msgsnd:
6822         ret = do_msgsnd(arg1, arg2, arg3, arg4);
6823         break;
6824 #endif
6825 #ifdef TARGET_NR_shmget
6826     case TARGET_NR_shmget:
6827         ret = get_errno(shmget(arg1, arg2, arg3));
6828         break;
6829 #endif
6830 #ifdef TARGET_NR_shmctl
6831     case TARGET_NR_shmctl:
6832         ret = do_shmctl(arg1, arg2, arg3);
6833         break;
6834 #endif
6835 #ifdef TARGET_NR_shmat
6836     case TARGET_NR_shmat:
6837         ret = do_shmat(arg1, arg2, arg3);
6838         break;
6839 #endif
6840 #ifdef TARGET_NR_shmdt
6841     case TARGET_NR_shmdt:
6842         ret = do_shmdt(arg1);
6843         break;
6844 #endif
6845     case TARGET_NR_fsync:
6846         ret = get_errno(fsync(arg1));
6847         break;
6848     case TARGET_NR_clone:
6849 #if defined(TARGET_SH4) || defined(TARGET_ALPHA)
6850         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg5, arg4));
6851 #elif defined(TARGET_CRIS)
6852         ret = get_errno(do_fork(cpu_env, arg2, arg1, arg3, arg4, arg5));
6853 #elif defined(TARGET_MICROBLAZE)
6854         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg4, arg6, arg5));
6855 #elif defined(TARGET_S390X)
6856         ret = get_errno(do_fork(cpu_env, arg2, arg1, arg3, arg5, arg4));
6857 #else
6858         ret = get_errno(do_fork(cpu_env, arg1, arg2, arg3, arg4, arg5));
6859 #endif
6860         break;
6861 #ifdef __NR_exit_group
6862         /* new thread calls */
6863     case TARGET_NR_exit_group:
6864 #ifdef TARGET_GPROF
6865         _mcleanup();
6866 #endif
6867         gdb_exit(cpu_env, arg1);
6868         ret = get_errno(exit_group(arg1));
6869         break;
6870 #endif
6871     case TARGET_NR_setdomainname:
6872         if (!(p = lock_user_string(arg1)))
6873             goto efault;
6874         ret = get_errno(setdomainname(p, arg2));
6875         unlock_user(p, arg1, 0);
6876         break;
6877     case TARGET_NR_uname:
6878         /* no need to transcode because we use the linux syscall */
6879         {
6880             struct new_utsname * buf;
6881 
6882             if (!lock_user_struct(VERIFY_WRITE, buf, arg1, 0))
6883                 goto efault;
6884             ret = get_errno(sys_uname(buf));
6885             if (!is_error(ret)) {
6886                 /* Overrite the native machine name with whatever is being
6887                    emulated. */
6888                 strcpy (buf->machine, cpu_to_uname_machine(cpu_env));
6889                 /* Allow the user to override the reported release.  */
6890                 if (qemu_uname_release && *qemu_uname_release)
6891                   strcpy (buf->release, qemu_uname_release);
6892             }
6893             unlock_user_struct(buf, arg1, 1);
6894         }
6895         break;
6896 #ifdef TARGET_I386
6897     case TARGET_NR_modify_ldt:
6898         ret = do_modify_ldt(cpu_env, arg1, arg2, arg3);
6899         break;
6900 #if !defined(TARGET_X86_64)
6901     case TARGET_NR_vm86old:
6902         goto unimplemented;
6903     case TARGET_NR_vm86:
6904         ret = do_vm86(cpu_env, arg1, arg2);
6905         break;
6906 #endif
6907 #endif
6908     case TARGET_NR_adjtimex:
6909         goto unimplemented;
6910 #ifdef TARGET_NR_create_module
6911     case TARGET_NR_create_module:
6912 #endif
6913     case TARGET_NR_init_module:
6914     case TARGET_NR_delete_module:
6915 #ifdef TARGET_NR_get_kernel_syms
6916     case TARGET_NR_get_kernel_syms:
6917 #endif
6918         goto unimplemented;
6919     case TARGET_NR_quotactl:
6920         goto unimplemented;
6921     case TARGET_NR_getpgid:
6922         ret = get_errno(getpgid(arg1));
6923         break;
6924     case TARGET_NR_fchdir:
6925         ret = get_errno(fchdir(arg1));
6926         break;
6927 #ifdef TARGET_NR_bdflush /* not on x86_64 */
6928     case TARGET_NR_bdflush:
6929         goto unimplemented;
6930 #endif
6931 #ifdef TARGET_NR_sysfs
6932     case TARGET_NR_sysfs:
6933         goto unimplemented;
6934 #endif
6935     case TARGET_NR_personality:
6936         ret = get_errno(personality(arg1));
6937         break;
6938 #ifdef TARGET_NR_afs_syscall
6939     case TARGET_NR_afs_syscall:
6940         goto unimplemented;
6941 #endif
6942 #ifdef TARGET_NR__llseek /* Not on alpha */
6943     case TARGET_NR__llseek:
6944         {
6945             int64_t res;
6946 #if !defined(__NR_llseek)
6947             res = lseek(arg1, ((uint64_t)arg2 << 32) | arg3, arg5);
6948             if (res == -1) {
6949                 ret = get_errno(res);
6950             } else {
6951                 ret = 0;
6952             }
6953 #else
6954             ret = get_errno(_llseek(arg1, arg2, arg3, &res, arg5));
6955 #endif
6956             if ((ret == 0) && put_user_s64(res, arg4)) {
6957                 goto efault;
6958             }
6959         }
6960         break;
6961 #endif
6962     case TARGET_NR_getdents:
6963 #ifdef __NR_getdents
6964 #if TARGET_ABI_BITS == 32 && HOST_LONG_BITS == 64
6965         {
6966             struct target_dirent *target_dirp;
6967             struct linux_dirent *dirp;
6968             abi_long count = arg3;
6969 
6970 	    dirp = malloc(count);
6971 	    if (!dirp) {
6972                 ret = -TARGET_ENOMEM;
6973                 goto fail;
6974             }
6975 
6976             ret = get_errno(sys_getdents(arg1, dirp, count));
6977             if (!is_error(ret)) {
6978                 struct linux_dirent *de;
6979 		struct target_dirent *tde;
6980                 int len = ret;
6981                 int reclen, treclen;
6982 		int count1, tnamelen;
6983 
6984 		count1 = 0;
6985                 de = dirp;
6986                 if (!(target_dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
6987                     goto efault;
6988 		tde = target_dirp;
6989                 while (len > 0) {
6990                     reclen = de->d_reclen;
6991                     tnamelen = reclen - offsetof(struct linux_dirent, d_name);
6992                     assert(tnamelen >= 0);
6993                     treclen = tnamelen + offsetof(struct target_dirent, d_name);
6994                     assert(count1 + treclen <= count);
6995                     tde->d_reclen = tswap16(treclen);
6996                     tde->d_ino = tswapal(de->d_ino);
6997                     tde->d_off = tswapal(de->d_off);
6998                     memcpy(tde->d_name, de->d_name, tnamelen);
6999                     de = (struct linux_dirent *)((char *)de + reclen);
7000                     len -= reclen;
7001                     tde = (struct target_dirent *)((char *)tde + treclen);
7002 		    count1 += treclen;
7003                 }
7004 		ret = count1;
7005                 unlock_user(target_dirp, arg2, ret);
7006             }
7007 	    free(dirp);
7008         }
7009 #else
7010         {
7011             struct linux_dirent *dirp;
7012             abi_long count = arg3;
7013 
7014             if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
7015                 goto efault;
7016             ret = get_errno(sys_getdents(arg1, dirp, count));
7017             if (!is_error(ret)) {
7018                 struct linux_dirent *de;
7019                 int len = ret;
7020                 int reclen;
7021                 de = dirp;
7022                 while (len > 0) {
7023                     reclen = de->d_reclen;
7024                     if (reclen > len)
7025                         break;
7026                     de->d_reclen = tswap16(reclen);
7027                     tswapls(&de->d_ino);
7028                     tswapls(&de->d_off);
7029                     de = (struct linux_dirent *)((char *)de + reclen);
7030                     len -= reclen;
7031                 }
7032             }
7033             unlock_user(dirp, arg2, ret);
7034         }
7035 #endif
7036 #else
7037         /* Implement getdents in terms of getdents64 */
7038         {
7039             struct linux_dirent64 *dirp;
7040             abi_long count = arg3;
7041 
7042             dirp = lock_user(VERIFY_WRITE, arg2, count, 0);
7043             if (!dirp) {
7044                 goto efault;
7045             }
7046             ret = get_errno(sys_getdents64(arg1, dirp, count));
7047             if (!is_error(ret)) {
7048                 /* Convert the dirent64 structs to target dirent.  We do this
7049                  * in-place, since we can guarantee that a target_dirent is no
7050                  * larger than a dirent64; however this means we have to be
7051                  * careful to read everything before writing in the new format.
7052                  */
7053                 struct linux_dirent64 *de;
7054                 struct target_dirent *tde;
7055                 int len = ret;
7056                 int tlen = 0;
7057 
7058                 de = dirp;
7059                 tde = (struct target_dirent *)dirp;
7060                 while (len > 0) {
7061                     int namelen, treclen;
7062                     int reclen = de->d_reclen;
7063                     uint64_t ino = de->d_ino;
7064                     int64_t off = de->d_off;
7065                     uint8_t type = de->d_type;
7066 
7067                     namelen = strlen(de->d_name);
7068                     treclen = offsetof(struct target_dirent, d_name)
7069                         + namelen + 2;
7070                     treclen = QEMU_ALIGN_UP(treclen, sizeof(abi_long));
7071 
7072                     memmove(tde->d_name, de->d_name, namelen + 1);
7073                     tde->d_ino = tswapal(ino);
7074                     tde->d_off = tswapal(off);
7075                     tde->d_reclen = tswap16(treclen);
7076                     /* The target_dirent type is in what was formerly a padding
7077                      * byte at the end of the structure:
7078                      */
7079                     *(((char *)tde) + treclen - 1) = type;
7080 
7081                     de = (struct linux_dirent64 *)((char *)de + reclen);
7082                     tde = (struct target_dirent *)((char *)tde + treclen);
7083                     len -= reclen;
7084                     tlen += treclen;
7085                 }
7086                 ret = tlen;
7087             }
7088             unlock_user(dirp, arg2, ret);
7089         }
7090 #endif
7091         break;
7092 #if defined(TARGET_NR_getdents64) && defined(__NR_getdents64)
7093     case TARGET_NR_getdents64:
7094         {
7095             struct linux_dirent64 *dirp;
7096             abi_long count = arg3;
7097             if (!(dirp = lock_user(VERIFY_WRITE, arg2, count, 0)))
7098                 goto efault;
7099             ret = get_errno(sys_getdents64(arg1, dirp, count));
7100             if (!is_error(ret)) {
7101                 struct linux_dirent64 *de;
7102                 int len = ret;
7103                 int reclen;
7104                 de = dirp;
7105                 while (len > 0) {
7106                     reclen = de->d_reclen;
7107                     if (reclen > len)
7108                         break;
7109                     de->d_reclen = tswap16(reclen);
7110                     tswap64s((uint64_t *)&de->d_ino);
7111                     tswap64s((uint64_t *)&de->d_off);
7112                     de = (struct linux_dirent64 *)((char *)de + reclen);
7113                     len -= reclen;
7114                 }
7115             }
7116             unlock_user(dirp, arg2, ret);
7117         }
7118         break;
7119 #endif /* TARGET_NR_getdents64 */
7120 #if defined(TARGET_NR__newselect)
7121     case TARGET_NR__newselect:
7122         ret = do_select(arg1, arg2, arg3, arg4, arg5);
7123         break;
7124 #endif
7125 #if defined(TARGET_NR_poll) || defined(TARGET_NR_ppoll)
7126 # ifdef TARGET_NR_poll
7127     case TARGET_NR_poll:
7128 # endif
7129 # ifdef TARGET_NR_ppoll
7130     case TARGET_NR_ppoll:
7131 # endif
7132         {
7133             struct target_pollfd *target_pfd;
7134             unsigned int nfds = arg2;
7135             int timeout = arg3;
7136             struct pollfd *pfd;
7137             unsigned int i;
7138 
7139             target_pfd = lock_user(VERIFY_WRITE, arg1, sizeof(struct target_pollfd) * nfds, 1);
7140             if (!target_pfd)
7141                 goto efault;
7142 
7143             pfd = alloca(sizeof(struct pollfd) * nfds);
7144             for(i = 0; i < nfds; i++) {
7145                 pfd[i].fd = tswap32(target_pfd[i].fd);
7146                 pfd[i].events = tswap16(target_pfd[i].events);
7147             }
7148 
7149 # ifdef TARGET_NR_ppoll
7150             if (num == TARGET_NR_ppoll) {
7151                 struct timespec _timeout_ts, *timeout_ts = &_timeout_ts;
7152                 target_sigset_t *target_set;
7153                 sigset_t _set, *set = &_set;
7154 
7155                 if (arg3) {
7156                     if (target_to_host_timespec(timeout_ts, arg3)) {
7157                         unlock_user(target_pfd, arg1, 0);
7158                         goto efault;
7159                     }
7160                 } else {
7161                     timeout_ts = NULL;
7162                 }
7163 
7164                 if (arg4) {
7165                     target_set = lock_user(VERIFY_READ, arg4, sizeof(target_sigset_t), 1);
7166                     if (!target_set) {
7167                         unlock_user(target_pfd, arg1, 0);
7168                         goto efault;
7169                     }
7170                     target_to_host_sigset(set, target_set);
7171                 } else {
7172                     set = NULL;
7173                 }
7174 
7175                 ret = get_errno(sys_ppoll(pfd, nfds, timeout_ts, set, _NSIG/8));
7176 
7177                 if (!is_error(ret) && arg3) {
7178                     host_to_target_timespec(arg3, timeout_ts);
7179                 }
7180                 if (arg4) {
7181                     unlock_user(target_set, arg4, 0);
7182                 }
7183             } else
7184 # endif
7185                 ret = get_errno(poll(pfd, nfds, timeout));
7186 
7187             if (!is_error(ret)) {
7188                 for(i = 0; i < nfds; i++) {
7189                     target_pfd[i].revents = tswap16(pfd[i].revents);
7190                 }
7191             }
7192             unlock_user(target_pfd, arg1, sizeof(struct target_pollfd) * nfds);
7193         }
7194         break;
7195 #endif
7196     case TARGET_NR_flock:
7197         /* NOTE: the flock constant seems to be the same for every
7198            Linux platform */
7199         ret = get_errno(flock(arg1, arg2));
7200         break;
7201     case TARGET_NR_readv:
7202         {
7203             struct iovec *vec = lock_iovec(VERIFY_WRITE, arg2, arg3, 0);
7204             if (vec != NULL) {
7205                 ret = get_errno(readv(arg1, vec, arg3));
7206                 unlock_iovec(vec, arg2, arg3, 1);
7207             } else {
7208                 ret = -host_to_target_errno(errno);
7209             }
7210         }
7211         break;
7212     case TARGET_NR_writev:
7213         {
7214             struct iovec *vec = lock_iovec(VERIFY_READ, arg2, arg3, 1);
7215             if (vec != NULL) {
7216                 ret = get_errno(writev(arg1, vec, arg3));
7217                 unlock_iovec(vec, arg2, arg3, 0);
7218             } else {
7219                 ret = -host_to_target_errno(errno);
7220             }
7221         }
7222         break;
7223     case TARGET_NR_getsid:
7224         ret = get_errno(getsid(arg1));
7225         break;
7226 #if defined(TARGET_NR_fdatasync) /* Not on alpha (osf_datasync ?) */
7227     case TARGET_NR_fdatasync:
7228         ret = get_errno(fdatasync(arg1));
7229         break;
7230 #endif
7231     case TARGET_NR__sysctl:
7232         /* We don't implement this, but ENOTDIR is always a safe
7233            return value. */
7234         ret = -TARGET_ENOTDIR;
7235         break;
7236     case TARGET_NR_sched_getaffinity:
7237         {
7238             unsigned int mask_size;
7239             unsigned long *mask;
7240 
7241             /*
7242              * sched_getaffinity needs multiples of ulong, so need to take
7243              * care of mismatches between target ulong and host ulong sizes.
7244              */
7245             if (arg2 & (sizeof(abi_ulong) - 1)) {
7246                 ret = -TARGET_EINVAL;
7247                 break;
7248             }
7249             mask_size = (arg2 + (sizeof(*mask) - 1)) & ~(sizeof(*mask) - 1);
7250 
7251             mask = alloca(mask_size);
7252             ret = get_errno(sys_sched_getaffinity(arg1, mask_size, mask));
7253 
7254             if (!is_error(ret)) {
7255                 if (copy_to_user(arg3, mask, ret)) {
7256                     goto efault;
7257                 }
7258             }
7259         }
7260         break;
7261     case TARGET_NR_sched_setaffinity:
7262         {
7263             unsigned int mask_size;
7264             unsigned long *mask;
7265 
7266             /*
7267              * sched_setaffinity needs multiples of ulong, so need to take
7268              * care of mismatches between target ulong and host ulong sizes.
7269              */
7270             if (arg2 & (sizeof(abi_ulong) - 1)) {
7271                 ret = -TARGET_EINVAL;
7272                 break;
7273             }
7274             mask_size = (arg2 + (sizeof(*mask) - 1)) & ~(sizeof(*mask) - 1);
7275 
7276             mask = alloca(mask_size);
7277             if (!lock_user_struct(VERIFY_READ, p, arg3, 1)) {
7278                 goto efault;
7279             }
7280             memcpy(mask, p, arg2);
7281             unlock_user_struct(p, arg2, 0);
7282 
7283             ret = get_errno(sys_sched_setaffinity(arg1, mask_size, mask));
7284         }
7285         break;
7286     case TARGET_NR_sched_setparam:
7287         {
7288             struct sched_param *target_schp;
7289             struct sched_param schp;
7290 
7291             if (!lock_user_struct(VERIFY_READ, target_schp, arg2, 1))
7292                 goto efault;
7293             schp.sched_priority = tswap32(target_schp->sched_priority);
7294             unlock_user_struct(target_schp, arg2, 0);
7295             ret = get_errno(sched_setparam(arg1, &schp));
7296         }
7297         break;
7298     case TARGET_NR_sched_getparam:
7299         {
7300             struct sched_param *target_schp;
7301             struct sched_param schp;
7302             ret = get_errno(sched_getparam(arg1, &schp));
7303             if (!is_error(ret)) {
7304                 if (!lock_user_struct(VERIFY_WRITE, target_schp, arg2, 0))
7305                     goto efault;
7306                 target_schp->sched_priority = tswap32(schp.sched_priority);
7307                 unlock_user_struct(target_schp, arg2, 1);
7308             }
7309         }
7310         break;
7311     case TARGET_NR_sched_setscheduler:
7312         {
7313             struct sched_param *target_schp;
7314             struct sched_param schp;
7315             if (!lock_user_struct(VERIFY_READ, target_schp, arg3, 1))
7316                 goto efault;
7317             schp.sched_priority = tswap32(target_schp->sched_priority);
7318             unlock_user_struct(target_schp, arg3, 0);
7319             ret = get_errno(sched_setscheduler(arg1, arg2, &schp));
7320         }
7321         break;
7322     case TARGET_NR_sched_getscheduler:
7323         ret = get_errno(sched_getscheduler(arg1));
7324         break;
7325     case TARGET_NR_sched_yield:
7326         ret = get_errno(sched_yield());
7327         break;
7328     case TARGET_NR_sched_get_priority_max:
7329         ret = get_errno(sched_get_priority_max(arg1));
7330         break;
7331     case TARGET_NR_sched_get_priority_min:
7332         ret = get_errno(sched_get_priority_min(arg1));
7333         break;
7334     case TARGET_NR_sched_rr_get_interval:
7335         {
7336             struct timespec ts;
7337             ret = get_errno(sched_rr_get_interval(arg1, &ts));
7338             if (!is_error(ret)) {
7339                 host_to_target_timespec(arg2, &ts);
7340             }
7341         }
7342         break;
7343     case TARGET_NR_nanosleep:
7344         {
7345             struct timespec req, rem;
7346             target_to_host_timespec(&req, arg1);
7347             ret = get_errno(nanosleep(&req, &rem));
7348             if (is_error(ret) && arg2) {
7349                 host_to_target_timespec(arg2, &rem);
7350             }
7351         }
7352         break;
7353 #ifdef TARGET_NR_query_module
7354     case TARGET_NR_query_module:
7355         goto unimplemented;
7356 #endif
7357 #ifdef TARGET_NR_nfsservctl
7358     case TARGET_NR_nfsservctl:
7359         goto unimplemented;
7360 #endif
7361     case TARGET_NR_prctl:
7362         switch (arg1) {
7363         case PR_GET_PDEATHSIG:
7364         {
7365             int deathsig;
7366             ret = get_errno(prctl(arg1, &deathsig, arg3, arg4, arg5));
7367             if (!is_error(ret) && arg2
7368                 && put_user_ual(deathsig, arg2)) {
7369                 goto efault;
7370             }
7371             break;
7372         }
7373 #ifdef PR_GET_NAME
7374         case PR_GET_NAME:
7375         {
7376             void *name = lock_user(VERIFY_WRITE, arg2, 16, 1);
7377             if (!name) {
7378                 goto efault;
7379             }
7380             ret = get_errno(prctl(arg1, (unsigned long)name,
7381                                   arg3, arg4, arg5));
7382             unlock_user(name, arg2, 16);
7383             break;
7384         }
7385         case PR_SET_NAME:
7386         {
7387             void *name = lock_user(VERIFY_READ, arg2, 16, 1);
7388             if (!name) {
7389                 goto efault;
7390             }
7391             ret = get_errno(prctl(arg1, (unsigned long)name,
7392                                   arg3, arg4, arg5));
7393             unlock_user(name, arg2, 0);
7394             break;
7395         }
7396 #endif
7397         default:
7398             /* Most prctl options have no pointer arguments */
7399             ret = get_errno(prctl(arg1, arg2, arg3, arg4, arg5));
7400             break;
7401         }
7402         break;
7403 #ifdef TARGET_NR_arch_prctl
7404     case TARGET_NR_arch_prctl:
7405 #if defined(TARGET_I386) && !defined(TARGET_ABI32)
7406         ret = do_arch_prctl(cpu_env, arg1, arg2);
7407         break;
7408 #else
7409         goto unimplemented;
7410 #endif
7411 #endif
7412 #ifdef TARGET_NR_pread64
7413     case TARGET_NR_pread64:
7414         if (regpairs_aligned(cpu_env)) {
7415             arg4 = arg5;
7416             arg5 = arg6;
7417         }
7418         if (!(p = lock_user(VERIFY_WRITE, arg2, arg3, 0)))
7419             goto efault;
7420         ret = get_errno(pread64(arg1, p, arg3, target_offset64(arg4, arg5)));
7421         unlock_user(p, arg2, ret);
7422         break;
7423     case TARGET_NR_pwrite64:
7424         if (regpairs_aligned(cpu_env)) {
7425             arg4 = arg5;
7426             arg5 = arg6;
7427         }
7428         if (!(p = lock_user(VERIFY_READ, arg2, arg3, 1)))
7429             goto efault;
7430         ret = get_errno(pwrite64(arg1, p, arg3, target_offset64(arg4, arg5)));
7431         unlock_user(p, arg2, 0);
7432         break;
7433 #endif
7434     case TARGET_NR_getcwd:
7435         if (!(p = lock_user(VERIFY_WRITE, arg1, arg2, 0)))
7436             goto efault;
7437         ret = get_errno(sys_getcwd1(p, arg2));
7438         unlock_user(p, arg1, ret);
7439         break;
7440     case TARGET_NR_capget:
7441         goto unimplemented;
7442     case TARGET_NR_capset:
7443         goto unimplemented;
7444     case TARGET_NR_sigaltstack:
7445 #if defined(TARGET_I386) || defined(TARGET_ARM) || defined(TARGET_MIPS) || \
7446     defined(TARGET_SPARC) || defined(TARGET_PPC) || defined(TARGET_ALPHA) || \
7447     defined(TARGET_M68K) || defined(TARGET_S390X) || defined(TARGET_OPENRISC)
7448         ret = do_sigaltstack(arg1, arg2, get_sp_from_cpustate((CPUArchState *)cpu_env));
7449         break;
7450 #else
7451         goto unimplemented;
7452 #endif
7453 
7454 #ifdef CONFIG_SENDFILE
7455     case TARGET_NR_sendfile:
7456     {
7457         off_t *offp = NULL;
7458         off_t off;
7459         if (arg3) {
7460             ret = get_user_sal(off, arg3);
7461             if (is_error(ret)) {
7462                 break;
7463             }
7464             offp = &off;
7465         }
7466         ret = get_errno(sendfile(arg1, arg2, offp, arg4));
7467         if (!is_error(ret) && arg3) {
7468             abi_long ret2 = put_user_sal(off, arg3);
7469             if (is_error(ret2)) {
7470                 ret = ret2;
7471             }
7472         }
7473         break;
7474     }
7475 #ifdef TARGET_NR_sendfile64
7476     case TARGET_NR_sendfile64:
7477     {
7478         off_t *offp = NULL;
7479         off_t off;
7480         if (arg3) {
7481             ret = get_user_s64(off, arg3);
7482             if (is_error(ret)) {
7483                 break;
7484             }
7485             offp = &off;
7486         }
7487         ret = get_errno(sendfile(arg1, arg2, offp, arg4));
7488         if (!is_error(ret) && arg3) {
7489             abi_long ret2 = put_user_s64(off, arg3);
7490             if (is_error(ret2)) {
7491                 ret = ret2;
7492             }
7493         }
7494         break;
7495     }
7496 #endif
7497 #else
7498     case TARGET_NR_sendfile:
7499 #ifdef TARGET_NR_sendfile64
7500     case TARGET_NR_sendfile64:
7501 #endif
7502         goto unimplemented;
7503 #endif
7504 
7505 #ifdef TARGET_NR_getpmsg
7506     case TARGET_NR_getpmsg:
7507         goto unimplemented;
7508 #endif
7509 #ifdef TARGET_NR_putpmsg
7510     case TARGET_NR_putpmsg:
7511         goto unimplemented;
7512 #endif
7513 #ifdef TARGET_NR_vfork
7514     case TARGET_NR_vfork:
7515         ret = get_errno(do_fork(cpu_env, CLONE_VFORK | CLONE_VM | SIGCHLD,
7516                         0, 0, 0, 0));
7517         break;
7518 #endif
7519 #ifdef TARGET_NR_ugetrlimit
7520     case TARGET_NR_ugetrlimit:
7521     {
7522 	struct rlimit rlim;
7523 	int resource = target_to_host_resource(arg1);
7524 	ret = get_errno(getrlimit(resource, &rlim));
7525 	if (!is_error(ret)) {
7526 	    struct target_rlimit *target_rlim;
7527             if (!lock_user_struct(VERIFY_WRITE, target_rlim, arg2, 0))
7528                 goto efault;
7529 	    target_rlim->rlim_cur = host_to_target_rlim(rlim.rlim_cur);
7530 	    target_rlim->rlim_max = host_to_target_rlim(rlim.rlim_max);
7531             unlock_user_struct(target_rlim, arg2, 1);
7532 	}
7533 	break;
7534     }
7535 #endif
7536 #ifdef TARGET_NR_truncate64
7537     case TARGET_NR_truncate64:
7538         if (!(p = lock_user_string(arg1)))
7539             goto efault;
7540 	ret = target_truncate64(cpu_env, p, arg2, arg3, arg4);
7541         unlock_user(p, arg1, 0);
7542 	break;
7543 #endif
7544 #ifdef TARGET_NR_ftruncate64
7545     case TARGET_NR_ftruncate64:
7546 	ret = target_ftruncate64(cpu_env, arg1, arg2, arg3, arg4);
7547 	break;
7548 #endif
7549 #ifdef TARGET_NR_stat64
7550     case TARGET_NR_stat64:
7551         if (!(p = lock_user_string(arg1)))
7552             goto efault;
7553         ret = get_errno(stat(path(p), &st));
7554         unlock_user(p, arg1, 0);
7555         if (!is_error(ret))
7556             ret = host_to_target_stat64(cpu_env, arg2, &st);
7557         break;
7558 #endif
7559 #ifdef TARGET_NR_lstat64
7560     case TARGET_NR_lstat64:
7561         if (!(p = lock_user_string(arg1)))
7562             goto efault;
7563         ret = get_errno(lstat(path(p), &st));
7564         unlock_user(p, arg1, 0);
7565         if (!is_error(ret))
7566             ret = host_to_target_stat64(cpu_env, arg2, &st);
7567         break;
7568 #endif
7569 #ifdef TARGET_NR_fstat64
7570     case TARGET_NR_fstat64:
7571         ret = get_errno(fstat(arg1, &st));
7572         if (!is_error(ret))
7573             ret = host_to_target_stat64(cpu_env, arg2, &st);
7574         break;
7575 #endif
7576 #if (defined(TARGET_NR_fstatat64) || defined(TARGET_NR_newfstatat))
7577 #ifdef TARGET_NR_fstatat64
7578     case TARGET_NR_fstatat64:
7579 #endif
7580 #ifdef TARGET_NR_newfstatat
7581     case TARGET_NR_newfstatat:
7582 #endif
7583         if (!(p = lock_user_string(arg2)))
7584             goto efault;
7585         ret = get_errno(fstatat(arg1, path(p), &st, arg4));
7586         if (!is_error(ret))
7587             ret = host_to_target_stat64(cpu_env, arg3, &st);
7588         break;
7589 #endif
7590     case TARGET_NR_lchown:
7591         if (!(p = lock_user_string(arg1)))
7592             goto efault;
7593         ret = get_errno(lchown(p, low2highuid(arg2), low2highgid(arg3)));
7594         unlock_user(p, arg1, 0);
7595         break;
7596 #ifdef TARGET_NR_getuid
7597     case TARGET_NR_getuid:
7598         ret = get_errno(high2lowuid(getuid()));
7599         break;
7600 #endif
7601 #ifdef TARGET_NR_getgid
7602     case TARGET_NR_getgid:
7603         ret = get_errno(high2lowgid(getgid()));
7604         break;
7605 #endif
7606 #ifdef TARGET_NR_geteuid
7607     case TARGET_NR_geteuid:
7608         ret = get_errno(high2lowuid(geteuid()));
7609         break;
7610 #endif
7611 #ifdef TARGET_NR_getegid
7612     case TARGET_NR_getegid:
7613         ret = get_errno(high2lowgid(getegid()));
7614         break;
7615 #endif
7616     case TARGET_NR_setreuid:
7617         ret = get_errno(setreuid(low2highuid(arg1), low2highuid(arg2)));
7618         break;
7619     case TARGET_NR_setregid:
7620         ret = get_errno(setregid(low2highgid(arg1), low2highgid(arg2)));
7621         break;
7622     case TARGET_NR_getgroups:
7623         {
7624             int gidsetsize = arg1;
7625             target_id *target_grouplist;
7626             gid_t *grouplist;
7627             int i;
7628 
7629             grouplist = alloca(gidsetsize * sizeof(gid_t));
7630             ret = get_errno(getgroups(gidsetsize, grouplist));
7631             if (gidsetsize == 0)
7632                 break;
7633             if (!is_error(ret)) {
7634                 target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * sizeof(target_id), 0);
7635                 if (!target_grouplist)
7636                     goto efault;
7637                 for(i = 0;i < ret; i++)
7638                     target_grouplist[i] = tswapid(high2lowgid(grouplist[i]));
7639                 unlock_user(target_grouplist, arg2, gidsetsize * sizeof(target_id));
7640             }
7641         }
7642         break;
7643     case TARGET_NR_setgroups:
7644         {
7645             int gidsetsize = arg1;
7646             target_id *target_grouplist;
7647             gid_t *grouplist = NULL;
7648             int i;
7649             if (gidsetsize) {
7650                 grouplist = alloca(gidsetsize * sizeof(gid_t));
7651                 target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * sizeof(target_id), 1);
7652                 if (!target_grouplist) {
7653                     ret = -TARGET_EFAULT;
7654                     goto fail;
7655                 }
7656                 for (i = 0; i < gidsetsize; i++) {
7657                     grouplist[i] = low2highgid(tswapid(target_grouplist[i]));
7658                 }
7659                 unlock_user(target_grouplist, arg2, 0);
7660             }
7661             ret = get_errno(setgroups(gidsetsize, grouplist));
7662         }
7663         break;
7664     case TARGET_NR_fchown:
7665         ret = get_errno(fchown(arg1, low2highuid(arg2), low2highgid(arg3)));
7666         break;
7667 #if defined(TARGET_NR_fchownat)
7668     case TARGET_NR_fchownat:
7669         if (!(p = lock_user_string(arg2)))
7670             goto efault;
7671         ret = get_errno(fchownat(arg1, p, low2highuid(arg3),
7672                                  low2highgid(arg4), arg5));
7673         unlock_user(p, arg2, 0);
7674         break;
7675 #endif
7676 #ifdef TARGET_NR_setresuid
7677     case TARGET_NR_setresuid:
7678         ret = get_errno(setresuid(low2highuid(arg1),
7679                                   low2highuid(arg2),
7680                                   low2highuid(arg3)));
7681         break;
7682 #endif
7683 #ifdef TARGET_NR_getresuid
7684     case TARGET_NR_getresuid:
7685         {
7686             uid_t ruid, euid, suid;
7687             ret = get_errno(getresuid(&ruid, &euid, &suid));
7688             if (!is_error(ret)) {
7689                 if (put_user_u16(high2lowuid(ruid), arg1)
7690                     || put_user_u16(high2lowuid(euid), arg2)
7691                     || put_user_u16(high2lowuid(suid), arg3))
7692                     goto efault;
7693             }
7694         }
7695         break;
7696 #endif
7697 #ifdef TARGET_NR_getresgid
7698     case TARGET_NR_setresgid:
7699         ret = get_errno(setresgid(low2highgid(arg1),
7700                                   low2highgid(arg2),
7701                                   low2highgid(arg3)));
7702         break;
7703 #endif
7704 #ifdef TARGET_NR_getresgid
7705     case TARGET_NR_getresgid:
7706         {
7707             gid_t rgid, egid, sgid;
7708             ret = get_errno(getresgid(&rgid, &egid, &sgid));
7709             if (!is_error(ret)) {
7710                 if (put_user_u16(high2lowgid(rgid), arg1)
7711                     || put_user_u16(high2lowgid(egid), arg2)
7712                     || put_user_u16(high2lowgid(sgid), arg3))
7713                     goto efault;
7714             }
7715         }
7716         break;
7717 #endif
7718     case TARGET_NR_chown:
7719         if (!(p = lock_user_string(arg1)))
7720             goto efault;
7721         ret = get_errno(chown(p, low2highuid(arg2), low2highgid(arg3)));
7722         unlock_user(p, arg1, 0);
7723         break;
7724     case TARGET_NR_setuid:
7725         ret = get_errno(setuid(low2highuid(arg1)));
7726         break;
7727     case TARGET_NR_setgid:
7728         ret = get_errno(setgid(low2highgid(arg1)));
7729         break;
7730     case TARGET_NR_setfsuid:
7731         ret = get_errno(setfsuid(arg1));
7732         break;
7733     case TARGET_NR_setfsgid:
7734         ret = get_errno(setfsgid(arg1));
7735         break;
7736 
7737 #ifdef TARGET_NR_lchown32
7738     case TARGET_NR_lchown32:
7739         if (!(p = lock_user_string(arg1)))
7740             goto efault;
7741         ret = get_errno(lchown(p, arg2, arg3));
7742         unlock_user(p, arg1, 0);
7743         break;
7744 #endif
7745 #ifdef TARGET_NR_getuid32
7746     case TARGET_NR_getuid32:
7747         ret = get_errno(getuid());
7748         break;
7749 #endif
7750 
7751 #if defined(TARGET_NR_getxuid) && defined(TARGET_ALPHA)
7752    /* Alpha specific */
7753     case TARGET_NR_getxuid:
7754          {
7755             uid_t euid;
7756             euid=geteuid();
7757             ((CPUAlphaState *)cpu_env)->ir[IR_A4]=euid;
7758          }
7759         ret = get_errno(getuid());
7760         break;
7761 #endif
7762 #if defined(TARGET_NR_getxgid) && defined(TARGET_ALPHA)
7763    /* Alpha specific */
7764     case TARGET_NR_getxgid:
7765          {
7766             uid_t egid;
7767             egid=getegid();
7768             ((CPUAlphaState *)cpu_env)->ir[IR_A4]=egid;
7769          }
7770         ret = get_errno(getgid());
7771         break;
7772 #endif
7773 #if defined(TARGET_NR_osf_getsysinfo) && defined(TARGET_ALPHA)
7774     /* Alpha specific */
7775     case TARGET_NR_osf_getsysinfo:
7776         ret = -TARGET_EOPNOTSUPP;
7777         switch (arg1) {
7778           case TARGET_GSI_IEEE_FP_CONTROL:
7779             {
7780                 uint64_t swcr, fpcr = cpu_alpha_load_fpcr (cpu_env);
7781 
7782                 /* Copied from linux ieee_fpcr_to_swcr.  */
7783                 swcr = (fpcr >> 35) & SWCR_STATUS_MASK;
7784                 swcr |= (fpcr >> 36) & SWCR_MAP_DMZ;
7785                 swcr |= (~fpcr >> 48) & (SWCR_TRAP_ENABLE_INV
7786                                         | SWCR_TRAP_ENABLE_DZE
7787                                         | SWCR_TRAP_ENABLE_OVF);
7788                 swcr |= (~fpcr >> 57) & (SWCR_TRAP_ENABLE_UNF
7789                                         | SWCR_TRAP_ENABLE_INE);
7790                 swcr |= (fpcr >> 47) & SWCR_MAP_UMZ;
7791                 swcr |= (~fpcr >> 41) & SWCR_TRAP_ENABLE_DNO;
7792 
7793                 if (put_user_u64 (swcr, arg2))
7794                         goto efault;
7795                 ret = 0;
7796             }
7797             break;
7798 
7799           /* case GSI_IEEE_STATE_AT_SIGNAL:
7800              -- Not implemented in linux kernel.
7801              case GSI_UACPROC:
7802              -- Retrieves current unaligned access state; not much used.
7803              case GSI_PROC_TYPE:
7804              -- Retrieves implver information; surely not used.
7805              case GSI_GET_HWRPB:
7806              -- Grabs a copy of the HWRPB; surely not used.
7807           */
7808         }
7809         break;
7810 #endif
7811 #if defined(TARGET_NR_osf_setsysinfo) && defined(TARGET_ALPHA)
7812     /* Alpha specific */
7813     case TARGET_NR_osf_setsysinfo:
7814         ret = -TARGET_EOPNOTSUPP;
7815         switch (arg1) {
7816           case TARGET_SSI_IEEE_FP_CONTROL:
7817             {
7818                 uint64_t swcr, fpcr, orig_fpcr;
7819 
7820                 if (get_user_u64 (swcr, arg2)) {
7821                     goto efault;
7822                 }
7823                 orig_fpcr = cpu_alpha_load_fpcr(cpu_env);
7824                 fpcr = orig_fpcr & FPCR_DYN_MASK;
7825 
7826                 /* Copied from linux ieee_swcr_to_fpcr.  */
7827                 fpcr |= (swcr & SWCR_STATUS_MASK) << 35;
7828                 fpcr |= (swcr & SWCR_MAP_DMZ) << 36;
7829                 fpcr |= (~swcr & (SWCR_TRAP_ENABLE_INV
7830                                   | SWCR_TRAP_ENABLE_DZE
7831                                   | SWCR_TRAP_ENABLE_OVF)) << 48;
7832                 fpcr |= (~swcr & (SWCR_TRAP_ENABLE_UNF
7833                                   | SWCR_TRAP_ENABLE_INE)) << 57;
7834                 fpcr |= (swcr & SWCR_MAP_UMZ ? FPCR_UNDZ | FPCR_UNFD : 0);
7835                 fpcr |= (~swcr & SWCR_TRAP_ENABLE_DNO) << 41;
7836 
7837                 cpu_alpha_store_fpcr(cpu_env, fpcr);
7838                 ret = 0;
7839             }
7840             break;
7841 
7842           case TARGET_SSI_IEEE_RAISE_EXCEPTION:
7843             {
7844                 uint64_t exc, fpcr, orig_fpcr;
7845                 int si_code;
7846 
7847                 if (get_user_u64(exc, arg2)) {
7848                     goto efault;
7849                 }
7850 
7851                 orig_fpcr = cpu_alpha_load_fpcr(cpu_env);
7852 
7853                 /* We only add to the exception status here.  */
7854                 fpcr = orig_fpcr | ((exc & SWCR_STATUS_MASK) << 35);
7855 
7856                 cpu_alpha_store_fpcr(cpu_env, fpcr);
7857                 ret = 0;
7858 
7859                 /* Old exceptions are not signaled.  */
7860                 fpcr &= ~(orig_fpcr & FPCR_STATUS_MASK);
7861 
7862                 /* If any exceptions set by this call,
7863                    and are unmasked, send a signal.  */
7864                 si_code = 0;
7865                 if ((fpcr & (FPCR_INE | FPCR_INED)) == FPCR_INE) {
7866                     si_code = TARGET_FPE_FLTRES;
7867                 }
7868                 if ((fpcr & (FPCR_UNF | FPCR_UNFD)) == FPCR_UNF) {
7869                     si_code = TARGET_FPE_FLTUND;
7870                 }
7871                 if ((fpcr & (FPCR_OVF | FPCR_OVFD)) == FPCR_OVF) {
7872                     si_code = TARGET_FPE_FLTOVF;
7873                 }
7874                 if ((fpcr & (FPCR_DZE | FPCR_DZED)) == FPCR_DZE) {
7875                     si_code = TARGET_FPE_FLTDIV;
7876                 }
7877                 if ((fpcr & (FPCR_INV | FPCR_INVD)) == FPCR_INV) {
7878                     si_code = TARGET_FPE_FLTINV;
7879                 }
7880                 if (si_code != 0) {
7881                     target_siginfo_t info;
7882                     info.si_signo = SIGFPE;
7883                     info.si_errno = 0;
7884                     info.si_code = si_code;
7885                     info._sifields._sigfault._addr
7886                         = ((CPUArchState *)cpu_env)->pc;
7887                     queue_signal((CPUArchState *)cpu_env, info.si_signo, &info);
7888                 }
7889             }
7890             break;
7891 
7892           /* case SSI_NVPAIRS:
7893              -- Used with SSIN_UACPROC to enable unaligned accesses.
7894              case SSI_IEEE_STATE_AT_SIGNAL:
7895              case SSI_IEEE_IGNORE_STATE_AT_SIGNAL:
7896              -- Not implemented in linux kernel
7897           */
7898         }
7899         break;
7900 #endif
7901 #ifdef TARGET_NR_osf_sigprocmask
7902     /* Alpha specific.  */
7903     case TARGET_NR_osf_sigprocmask:
7904         {
7905             abi_ulong mask;
7906             int how;
7907             sigset_t set, oldset;
7908 
7909             switch(arg1) {
7910             case TARGET_SIG_BLOCK:
7911                 how = SIG_BLOCK;
7912                 break;
7913             case TARGET_SIG_UNBLOCK:
7914                 how = SIG_UNBLOCK;
7915                 break;
7916             case TARGET_SIG_SETMASK:
7917                 how = SIG_SETMASK;
7918                 break;
7919             default:
7920                 ret = -TARGET_EINVAL;
7921                 goto fail;
7922             }
7923             mask = arg2;
7924             target_to_host_old_sigset(&set, &mask);
7925             sigprocmask(how, &set, &oldset);
7926             host_to_target_old_sigset(&mask, &oldset);
7927             ret = mask;
7928         }
7929         break;
7930 #endif
7931 
7932 #ifdef TARGET_NR_getgid32
7933     case TARGET_NR_getgid32:
7934         ret = get_errno(getgid());
7935         break;
7936 #endif
7937 #ifdef TARGET_NR_geteuid32
7938     case TARGET_NR_geteuid32:
7939         ret = get_errno(geteuid());
7940         break;
7941 #endif
7942 #ifdef TARGET_NR_getegid32
7943     case TARGET_NR_getegid32:
7944         ret = get_errno(getegid());
7945         break;
7946 #endif
7947 #ifdef TARGET_NR_setreuid32
7948     case TARGET_NR_setreuid32:
7949         ret = get_errno(setreuid(arg1, arg2));
7950         break;
7951 #endif
7952 #ifdef TARGET_NR_setregid32
7953     case TARGET_NR_setregid32:
7954         ret = get_errno(setregid(arg1, arg2));
7955         break;
7956 #endif
7957 #ifdef TARGET_NR_getgroups32
7958     case TARGET_NR_getgroups32:
7959         {
7960             int gidsetsize = arg1;
7961             uint32_t *target_grouplist;
7962             gid_t *grouplist;
7963             int i;
7964 
7965             grouplist = alloca(gidsetsize * sizeof(gid_t));
7966             ret = get_errno(getgroups(gidsetsize, grouplist));
7967             if (gidsetsize == 0)
7968                 break;
7969             if (!is_error(ret)) {
7970                 target_grouplist = lock_user(VERIFY_WRITE, arg2, gidsetsize * 4, 0);
7971                 if (!target_grouplist) {
7972                     ret = -TARGET_EFAULT;
7973                     goto fail;
7974                 }
7975                 for(i = 0;i < ret; i++)
7976                     target_grouplist[i] = tswap32(grouplist[i]);
7977                 unlock_user(target_grouplist, arg2, gidsetsize * 4);
7978             }
7979         }
7980         break;
7981 #endif
7982 #ifdef TARGET_NR_setgroups32
7983     case TARGET_NR_setgroups32:
7984         {
7985             int gidsetsize = arg1;
7986             uint32_t *target_grouplist;
7987             gid_t *grouplist;
7988             int i;
7989 
7990             grouplist = alloca(gidsetsize * sizeof(gid_t));
7991             target_grouplist = lock_user(VERIFY_READ, arg2, gidsetsize * 4, 1);
7992             if (!target_grouplist) {
7993                 ret = -TARGET_EFAULT;
7994                 goto fail;
7995             }
7996             for(i = 0;i < gidsetsize; i++)
7997                 grouplist[i] = tswap32(target_grouplist[i]);
7998             unlock_user(target_grouplist, arg2, 0);
7999             ret = get_errno(setgroups(gidsetsize, grouplist));
8000         }
8001         break;
8002 #endif
8003 #ifdef TARGET_NR_fchown32
8004     case TARGET_NR_fchown32:
8005         ret = get_errno(fchown(arg1, arg2, arg3));
8006         break;
8007 #endif
8008 #ifdef TARGET_NR_setresuid32
8009     case TARGET_NR_setresuid32:
8010         ret = get_errno(setresuid(arg1, arg2, arg3));
8011         break;
8012 #endif
8013 #ifdef TARGET_NR_getresuid32
8014     case TARGET_NR_getresuid32:
8015         {
8016             uid_t ruid, euid, suid;
8017             ret = get_errno(getresuid(&ruid, &euid, &suid));
8018             if (!is_error(ret)) {
8019                 if (put_user_u32(ruid, arg1)
8020                     || put_user_u32(euid, arg2)
8021                     || put_user_u32(suid, arg3))
8022                     goto efault;
8023             }
8024         }
8025         break;
8026 #endif
8027 #ifdef TARGET_NR_setresgid32
8028     case TARGET_NR_setresgid32:
8029         ret = get_errno(setresgid(arg1, arg2, arg3));
8030         break;
8031 #endif
8032 #ifdef TARGET_NR_getresgid32
8033     case TARGET_NR_getresgid32:
8034         {
8035             gid_t rgid, egid, sgid;
8036             ret = get_errno(getresgid(&rgid, &egid, &sgid));
8037             if (!is_error(ret)) {
8038                 if (put_user_u32(rgid, arg1)
8039                     || put_user_u32(egid, arg2)
8040                     || put_user_u32(sgid, arg3))
8041                     goto efault;
8042             }
8043         }
8044         break;
8045 #endif
8046 #ifdef TARGET_NR_chown32
8047     case TARGET_NR_chown32:
8048         if (!(p = lock_user_string(arg1)))
8049             goto efault;
8050         ret = get_errno(chown(p, arg2, arg3));
8051         unlock_user(p, arg1, 0);
8052         break;
8053 #endif
8054 #ifdef TARGET_NR_setuid32
8055     case TARGET_NR_setuid32:
8056         ret = get_errno(setuid(arg1));
8057         break;
8058 #endif
8059 #ifdef TARGET_NR_setgid32
8060     case TARGET_NR_setgid32:
8061         ret = get_errno(setgid(arg1));
8062         break;
8063 #endif
8064 #ifdef TARGET_NR_setfsuid32
8065     case TARGET_NR_setfsuid32:
8066         ret = get_errno(setfsuid(arg1));
8067         break;
8068 #endif
8069 #ifdef TARGET_NR_setfsgid32
8070     case TARGET_NR_setfsgid32:
8071         ret = get_errno(setfsgid(arg1));
8072         break;
8073 #endif
8074 
8075     case TARGET_NR_pivot_root:
8076         goto unimplemented;
8077 #ifdef TARGET_NR_mincore
8078     case TARGET_NR_mincore:
8079         {
8080             void *a;
8081             ret = -TARGET_EFAULT;
8082             if (!(a = lock_user(VERIFY_READ, arg1,arg2, 0)))
8083                 goto efault;
8084             if (!(p = lock_user_string(arg3)))
8085                 goto mincore_fail;
8086             ret = get_errno(mincore(a, arg2, p));
8087             unlock_user(p, arg3, ret);
8088             mincore_fail:
8089             unlock_user(a, arg1, 0);
8090         }
8091         break;
8092 #endif
8093 #ifdef TARGET_NR_arm_fadvise64_64
8094     case TARGET_NR_arm_fadvise64_64:
8095 	{
8096 		/*
8097 		 * arm_fadvise64_64 looks like fadvise64_64 but
8098 		 * with different argument order
8099 		 */
8100 		abi_long temp;
8101 		temp = arg3;
8102 		arg3 = arg4;
8103 		arg4 = temp;
8104 	}
8105 #endif
8106 #if defined(TARGET_NR_fadvise64_64) || defined(TARGET_NR_arm_fadvise64_64) || defined(TARGET_NR_fadvise64)
8107 #ifdef TARGET_NR_fadvise64_64
8108     case TARGET_NR_fadvise64_64:
8109 #endif
8110 #ifdef TARGET_NR_fadvise64
8111     case TARGET_NR_fadvise64:
8112 #endif
8113 #ifdef TARGET_S390X
8114         switch (arg4) {
8115         case 4: arg4 = POSIX_FADV_NOREUSE + 1; break; /* make sure it's an invalid value */
8116         case 5: arg4 = POSIX_FADV_NOREUSE + 2; break; /* ditto */
8117         case 6: arg4 = POSIX_FADV_DONTNEED; break;
8118         case 7: arg4 = POSIX_FADV_NOREUSE; break;
8119         default: break;
8120         }
8121 #endif
8122         ret = -posix_fadvise(arg1, arg2, arg3, arg4);
8123 	break;
8124 #endif
8125 #ifdef TARGET_NR_madvise
8126     case TARGET_NR_madvise:
8127         /* A straight passthrough may not be safe because qemu sometimes
8128            turns private file-backed mappings into anonymous mappings.
8129            This will break MADV_DONTNEED.
8130            This is a hint, so ignoring and returning success is ok.  */
8131         ret = get_errno(0);
8132         break;
8133 #endif
8134 #if TARGET_ABI_BITS == 32
8135     case TARGET_NR_fcntl64:
8136     {
8137 	int cmd;
8138 	struct flock64 fl;
8139 	struct target_flock64 *target_fl;
8140 #ifdef TARGET_ARM
8141 	struct target_eabi_flock64 *target_efl;
8142 #endif
8143 
8144 	cmd = target_to_host_fcntl_cmd(arg2);
8145         if (cmd == -TARGET_EINVAL) {
8146             ret = cmd;
8147             break;
8148         }
8149 
8150         switch(arg2) {
8151         case TARGET_F_GETLK64:
8152 #ifdef TARGET_ARM
8153             if (((CPUARMState *)cpu_env)->eabi) {
8154                 if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
8155                     goto efault;
8156                 fl.l_type = tswap16(target_efl->l_type);
8157                 fl.l_whence = tswap16(target_efl->l_whence);
8158                 fl.l_start = tswap64(target_efl->l_start);
8159                 fl.l_len = tswap64(target_efl->l_len);
8160                 fl.l_pid = tswap32(target_efl->l_pid);
8161                 unlock_user_struct(target_efl, arg3, 0);
8162             } else
8163 #endif
8164             {
8165                 if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
8166                     goto efault;
8167                 fl.l_type = tswap16(target_fl->l_type);
8168                 fl.l_whence = tswap16(target_fl->l_whence);
8169                 fl.l_start = tswap64(target_fl->l_start);
8170                 fl.l_len = tswap64(target_fl->l_len);
8171                 fl.l_pid = tswap32(target_fl->l_pid);
8172                 unlock_user_struct(target_fl, arg3, 0);
8173             }
8174             ret = get_errno(fcntl(arg1, cmd, &fl));
8175 	    if (ret == 0) {
8176 #ifdef TARGET_ARM
8177                 if (((CPUARMState *)cpu_env)->eabi) {
8178                     if (!lock_user_struct(VERIFY_WRITE, target_efl, arg3, 0))
8179                         goto efault;
8180                     target_efl->l_type = tswap16(fl.l_type);
8181                     target_efl->l_whence = tswap16(fl.l_whence);
8182                     target_efl->l_start = tswap64(fl.l_start);
8183                     target_efl->l_len = tswap64(fl.l_len);
8184                     target_efl->l_pid = tswap32(fl.l_pid);
8185                     unlock_user_struct(target_efl, arg3, 1);
8186                 } else
8187 #endif
8188                 {
8189                     if (!lock_user_struct(VERIFY_WRITE, target_fl, arg3, 0))
8190                         goto efault;
8191                     target_fl->l_type = tswap16(fl.l_type);
8192                     target_fl->l_whence = tswap16(fl.l_whence);
8193                     target_fl->l_start = tswap64(fl.l_start);
8194                     target_fl->l_len = tswap64(fl.l_len);
8195                     target_fl->l_pid = tswap32(fl.l_pid);
8196                     unlock_user_struct(target_fl, arg3, 1);
8197                 }
8198 	    }
8199 	    break;
8200 
8201         case TARGET_F_SETLK64:
8202         case TARGET_F_SETLKW64:
8203 #ifdef TARGET_ARM
8204             if (((CPUARMState *)cpu_env)->eabi) {
8205                 if (!lock_user_struct(VERIFY_READ, target_efl, arg3, 1))
8206                     goto efault;
8207                 fl.l_type = tswap16(target_efl->l_type);
8208                 fl.l_whence = tswap16(target_efl->l_whence);
8209                 fl.l_start = tswap64(target_efl->l_start);
8210                 fl.l_len = tswap64(target_efl->l_len);
8211                 fl.l_pid = tswap32(target_efl->l_pid);
8212                 unlock_user_struct(target_efl, arg3, 0);
8213             } else
8214 #endif
8215             {
8216                 if (!lock_user_struct(VERIFY_READ, target_fl, arg3, 1))
8217                     goto efault;
8218                 fl.l_type = tswap16(target_fl->l_type);
8219                 fl.l_whence = tswap16(target_fl->l_whence);
8220                 fl.l_start = tswap64(target_fl->l_start);
8221                 fl.l_len = tswap64(target_fl->l_len);
8222                 fl.l_pid = tswap32(target_fl->l_pid);
8223                 unlock_user_struct(target_fl, arg3, 0);
8224             }
8225             ret = get_errno(fcntl(arg1, cmd, &fl));
8226 	    break;
8227         default:
8228             ret = do_fcntl(arg1, arg2, arg3);
8229             break;
8230         }
8231 	break;
8232     }
8233 #endif
8234 #ifdef TARGET_NR_cacheflush
8235     case TARGET_NR_cacheflush:
8236         /* self-modifying code is handled automatically, so nothing needed */
8237         ret = 0;
8238         break;
8239 #endif
8240 #ifdef TARGET_NR_security
8241     case TARGET_NR_security:
8242         goto unimplemented;
8243 #endif
8244 #ifdef TARGET_NR_getpagesize
8245     case TARGET_NR_getpagesize:
8246         ret = TARGET_PAGE_SIZE;
8247         break;
8248 #endif
8249     case TARGET_NR_gettid:
8250         ret = get_errno(gettid());
8251         break;
8252 #ifdef TARGET_NR_readahead
8253     case TARGET_NR_readahead:
8254 #if TARGET_ABI_BITS == 32
8255         if (regpairs_aligned(cpu_env)) {
8256             arg2 = arg3;
8257             arg3 = arg4;
8258             arg4 = arg5;
8259         }
8260         ret = get_errno(readahead(arg1, ((off64_t)arg3 << 32) | arg2, arg4));
8261 #else
8262         ret = get_errno(readahead(arg1, arg2, arg3));
8263 #endif
8264         break;
8265 #endif
8266 #ifdef CONFIG_ATTR
8267 #ifdef TARGET_NR_setxattr
8268     case TARGET_NR_listxattr:
8269     case TARGET_NR_llistxattr:
8270     {
8271         void *p, *b = 0;
8272         if (arg2) {
8273             b = lock_user(VERIFY_WRITE, arg2, arg3, 0);
8274             if (!b) {
8275                 ret = -TARGET_EFAULT;
8276                 break;
8277             }
8278         }
8279         p = lock_user_string(arg1);
8280         if (p) {
8281             if (num == TARGET_NR_listxattr) {
8282                 ret = get_errno(listxattr(p, b, arg3));
8283             } else {
8284                 ret = get_errno(llistxattr(p, b, arg3));
8285             }
8286         } else {
8287             ret = -TARGET_EFAULT;
8288         }
8289         unlock_user(p, arg1, 0);
8290         unlock_user(b, arg2, arg3);
8291         break;
8292     }
8293     case TARGET_NR_flistxattr:
8294     {
8295         void *b = 0;
8296         if (arg2) {
8297             b = lock_user(VERIFY_WRITE, arg2, arg3, 0);
8298             if (!b) {
8299                 ret = -TARGET_EFAULT;
8300                 break;
8301             }
8302         }
8303         ret = get_errno(flistxattr(arg1, b, arg3));
8304         unlock_user(b, arg2, arg3);
8305         break;
8306     }
8307     case TARGET_NR_setxattr:
8308     case TARGET_NR_lsetxattr:
8309         {
8310             void *p, *n, *v = 0;
8311             if (arg3) {
8312                 v = lock_user(VERIFY_READ, arg3, arg4, 1);
8313                 if (!v) {
8314                     ret = -TARGET_EFAULT;
8315                     break;
8316                 }
8317             }
8318             p = lock_user_string(arg1);
8319             n = lock_user_string(arg2);
8320             if (p && n) {
8321                 if (num == TARGET_NR_setxattr) {
8322                     ret = get_errno(setxattr(p, n, v, arg4, arg5));
8323                 } else {
8324                     ret = get_errno(lsetxattr(p, n, v, arg4, arg5));
8325                 }
8326             } else {
8327                 ret = -TARGET_EFAULT;
8328             }
8329             unlock_user(p, arg1, 0);
8330             unlock_user(n, arg2, 0);
8331             unlock_user(v, arg3, 0);
8332         }
8333         break;
8334     case TARGET_NR_fsetxattr:
8335         {
8336             void *n, *v = 0;
8337             if (arg3) {
8338                 v = lock_user(VERIFY_READ, arg3, arg4, 1);
8339                 if (!v) {
8340                     ret = -TARGET_EFAULT;
8341                     break;
8342                 }
8343             }
8344             n = lock_user_string(arg2);
8345             if (n) {
8346                 ret = get_errno(fsetxattr(arg1, n, v, arg4, arg5));
8347             } else {
8348                 ret = -TARGET_EFAULT;
8349             }
8350             unlock_user(n, arg2, 0);
8351             unlock_user(v, arg3, 0);
8352         }
8353         break;
8354     case TARGET_NR_getxattr:
8355     case TARGET_NR_lgetxattr:
8356         {
8357             void *p, *n, *v = 0;
8358             if (arg3) {
8359                 v = lock_user(VERIFY_WRITE, arg3, arg4, 0);
8360                 if (!v) {
8361                     ret = -TARGET_EFAULT;
8362                     break;
8363                 }
8364             }
8365             p = lock_user_string(arg1);
8366             n = lock_user_string(arg2);
8367             if (p && n) {
8368                 if (num == TARGET_NR_getxattr) {
8369                     ret = get_errno(getxattr(p, n, v, arg4));
8370                 } else {
8371                     ret = get_errno(lgetxattr(p, n, v, arg4));
8372                 }
8373             } else {
8374                 ret = -TARGET_EFAULT;
8375             }
8376             unlock_user(p, arg1, 0);
8377             unlock_user(n, arg2, 0);
8378             unlock_user(v, arg3, arg4);
8379         }
8380         break;
8381     case TARGET_NR_fgetxattr:
8382         {
8383             void *n, *v = 0;
8384             if (arg3) {
8385                 v = lock_user(VERIFY_WRITE, arg3, arg4, 0);
8386                 if (!v) {
8387                     ret = -TARGET_EFAULT;
8388                     break;
8389                 }
8390             }
8391             n = lock_user_string(arg2);
8392             if (n) {
8393                 ret = get_errno(fgetxattr(arg1, n, v, arg4));
8394             } else {
8395                 ret = -TARGET_EFAULT;
8396             }
8397             unlock_user(n, arg2, 0);
8398             unlock_user(v, arg3, arg4);
8399         }
8400         break;
8401     case TARGET_NR_removexattr:
8402     case TARGET_NR_lremovexattr:
8403         {
8404             void *p, *n;
8405             p = lock_user_string(arg1);
8406             n = lock_user_string(arg2);
8407             if (p && n) {
8408                 if (num == TARGET_NR_removexattr) {
8409                     ret = get_errno(removexattr(p, n));
8410                 } else {
8411                     ret = get_errno(lremovexattr(p, n));
8412                 }
8413             } else {
8414                 ret = -TARGET_EFAULT;
8415             }
8416             unlock_user(p, arg1, 0);
8417             unlock_user(n, arg2, 0);
8418         }
8419         break;
8420     case TARGET_NR_fremovexattr:
8421         {
8422             void *n;
8423             n = lock_user_string(arg2);
8424             if (n) {
8425                 ret = get_errno(fremovexattr(arg1, n));
8426             } else {
8427                 ret = -TARGET_EFAULT;
8428             }
8429             unlock_user(n, arg2, 0);
8430         }
8431         break;
8432 #endif
8433 #endif /* CONFIG_ATTR */
8434 #ifdef TARGET_NR_set_thread_area
8435     case TARGET_NR_set_thread_area:
8436 #if defined(TARGET_MIPS)
8437       ((CPUMIPSState *) cpu_env)->tls_value = arg1;
8438       ret = 0;
8439       break;
8440 #elif defined(TARGET_CRIS)
8441       if (arg1 & 0xff)
8442           ret = -TARGET_EINVAL;
8443       else {
8444           ((CPUCRISState *) cpu_env)->pregs[PR_PID] = arg1;
8445           ret = 0;
8446       }
8447       break;
8448 #elif defined(TARGET_I386) && defined(TARGET_ABI32)
8449       ret = do_set_thread_area(cpu_env, arg1);
8450       break;
8451 #else
8452       goto unimplemented_nowarn;
8453 #endif
8454 #endif
8455 #ifdef TARGET_NR_get_thread_area
8456     case TARGET_NR_get_thread_area:
8457 #if defined(TARGET_I386) && defined(TARGET_ABI32)
8458         ret = do_get_thread_area(cpu_env, arg1);
8459 #else
8460         goto unimplemented_nowarn;
8461 #endif
8462 #endif
8463 #ifdef TARGET_NR_getdomainname
8464     case TARGET_NR_getdomainname:
8465         goto unimplemented_nowarn;
8466 #endif
8467 
8468 #ifdef TARGET_NR_clock_gettime
8469     case TARGET_NR_clock_gettime:
8470     {
8471         struct timespec ts;
8472         ret = get_errno(clock_gettime(arg1, &ts));
8473         if (!is_error(ret)) {
8474             host_to_target_timespec(arg2, &ts);
8475         }
8476         break;
8477     }
8478 #endif
8479 #ifdef TARGET_NR_clock_getres
8480     case TARGET_NR_clock_getres:
8481     {
8482         struct timespec ts;
8483         ret = get_errno(clock_getres(arg1, &ts));
8484         if (!is_error(ret)) {
8485             host_to_target_timespec(arg2, &ts);
8486         }
8487         break;
8488     }
8489 #endif
8490 #ifdef TARGET_NR_clock_nanosleep
8491     case TARGET_NR_clock_nanosleep:
8492     {
8493         struct timespec ts;
8494         target_to_host_timespec(&ts, arg3);
8495         ret = get_errno(clock_nanosleep(arg1, arg2, &ts, arg4 ? &ts : NULL));
8496         if (arg4)
8497             host_to_target_timespec(arg4, &ts);
8498         break;
8499     }
8500 #endif
8501 
8502 #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
8503     case TARGET_NR_set_tid_address:
8504         ret = get_errno(set_tid_address((int *)g2h(arg1)));
8505         break;
8506 #endif
8507 
8508 #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
8509     case TARGET_NR_tkill:
8510         ret = get_errno(sys_tkill((int)arg1, target_to_host_signal(arg2)));
8511         break;
8512 #endif
8513 
8514 #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
8515     case TARGET_NR_tgkill:
8516 	ret = get_errno(sys_tgkill((int)arg1, (int)arg2,
8517                         target_to_host_signal(arg3)));
8518 	break;
8519 #endif
8520 
8521 #ifdef TARGET_NR_set_robust_list
8522     case TARGET_NR_set_robust_list:
8523     case TARGET_NR_get_robust_list:
8524         /* The ABI for supporting robust futexes has userspace pass
8525          * the kernel a pointer to a linked list which is updated by
8526          * userspace after the syscall; the list is walked by the kernel
8527          * when the thread exits. Since the linked list in QEMU guest
8528          * memory isn't a valid linked list for the host and we have
8529          * no way to reliably intercept the thread-death event, we can't
8530          * support these. Silently return ENOSYS so that guest userspace
8531          * falls back to a non-robust futex implementation (which should
8532          * be OK except in the corner case of the guest crashing while
8533          * holding a mutex that is shared with another process via
8534          * shared memory).
8535          */
8536         goto unimplemented_nowarn;
8537 #endif
8538 
8539 #if defined(TARGET_NR_utimensat) && defined(__NR_utimensat)
8540     case TARGET_NR_utimensat:
8541         {
8542             struct timespec *tsp, ts[2];
8543             if (!arg3) {
8544                 tsp = NULL;
8545             } else {
8546                 target_to_host_timespec(ts, arg3);
8547                 target_to_host_timespec(ts+1, arg3+sizeof(struct target_timespec));
8548                 tsp = ts;
8549             }
8550             if (!arg2)
8551                 ret = get_errno(sys_utimensat(arg1, NULL, tsp, arg4));
8552             else {
8553                 if (!(p = lock_user_string(arg2))) {
8554                     ret = -TARGET_EFAULT;
8555                     goto fail;
8556                 }
8557                 ret = get_errno(sys_utimensat(arg1, path(p), tsp, arg4));
8558                 unlock_user(p, arg2, 0);
8559             }
8560         }
8561 	break;
8562 #endif
8563 #if defined(CONFIG_USE_NPTL)
8564     case TARGET_NR_futex:
8565         ret = do_futex(arg1, arg2, arg3, arg4, arg5, arg6);
8566         break;
8567 #endif
8568 #if defined(TARGET_NR_inotify_init) && defined(__NR_inotify_init)
8569     case TARGET_NR_inotify_init:
8570         ret = get_errno(sys_inotify_init());
8571         break;
8572 #endif
8573 #ifdef CONFIG_INOTIFY1
8574 #if defined(TARGET_NR_inotify_init1) && defined(__NR_inotify_init1)
8575     case TARGET_NR_inotify_init1:
8576         ret = get_errno(sys_inotify_init1(arg1));
8577         break;
8578 #endif
8579 #endif
8580 #if defined(TARGET_NR_inotify_add_watch) && defined(__NR_inotify_add_watch)
8581     case TARGET_NR_inotify_add_watch:
8582         p = lock_user_string(arg2);
8583         ret = get_errno(sys_inotify_add_watch(arg1, path(p), arg3));
8584         unlock_user(p, arg2, 0);
8585         break;
8586 #endif
8587 #if defined(TARGET_NR_inotify_rm_watch) && defined(__NR_inotify_rm_watch)
8588     case TARGET_NR_inotify_rm_watch:
8589         ret = get_errno(sys_inotify_rm_watch(arg1, arg2));
8590         break;
8591 #endif
8592 
8593 #if defined(TARGET_NR_mq_open) && defined(__NR_mq_open)
8594     case TARGET_NR_mq_open:
8595         {
8596             struct mq_attr posix_mq_attr;
8597 
8598             p = lock_user_string(arg1 - 1);
8599             if (arg4 != 0)
8600                 copy_from_user_mq_attr (&posix_mq_attr, arg4);
8601             ret = get_errno(mq_open(p, arg2, arg3, &posix_mq_attr));
8602             unlock_user (p, arg1, 0);
8603         }
8604         break;
8605 
8606     case TARGET_NR_mq_unlink:
8607         p = lock_user_string(arg1 - 1);
8608         ret = get_errno(mq_unlink(p));
8609         unlock_user (p, arg1, 0);
8610         break;
8611 
8612     case TARGET_NR_mq_timedsend:
8613         {
8614             struct timespec ts;
8615 
8616             p = lock_user (VERIFY_READ, arg2, arg3, 1);
8617             if (arg5 != 0) {
8618                 target_to_host_timespec(&ts, arg5);
8619                 ret = get_errno(mq_timedsend(arg1, p, arg3, arg4, &ts));
8620                 host_to_target_timespec(arg5, &ts);
8621             }
8622             else
8623                 ret = get_errno(mq_send(arg1, p, arg3, arg4));
8624             unlock_user (p, arg2, arg3);
8625         }
8626         break;
8627 
8628     case TARGET_NR_mq_timedreceive:
8629         {
8630             struct timespec ts;
8631             unsigned int prio;
8632 
8633             p = lock_user (VERIFY_READ, arg2, arg3, 1);
8634             if (arg5 != 0) {
8635                 target_to_host_timespec(&ts, arg5);
8636                 ret = get_errno(mq_timedreceive(arg1, p, arg3, &prio, &ts));
8637                 host_to_target_timespec(arg5, &ts);
8638             }
8639             else
8640                 ret = get_errno(mq_receive(arg1, p, arg3, &prio));
8641             unlock_user (p, arg2, arg3);
8642             if (arg4 != 0)
8643                 put_user_u32(prio, arg4);
8644         }
8645         break;
8646 
8647     /* Not implemented for now... */
8648 /*     case TARGET_NR_mq_notify: */
8649 /*         break; */
8650 
8651     case TARGET_NR_mq_getsetattr:
8652         {
8653             struct mq_attr posix_mq_attr_in, posix_mq_attr_out;
8654             ret = 0;
8655             if (arg3 != 0) {
8656                 ret = mq_getattr(arg1, &posix_mq_attr_out);
8657                 copy_to_user_mq_attr(arg3, &posix_mq_attr_out);
8658             }
8659             if (arg2 != 0) {
8660                 copy_from_user_mq_attr(&posix_mq_attr_in, arg2);
8661                 ret |= mq_setattr(arg1, &posix_mq_attr_in, &posix_mq_attr_out);
8662             }
8663 
8664         }
8665         break;
8666 #endif
8667 
8668 #ifdef CONFIG_SPLICE
8669 #ifdef TARGET_NR_tee
8670     case TARGET_NR_tee:
8671         {
8672             ret = get_errno(tee(arg1,arg2,arg3,arg4));
8673         }
8674         break;
8675 #endif
8676 #ifdef TARGET_NR_splice
8677     case TARGET_NR_splice:
8678         {
8679             loff_t loff_in, loff_out;
8680             loff_t *ploff_in = NULL, *ploff_out = NULL;
8681             if(arg2) {
8682                 get_user_u64(loff_in, arg2);
8683                 ploff_in = &loff_in;
8684             }
8685             if(arg4) {
8686                 get_user_u64(loff_out, arg2);
8687                 ploff_out = &loff_out;
8688             }
8689             ret = get_errno(splice(arg1, ploff_in, arg3, ploff_out, arg5, arg6));
8690         }
8691         break;
8692 #endif
8693 #ifdef TARGET_NR_vmsplice
8694 	case TARGET_NR_vmsplice:
8695         {
8696             struct iovec *vec = lock_iovec(VERIFY_READ, arg2, arg3, 1);
8697             if (vec != NULL) {
8698                 ret = get_errno(vmsplice(arg1, vec, arg3, arg4));
8699                 unlock_iovec(vec, arg2, arg3, 0);
8700             } else {
8701                 ret = -host_to_target_errno(errno);
8702             }
8703         }
8704         break;
8705 #endif
8706 #endif /* CONFIG_SPLICE */
8707 #ifdef CONFIG_EVENTFD
8708 #if defined(TARGET_NR_eventfd)
8709     case TARGET_NR_eventfd:
8710         ret = get_errno(eventfd(arg1, 0));
8711         break;
8712 #endif
8713 #if defined(TARGET_NR_eventfd2)
8714     case TARGET_NR_eventfd2:
8715     {
8716         int host_flags = arg2 & (~(TARGET_O_NONBLOCK | TARGET_O_CLOEXEC));
8717         if (arg2 & TARGET_O_NONBLOCK) {
8718             host_flags |= O_NONBLOCK;
8719         }
8720         if (arg2 & TARGET_O_CLOEXEC) {
8721             host_flags |= O_CLOEXEC;
8722         }
8723         ret = get_errno(eventfd(arg1, host_flags));
8724         break;
8725     }
8726 #endif
8727 #endif /* CONFIG_EVENTFD  */
8728 #if defined(CONFIG_FALLOCATE) && defined(TARGET_NR_fallocate)
8729     case TARGET_NR_fallocate:
8730 #if TARGET_ABI_BITS == 32
8731         ret = get_errno(fallocate(arg1, arg2, target_offset64(arg3, arg4),
8732                                   target_offset64(arg5, arg6)));
8733 #else
8734         ret = get_errno(fallocate(arg1, arg2, arg3, arg4));
8735 #endif
8736         break;
8737 #endif
8738 #if defined(CONFIG_SYNC_FILE_RANGE)
8739 #if defined(TARGET_NR_sync_file_range)
8740     case TARGET_NR_sync_file_range:
8741 #if TARGET_ABI_BITS == 32
8742 #if defined(TARGET_MIPS)
8743         ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
8744                                         target_offset64(arg5, arg6), arg7));
8745 #else
8746         ret = get_errno(sync_file_range(arg1, target_offset64(arg2, arg3),
8747                                         target_offset64(arg4, arg5), arg6));
8748 #endif /* !TARGET_MIPS */
8749 #else
8750         ret = get_errno(sync_file_range(arg1, arg2, arg3, arg4));
8751 #endif
8752         break;
8753 #endif
8754 #if defined(TARGET_NR_sync_file_range2)
8755     case TARGET_NR_sync_file_range2:
8756         /* This is like sync_file_range but the arguments are reordered */
8757 #if TARGET_ABI_BITS == 32
8758         ret = get_errno(sync_file_range(arg1, target_offset64(arg3, arg4),
8759                                         target_offset64(arg5, arg6), arg2));
8760 #else
8761         ret = get_errno(sync_file_range(arg1, arg3, arg4, arg2));
8762 #endif
8763         break;
8764 #endif
8765 #endif
8766 #if defined(CONFIG_EPOLL)
8767 #if defined(TARGET_NR_epoll_create)
8768     case TARGET_NR_epoll_create:
8769         ret = get_errno(epoll_create(arg1));
8770         break;
8771 #endif
8772 #if defined(TARGET_NR_epoll_create1) && defined(CONFIG_EPOLL_CREATE1)
8773     case TARGET_NR_epoll_create1:
8774         ret = get_errno(epoll_create1(arg1));
8775         break;
8776 #endif
8777 #if defined(TARGET_NR_epoll_ctl)
8778     case TARGET_NR_epoll_ctl:
8779     {
8780         struct epoll_event ep;
8781         struct epoll_event *epp = 0;
8782         if (arg4) {
8783             struct target_epoll_event *target_ep;
8784             if (!lock_user_struct(VERIFY_READ, target_ep, arg4, 1)) {
8785                 goto efault;
8786             }
8787             ep.events = tswap32(target_ep->events);
8788             /* The epoll_data_t union is just opaque data to the kernel,
8789              * so we transfer all 64 bits across and need not worry what
8790              * actual data type it is.
8791              */
8792             ep.data.u64 = tswap64(target_ep->data.u64);
8793             unlock_user_struct(target_ep, arg4, 0);
8794             epp = &ep;
8795         }
8796         ret = get_errno(epoll_ctl(arg1, arg2, arg3, epp));
8797         break;
8798     }
8799 #endif
8800 
8801 #if defined(TARGET_NR_epoll_pwait) && defined(CONFIG_EPOLL_PWAIT)
8802 #define IMPLEMENT_EPOLL_PWAIT
8803 #endif
8804 #if defined(TARGET_NR_epoll_wait) || defined(IMPLEMENT_EPOLL_PWAIT)
8805 #if defined(TARGET_NR_epoll_wait)
8806     case TARGET_NR_epoll_wait:
8807 #endif
8808 #if defined(IMPLEMENT_EPOLL_PWAIT)
8809     case TARGET_NR_epoll_pwait:
8810 #endif
8811     {
8812         struct target_epoll_event *target_ep;
8813         struct epoll_event *ep;
8814         int epfd = arg1;
8815         int maxevents = arg3;
8816         int timeout = arg4;
8817 
8818         target_ep = lock_user(VERIFY_WRITE, arg2,
8819                               maxevents * sizeof(struct target_epoll_event), 1);
8820         if (!target_ep) {
8821             goto efault;
8822         }
8823 
8824         ep = alloca(maxevents * sizeof(struct epoll_event));
8825 
8826         switch (num) {
8827 #if defined(IMPLEMENT_EPOLL_PWAIT)
8828         case TARGET_NR_epoll_pwait:
8829         {
8830             target_sigset_t *target_set;
8831             sigset_t _set, *set = &_set;
8832 
8833             if (arg5) {
8834                 target_set = lock_user(VERIFY_READ, arg5,
8835                                        sizeof(target_sigset_t), 1);
8836                 if (!target_set) {
8837                     unlock_user(target_ep, arg2, 0);
8838                     goto efault;
8839                 }
8840                 target_to_host_sigset(set, target_set);
8841                 unlock_user(target_set, arg5, 0);
8842             } else {
8843                 set = NULL;
8844             }
8845 
8846             ret = get_errno(epoll_pwait(epfd, ep, maxevents, timeout, set));
8847             break;
8848         }
8849 #endif
8850 #if defined(TARGET_NR_epoll_wait)
8851         case TARGET_NR_epoll_wait:
8852             ret = get_errno(epoll_wait(epfd, ep, maxevents, timeout));
8853             break;
8854 #endif
8855         default:
8856             ret = -TARGET_ENOSYS;
8857         }
8858         if (!is_error(ret)) {
8859             int i;
8860             for (i = 0; i < ret; i++) {
8861                 target_ep[i].events = tswap32(ep[i].events);
8862                 target_ep[i].data.u64 = tswap64(ep[i].data.u64);
8863             }
8864         }
8865         unlock_user(target_ep, arg2, ret * sizeof(struct target_epoll_event));
8866         break;
8867     }
8868 #endif
8869 #endif
8870 #ifdef TARGET_NR_prlimit64
8871     case TARGET_NR_prlimit64:
8872     {
8873         /* args: pid, resource number, ptr to new rlimit, ptr to old rlimit */
8874         struct target_rlimit64 *target_rnew, *target_rold;
8875         struct host_rlimit64 rnew, rold, *rnewp = 0;
8876         if (arg3) {
8877             if (!lock_user_struct(VERIFY_READ, target_rnew, arg3, 1)) {
8878                 goto efault;
8879             }
8880             rnew.rlim_cur = tswap64(target_rnew->rlim_cur);
8881             rnew.rlim_max = tswap64(target_rnew->rlim_max);
8882             unlock_user_struct(target_rnew, arg3, 0);
8883             rnewp = &rnew;
8884         }
8885 
8886         ret = get_errno(sys_prlimit64(arg1, arg2, rnewp, arg4 ? &rold : 0));
8887         if (!is_error(ret) && arg4) {
8888             if (!lock_user_struct(VERIFY_WRITE, target_rold, arg4, 1)) {
8889                 goto efault;
8890             }
8891             target_rold->rlim_cur = tswap64(rold.rlim_cur);
8892             target_rold->rlim_max = tswap64(rold.rlim_max);
8893             unlock_user_struct(target_rold, arg4, 1);
8894         }
8895         break;
8896     }
8897 #endif
8898 #ifdef TARGET_NR_gethostname
8899     case TARGET_NR_gethostname:
8900     {
8901         char *name = lock_user(VERIFY_WRITE, arg1, arg2, 0);
8902         if (name) {
8903             ret = get_errno(gethostname(name, arg2));
8904             unlock_user(name, arg1, arg2);
8905         } else {
8906             ret = -TARGET_EFAULT;
8907         }
8908         break;
8909     }
8910 #endif
8911     default:
8912     unimplemented:
8913         gemu_log("qemu: Unsupported syscall: %d\n", num);
8914 #if defined(TARGET_NR_setxattr) || defined(TARGET_NR_get_thread_area) || defined(TARGET_NR_getdomainname) || defined(TARGET_NR_set_robust_list)
8915     unimplemented_nowarn:
8916 #endif
8917         ret = -TARGET_ENOSYS;
8918         break;
8919     }
8920 fail:
8921 #ifdef DEBUG
8922     gemu_log(" = " TARGET_ABI_FMT_ld "\n", ret);
8923 #endif
8924     if(do_strace)
8925         print_syscall_ret(num, ret);
8926     return ret;
8927 efault:
8928     ret = -TARGET_EFAULT;
8929     goto fail;
8930 }
8931