linux-user: Fix up timer id handling
[qemu.git] / linux-user / syscall.c
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 <linux/capability.h>
47 #include <signal.h>
48 #include <sched.h>
49 #ifdef __ia64__
50 int __clone2(int (*fn)(void *), void *child_stack_base,
51 size_t stack_size, int flags, void *arg, ...);
52 #endif
53 #include <sys/socket.h>
54 #include <sys/un.h>
55 #include <sys/uio.h>
56 #include <sys/poll.h>
57 #include <sys/times.h>
58 #include <sys/shm.h>
59 #include <sys/sem.h>
60 #include <sys/statfs.h>
61 #include <utime.h>
62 #include <sys/sysinfo.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 CONFIG_TIMERFD
70 #include <sys/timerfd.h>
71 #endif
72 #ifdef TARGET_GPROF
73 #include <sys/gmon.h>
74 #endif
75 #ifdef CONFIG_EVENTFD
76 #include <sys/eventfd.h>
77 #endif
78 #ifdef CONFIG_EPOLL
79 #include <sys/epoll.h>
80 #endif
81 #ifdef CONFIG_ATTR
82 #include "qemu/xattr.h"
83 #endif
84 #ifdef CONFIG_SENDFILE
85 #include <sys/sendfile.h>
86 #endif
87
88 #define termios host_termios
89 #define winsize host_winsize
90 #define termio host_termio
91 #define sgttyb host_sgttyb /* same as target */
92 #define tchars host_tchars /* same as target */
93 #define ltchars host_ltchars /* same as target */
94
95 #include <linux/termios.h>
96 #include <linux/unistd.h>
97 #include <linux/cdrom.h>
98 #include <linux/hdreg.h>
99 #include <linux/soundcard.h>
100 #include <linux/kd.h>
101 #include <linux/mtio.h>
102 #include <linux/fs.h>
103 #if defined(CONFIG_FIEMAP)
104 #include <linux/fiemap.h>
105 #endif
106 #include <linux/fb.h>
107 #include <linux/vt.h>
108 #include <linux/dm-ioctl.h>
109 #include <linux/reboot.h>
110 #include <linux/route.h>
111 #include <linux/filter.h>
112 #include <linux/blkpg.h>
113 #include "linux_loop.h"
114 #include "uname.h"
115
116 #include "qemu.h"
117
118 #define CLONE_NPTL_FLAGS2 (CLONE_SETTLS | \
119 CLONE_PARENT_SETTID | CLONE_CHILD_SETTID | CLONE_CHILD_CLEARTID)
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 /* Newer kernel ports have llseek() instead of _llseek() */
203 #if defined(TARGET_NR_llseek) && !defined(TARGET_NR__llseek)
204 #define TARGET_NR__llseek TARGET_NR_llseek
205 #endif
206
207 #ifdef __NR_gettid
208 _syscall0(int, gettid)
209 #else
210 /* This is a replacement for the host gettid() and must return a host
211 errno. */
212 static int gettid(void) {
213 return -ENOSYS;
214 }
215 #endif
216 #ifdef __NR_getdents
217 _syscall3(int, sys_getdents, uint, fd, struct linux_dirent *, dirp, uint, count);
218 #endif
219 #if !defined(__NR_getdents) || \
220 (defined(TARGET_NR_getdents64) && defined(__NR_getdents64))
221 _syscall3(int, sys_getdents64, uint, fd, struct linux_dirent64 *, dirp, uint, count);
222 #endif
223 #if defined(TARGET_NR__llseek) && defined(__NR_llseek)
224 _syscall5(int, _llseek, uint, fd, ulong, hi, ulong, lo,
225 loff_t *, res, uint, wh);
226 #endif
227 _syscall3(int,sys_rt_sigqueueinfo,int,pid,int,sig,siginfo_t *,uinfo)
228 _syscall3(int,sys_syslog,int,type,char*,bufp,int,len)
229 #if defined(TARGET_NR_tgkill) && defined(__NR_tgkill)
230 _syscall3(int,sys_tgkill,int,tgid,int,pid,int,sig)
231 #endif
232 #if defined(TARGET_NR_tkill) && defined(__NR_tkill)
233 _syscall2(int,sys_tkill,int,tid,int,sig)
234 #endif
235 #ifdef __NR_exit_group
236 _syscall1(int,exit_group,int,error_code)
237 #endif
238 #if defined(TARGET_NR_set_tid_address) && defined(__NR_set_tid_address)
239 _syscall1(int,set_tid_address,int *,tidptr)
240 #endif
241 #if defined(TARGET_NR_futex) && defined(__NR_futex)
242 _syscall6(int,sys_futex,int *,uaddr,int,op,int,val,
243 const struct timespec *,timeout,int *,uaddr2,int,val3)
244 #endif
245 #define __NR_sys_sched_getaffinity __NR_sched_getaffinity
246 _syscall3(int, sys_sched_getaffinity, pid_t, pid, unsigned int, len,
247 unsigned long *, user_mask_ptr);
248 #define __NR_sys_sched_setaffinity __NR_sched_setaffinity
249 _syscall3(int, sys_sched_setaffinity, pid_t, pid, unsigned int, len,
250 unsigned long *, user_mask_ptr);
251 _syscall4(int, reboot, int, magic1, int, magic2, unsigned int, cmd,
252 void *, arg);
253 _syscall2(int, capget, struct __user_cap_header_struct *, header,
254 struct __user_cap_data_struct *, data);
255 _syscall2(int, capset, struct __user_cap_header_struct *, header,
256 struct __user_cap_data_struct *, data);
257 #if defined(TARGET_NR_ioprio_get) && defined(__NR_ioprio_get)
258 _syscall2(int, ioprio_get, int, which, int, who)
259 #endif
260 #if defined(TARGET_NR_ioprio_set) && defined(__NR_ioprio_set)
261 _syscall3(int, ioprio_set, int, which, int, who, int, ioprio)
262 #endif
263
264 static bitmask_transtbl fcntl_flags_tbl[] = {
265 { TARGET_O_ACCMODE, TARGET_O_WRONLY, O_ACCMODE, O_WRONLY, },
266 { TARGET_O_ACCMODE, TARGET_O_RDWR, O_ACCMODE, O_RDWR, },
267 { TARGET_O_CREAT, TARGET_O_CREAT, O_CREAT, O_CREAT, },
268 { TARGET_O_EXCL, TARGET_O_EXCL, O_EXCL, O_EXCL, },
269 { TARGET_O_NOCTTY, TARGET_O_NOCTTY, O_NOCTTY, O_NOCTTY, },
270 { TARGET_O_TRUNC, TARGET_O_TRUNC, O_TRUNC, O_TRUNC, },
271 { TARGET_O_APPEND, TARGET_O_APPEND, O_APPEND, O_APPEND, },
272 { TARGET_O_NONBLOCK, TARGET_O_NONBLOCK, O_NONBLOCK, O_NONBLOCK, },
273 { TARGET_O_SYNC, TARGET_O_DSYNC, O_SYNC, O_DSYNC, },
274 { TARGET_O_SYNC, TARGET_O_SYNC, O_SYNC, O_SYNC, },
275 { TARGET_FASYNC, TARGET_FASYNC, FASYNC, FASYNC, },
276 { TARGET_O_DIRECTORY, TARGET_O_DIRECTORY, O_DIRECTORY, O_DIRECTORY, },
277 { TARGET_O_NOFOLLOW, TARGET_O_NOFOLLOW, O_NOFOLLOW, O_NOFOLLOW, },
278 #if defined(O_DIRECT)
279 { TARGET_O_DIRECT, TARGET_O_DIRECT, O_DIRECT, O_DIRECT, },
280 #endif
281 #if defined(O_NOATIME)
282 { TARGET_O_NOATIME, TARGET_O_NOATIME, O_NOATIME, O_NOATIME },
283 #endif
284 #if defined(O_CLOEXEC)
285 { TARGET_O_CLOEXEC, TARGET_O_CLOEXEC, O_CLOEXEC, O_CLOEXEC },
286 #endif
287 #if defined(O_PATH)
288 { TARGET_O_PATH, TARGET_O_PATH, O_PATH, O_PATH },
289 #endif
290 /* Don't terminate the list prematurely on 64-bit host+guest. */
291 #if TARGET_O_LARGEFILE != 0 || O_LARGEFILE != 0
292 { TARGET_O_LARGEFILE, TARGET_O_LARGEFILE, O_LARGEFILE, O_LARGEFILE, },
293 #endif
294 { 0, 0, 0, 0 }
295 };
296
297 static int sys_getcwd1(char *buf, size_t size)
298 {
299 if (getcwd(buf, size) == NULL) {
300 /* getcwd() sets errno */
301 return (-1);
302 }
303 return strlen(buf)+1;
304 }
305
306 static int sys_openat(int dirfd, const char *pathname, int flags, mode_t mode)
307 {
308 /*
309 * open(2) has extra parameter 'mode' when called with
310 * flag O_CREAT.
311 */
312 if ((flags & O_CREAT) != 0) {
313 return (openat(dirfd, pathname, flags, mode));
314 }
315 return (openat(dirfd, pathname, flags));
316 }
317
318 #ifdef TARGET_NR_utimensat
319 #ifdef CONFIG_UTIMENSAT
320 static int sys_utimensat(int dirfd, const char *pathname,
321 const struct timespec times[2], int flags)
322 {
323 if (pathname == NULL)
324 return futimens(dirfd, times);
325 else
326 return utimensat(dirfd, pathname, times, flags);
327 }
328 #elif defined(__NR_utimensat)
329 #define __NR_sys_utimensat __NR_utimensat
330 _syscall4(int,sys_utimensat,int,dirfd,const char *,pathname,
331 const struct timespec *,tsp,int,flags)
332 #else
333 static int sys_utimensat(int dirfd, const char *pathname,
334 const struct timespec times[2], int flags)
335 {
336 errno = ENOSYS;
337 return -1;
338 }
339 #endif
340 #endif /* TARGET_NR_utimensat */
341
342 #ifdef CONFIG_INOTIFY
343 #include <sys/inotify.h>
344
345 #if defined(TARGET_NR_inotify_init) && defined(__NR_inotify_init)
346 static int sys_inotify_init(void)
347 {
348 return (inotify_init());
349 }
350 #endif
351 #if defined(TARGET_NR_inotify_add_watch) && defined(__NR_inotify_add_watch)
352 static int sys_inotify_add_watch(int fd,const char *pathname, int32_t mask)
353 {
354 return (inotify_add_watch(fd, pathname, mask));
355 }
356 #endif
357 #if defined(TARGET_NR_inotify_rm_watch) && defined(__NR_inotify_rm_watch)
358 static int sys_inotify_rm_watch(int fd, int32_t wd)
359 {
360 return (inotify_rm_watch(fd, wd));
361 }
362 #endif
363 #ifdef CONFIG_INOTIFY1
364 #if defined(TARGET_NR_inotify_init1) && defined(__NR_inotify_init1)
365 static int sys_inotify_init1(int flags)
366 {
367 return (inotify_init1(flags));
368 }
369 #endif
370 #endif
371 #else
372 /* Userspace can usually survive runtime without inotify */
373 #undef TARGET_NR_inotify_init
374 #undef TARGET_NR_inotify_init1
375 #undef TARGET_NR_inotify_add_watch
376 #undef TARGET_NR_inotify_rm_watch
377 #endif /* CONFIG_INOTIFY */
378
379 #if defined(TARGET_NR_ppoll)
380 #ifndef __NR_ppoll
381 # define __NR_ppoll -1
382 #endif
383 #define __NR_sys_ppoll __NR_ppoll
384 _syscall5(int, sys_ppoll, struct pollfd *, fds, nfds_t, nfds,
385 struct timespec *, timeout, const sigset_t *, sigmask,
386 size_t, sigsetsize)
387 #endif
388
389 #if defined(TARGET_NR_pselect6)
390 #ifndef __NR_pselect6
391 # define __NR_pselect6 -1
392 #endif
393 #define __NR_sys_pselect6 __NR_pselect6
394 _syscall6(int, sys_pselect6, int, nfds, fd_set *, readfds, fd_set *, writefds,
395 fd_set *, exceptfds, struct timespec *, timeout, void *, sig);
396 #endif
397
398 #if defined(TARGET_NR_prlimit64)
399 #ifndef __NR_prlimit64
400 # define __NR_prlimit64 -1
401 #endif
402 #define __NR_sys_prlimit64 __NR_prlimit64
403 /* The glibc rlimit structure may not be that used by the underlying syscall */
404 struct host_rlimit64 {
405 uint64_t rlim_cur;
406 uint64_t rlim_max;
407 };
408 _syscall4(int, sys_prlimit64, pid_t, pid, int, resource,
409 const struct host_rlimit64 *, new_limit,
410 struct host_rlimit64 *, old_limit)
411 #endif
412
413
414 #if defined(TARGET_NR_timer_create)
415 /* Maxiumum of 32 active POSIX timers allowed at any one time. */
416 static timer_t g_posix_timers[32] = { 0, } ;
417
418 static inline int next_free_host_timer(void)
419 {
420 int k ;
421 /* FIXME: Does finding the next free slot require a lock? */
422 for (k = 0; k < ARRAY_SIZE(g_posix_timers); k++) {
423 if (g_posix_timers[k] == 0) {
424 g_posix_timers[k] = (timer_t) 1;
425 return k;
426 }
427 }
428 return -1;
429 }
430 #endif
431
432 /* ARM EABI and MIPS expect 64bit types aligned even on pairs or registers */
433 #ifdef TARGET_ARM
434 static inline int regpairs_aligned(void *cpu_env) {
435 return ((((CPUARMState *)cpu_env)->eabi) == 1) ;
436 }
437 #elif defined(TARGET_MIPS)
438 static inline int regpairs_aligned(void *cpu_env) { return 1; }
439 #elif defined(TARGET_PPC) && !defined(TARGET_PPC64)
440 /* SysV AVI for PPC32 expects 64bit parameters to be passed on odd/even pairs
441 * of registers which translates to the same as ARM/MIPS, because we start with
442 * r3 as arg1 */
443 static inline int regpairs_aligned(void *cpu_env) { return 1; }
444 #else
445 static inline int regpairs_aligned(void *cpu_env) { return 0; }
446 #endif
447
448 #define ERRNO_TABLE_SIZE 1200
449
450 /* target_to_host_errno_table[] is initialized from
451 * host_to_target_errno_table[] in syscall_init(). */
452 static uint16_t target_to_host_errno_table[ERRNO_TABLE_SIZE] = {
453 };
454
455 /*
456 * This list is the union of errno values overridden in asm-<arch>/errno.h
457 * minus the errnos that are not actually generic to all archs.
458 */
459 static uint16_t host_to_target_errno_table[ERRNO_TABLE_SIZE] = {
460 [EIDRM] = TARGET_EIDRM,
461 [ECHRNG] = TARGET_ECHRNG,
462 [EL2NSYNC] = TARGET_EL2NSYNC,
463 [EL3HLT] = TARGET_EL3HLT,
464 [EL3RST] = TARGET_EL3RST,
465 [ELNRNG] = TARGET_ELNRNG,
466 [EUNATCH] = TARGET_EUNATCH,
467 [ENOCSI] = TARGET_ENOCSI,
468 [EL2HLT] = TARGET_EL2HLT,
469 [EDEADLK] = TARGET_EDEADLK,
470 [ENOLCK] = TARGET_ENOLCK,
471 [EBADE] = TARGET_EBADE,
472 [EBADR] = TARGET_EBADR,
473 [EXFULL] = TARGET_EXFULL,
474 [ENOANO] = TARGET_ENOANO,
475 [EBADRQC] = TARGET_EBADRQC,
476 [EBADSLT] = TARGET_EBADSLT,
477 [EBFONT] = TARGET_EBFONT,
478 [ENOSTR] = TARGET_ENOSTR,
479 [ENODATA] = TARGET_ENODATA,
480 [ETIME] = TARGET_ETIME,
481 [ENOSR] = TARGET_ENOSR,
482 [ENONET] = TARGET_ENONET,
483 [ENOPKG] = TARGET_ENOPKG,
484 [EREMOTE] = TARGET_EREMOTE,
485 [ENOLINK] = TARGET_ENOLINK,
486 [EADV] = TARGET_EADV,
487 [ESRMNT] = TARGET_ESRMNT,
488 [ECOMM] = TARGET_ECOMM,
489 [EPROTO] = TARGET_EPROTO,
490 [EDOTDOT] = TARGET_EDOTDOT,
491 [EMULTIHOP] = TARGET_EMULTIHOP,
492 [EBADMSG] = TARGET_EBADMSG,
493 [ENAMETOOLONG] = TARGET_ENAMETOOLONG,
494 [EOVERFLOW] = TARGET_EOVERFLOW,
495 [ENOTUNIQ] = TARGET_ENOTUNIQ,
496 [EBADFD] = TARGET_EBADFD,
497 [EREMCHG] = TARGET_EREMCHG,
498 [ELIBACC] = TARGET_ELIBACC,
499 [ELIBBAD] = TARGET_ELIBBAD,
500 [ELIBSCN] = TARGET_ELIBSCN,
501 [ELIBMAX] = TARGET_ELIBMAX,
502 [ELIBEXEC] = TARGET_ELIBEXEC,
503 [EILSEQ] = TARGET_EILSEQ,
504 [ENOSYS] = TARGET_ENOSYS,
505 [ELOOP] = TARGET_ELOOP,
506 [ERESTART] = TARGET_ERESTART,
507 [ESTRPIPE] = TARGET_ESTRPIPE,
508 [ENOTEMPTY] = TARGET_ENOTEMPTY,
509 [EUSERS] = TARGET_EUSERS,
510 [ENOTSOCK] = TARGET_ENOTSOCK,
511 [EDESTADDRREQ] = TARGET_EDESTADDRREQ,
512 [EMSGSIZE] = TARGET_EMSGSIZE,
513 [EPROTOTYPE] = TARGET_EPROTOTYPE,
514 [ENOPROTOOPT] = TARGET_ENOPROTOOPT,
515 [EPROTONOSUPPORT] = TARGET_EPROTONOSUPPORT,
516 [ESOCKTNOSUPPORT] = TARGET_ESOCKTNOSUPPORT,
517 [EOPNOTSUPP] = TARGET_EOPNOTSUPP,
518 [EPFNOSUPPORT] = TARGET_EPFNOSUPPORT,
519 [EAFNOSUPPORT] = TARGET_EAFNOSUPPORT,
520 [EADDRINUSE] = TARGET_EADDRINUSE,
521 [EADDRNOTAVAIL] = TARGET_EADDRNOTAVAIL,
522 [ENETDOWN] = TARGET_ENETDOWN,
523 [ENETUNREACH] = TARGET_ENETUNREACH,
524 [ENETRESET] = TARGET_ENETRESET,
525 [ECONNABORTED] = TARGET_ECONNABORTED,
526 [ECONNRESET] = TARGET_ECONNRESET,
527 [ENOBUFS] = TARGET_ENOBUFS,
528 [EISCONN] = TARGET_EISCONN,
529 [ENOTCONN] = TARGET_ENOTCONN,
530 [EUCLEAN] = TARGET_EUCLEAN,
531 [ENOTNAM] = TARGET_ENOTNAM,
532 [ENAVAIL] = TARGET_ENAVAIL,
533 [EISNAM] = TARGET_EISNAM,
534 [EREMOTEIO] = TARGET_EREMOTEIO,
535 [ESHUTDOWN] = TARGET_ESHUTDOWN,
536 [ETOOMANYREFS] = TARGET_ETOOMANYREFS,
537 [ETIMEDOUT] = TARGET_ETIMEDOUT,
538 [ECONNREFUSED] = TARGET_ECONNREFUSED,
539 [EHOSTDOWN] = TARGET_EHOSTDOWN,
540 [EHOSTUNREACH] = TARGET_EHOSTUNREACH,
541 [EALREADY] = TARGET_EALREADY,
542 [EINPROGRESS] = TARGET_EINPROGRESS,
543 [ESTALE] = TARGET_ESTALE,
544 [ECANCELED] = TARGET_ECANCELED,
545 [ENOMEDIUM] = TARGET_ENOMEDIUM,
546 [EMEDIUMTYPE] = TARGET_EMEDIUMTYPE,
547 #ifdef ENOKEY
548 [ENOKEY] = TARGET_ENOKEY,
549 #endif
550 #ifdef EKEYEXPIRED
551 [EKEYEXPIRED] = TARGET_EKEYEXPIRED,
552 #endif
553 #ifdef EKEYREVOKED
554 [EKEYREVOKED] = TARGET_EKEYREVOKED,
555 #endif
556 #ifdef EKEYREJECTED
557 [EKEYREJECTED] = TARGET_EKEYREJECTED,
558 #endif
559 #ifdef EOWNERDEAD
560 [EOWNERDEAD] = TARGET_EOWNERDEAD,
561 #endif
562 #ifdef ENOTRECOVERABLE
563 [ENOTRECOVERABLE] = TARGET_ENOTRECOVERABLE,
564 #endif
565 };
566
567 static inline int host_to_target_errno(int err)
568 {
569 if(host_to_target_errno_table[err])
570 return host_to_target_errno_table[err];
571 return err;
572 }
573
574 static inline int target_to_host_errno(int err)
575 {
576 if (target_to_host_errno_table[err])
577 return target_to_host_errno_table[err];
578 return err;
579 }
580
581 static inline abi_long get_errno(abi_long ret)
582 {
583 if (ret == -1)
584 return -host_to_target_errno(errno);
585 else
586 return ret;
587 }
588
589 static inline int is_error(abi_long ret)
590 {
591 return (abi_ulong)ret >= (abi_ulong)(-4096);
592 }
593
594 char *target_strerror(int err)
595 {
596 if ((err >= ERRNO_TABLE_SIZE) || (err < 0)) {
597 return NULL;
598 }
599 return strerror(target_to_host_errno(err));
600 }
601
602 static inline int host_to_target_sock_type(int host_type)
603 {
604 int target_type;
605
606 switch (host_type & 0xf /* SOCK_TYPE_MASK */) {
607 case SOCK_DGRAM:
608 target_type = TARGET_SOCK_DGRAM;
609 break;
610 case SOCK_STREAM:
611 target_type = TARGET_SOCK_STREAM;
612 break;
613 default:
614 target_type = host_type & 0xf /* SOCK_TYPE_MASK */;
615 break;
616 }
617
618 #if defined(SOCK_CLOEXEC)
619 if (host_type & SOCK_CLOEXEC) {
620 target_type |= TARGET_SOCK_CLOEXEC;
621 }
622 #endif
623
624 #if defined(SOCK_NONBLOCK)
625 if (host_type & SOCK_NONBLOCK) {
626 target_type |= TARGET_SOCK_NONBLOCK;
627 }
628 #endif
629
630 return target_type;
631 }
632
633 static abi_ulong target_brk;
634 static abi_ulong target_original_brk;
635 static abi_ulong brk_page;
636
637 void target_set_brk(abi_ulong new_brk)
638 {
639 target_original_brk = target_brk = HOST_PAGE_ALIGN(new_brk);
640 brk_page = HOST_PAGE_ALIGN(target_brk);
641 }
642
643 //#define DEBUGF_BRK(message, args...) do { fprintf(stderr, (message), ## args); } while (0)
644 #define DEBUGF_BRK(message, args...)
645
646 /* do_brk() must return target values and target errnos. */
647 abi_long do_brk(abi_ulong new_brk)
648 {
649 abi_long mapped_addr;
650 int new_alloc_size;
651
652 DEBUGF_BRK("do_brk(" TARGET_ABI_FMT_lx ") -> ", new_brk);
653
654 if (!new_brk) {
655 DEBUGF_BRK(TARGET_ABI_FMT_lx " (!new_brk)\n", target_brk);
656 return target_brk;
657 }
658 if (new_brk < target_original_brk) {
659 DEBUGF_BRK(TARGET_ABI_FMT_lx " (new_brk < target_original_brk)\n",
660 target_brk);
661 return target_brk;
662 }
663
664 /* If the new brk is less than the highest page reserved to the
665 * target heap allocation, set it and we're almost done... */
666 if (new_brk <= brk_page) {
667 /* Heap contents are initialized to zero, as for anonymous
668 * mapped pages. */
669 if (new_brk > target_brk) {
670 memset(g2h(target_brk), 0, new_brk - target_brk);
671 }
672 target_brk = new_brk;
673 DEBUGF_BRK(TARGET_ABI_FMT_lx " (new_brk <= brk_page)\n", target_brk);
674 return target_brk;
675 }
676
677 /* We need to allocate more memory after the brk... Note that
678 * we don't use MAP_FIXED because that will map over the top of
679 * any existing mapping (like the one with the host libc or qemu
680 * itself); instead we treat "mapped but at wrong address" as
681 * a failure and unmap again.
682 */
683 new_alloc_size = HOST_PAGE_ALIGN(new_brk - brk_page);
684 mapped_addr = get_errno(target_mmap(brk_page, new_alloc_size,
685 PROT_READ|PROT_WRITE,
686 MAP_ANON|MAP_PRIVATE, 0, 0));
687
688 if (mapped_addr == brk_page) {
689 /* Heap contents are initialized to zero, as for anonymous
690 * mapped pages. Technically the new pages are already
691 * initialized to zero since they *are* anonymous mapped
692 * pages, however we have to take care with the contents that
693 * come from the remaining part of the previous page: it may
694 * contains garbage data due to a previous heap usage (grown
695 * then shrunken). */
696 memset(g2h(target_brk), 0, brk_page - target_brk);
697
698 target_brk = new_brk;
699 brk_page = HOST_PAGE_ALIGN(target_brk);
700 DEBUGF_BRK(TARGET_ABI_FMT_lx " (mapped_addr == brk_page)\n",
701 target_brk);
702 return target_brk;
703 } else if (mapped_addr != -1) {
704 /* Mapped but at wrong address, meaning there wasn't actually
705 * enough space for this brk.
706 */
707 target_munmap(mapped_addr, new_alloc_size);
708 mapped_addr = -1;
709 DEBUGF_BRK(TARGET_ABI_FMT_lx " (mapped_addr != -1)\n", target_brk);
710 }
711 else {
712 DEBUGF_BRK(TARGET_ABI_FMT_lx " (otherwise)\n", target_brk);
713 }
714
715 #if defined(TARGET_ALPHA)
716 /* We (partially) emulate OSF/1 on Alpha, which requires we
717 return a proper errno, not an unchanged brk value. */
718 return -TARGET_ENOMEM;
719 #endif
720 /* For everything else, return the previous break. */
721 return target_brk;
722 }
723
724 static inline abi_long copy_from_user_fdset(fd_set *fds,
725 abi_ulong target_fds_addr,
726 int n)
727 {
728 int i, nw, j, k;
729 abi_ulong b, *target_fds;
730
731 nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
732 if (!(target_fds = lock_user(VERIFY_READ,
733 target_fds_addr,
734 sizeof(abi_ulong) * nw,
735 1)))
736 return -TARGET_EFAULT;
737
738 FD_ZERO(fds);
739 k = 0;
740 for (i = 0; i < nw; i++) {
741 /* grab the abi_ulong */
742 __get_user(b, &target_fds[i]);
743 for (j = 0; j < TARGET_ABI_BITS; j++) {
744 /* check the bit inside the abi_ulong */
745 if ((b >> j) & 1)
746 FD_SET(k, fds);
747 k++;
748 }
749 }
750
751 unlock_user(target_fds, target_fds_addr, 0);
752
753 return 0;
754 }
755
756 static inline abi_ulong copy_from_user_fdset_ptr(fd_set *fds, fd_set **fds_ptr,
757 abi_ulong target_fds_addr,
758 int n)
759 {
760 if (target_fds_addr) {
761 if (copy_from_user_fdset(fds, target_fds_addr, n))
762 return -TARGET_EFAULT;
763 *fds_ptr = fds;
764 } else {
765 *fds_ptr = NULL;
766 }
767 return 0;
768 }
769
770 static inline abi_long copy_to_user_fdset(abi_ulong target_fds_addr,
771 const fd_set *fds,
772 int n)
773 {
774 int i, nw, j, k;
775 abi_long v;
776 abi_ulong *target_fds;
777
778 nw = (n + TARGET_ABI_BITS - 1) / TARGET_ABI_BITS;
779 if (!(target_fds = lock_user(VERIFY_WRITE,
780 target_fds_addr,
781 sizeof(abi_ulong) * nw,
782 0)))
783 return -TARGET_EFAULT;
784
785 k = 0;
786 for (i = 0; i < nw; i++) {
787 v = 0;
788 for (j = 0; j < TARGET_ABI_BITS; j++) {
789 v |= ((abi_ulong)(FD_ISSET(k, fds) != 0) << j);
790 k++;
791 }
792 __put_user(v, &target_fds[i]);
793 }
794
795 unlock_user(target_fds, target_fds_addr, sizeof(abi_ulong) * nw);
796
797 return 0;
798 }
799
800 #if defined(__alpha__)
801 #define HOST_HZ 1024
802 #else
803 #define HOST_HZ 100
804 #endif
805
806 static inline abi_long host_to_target_clock_t(long ticks)
807 {
808 #if HOST_HZ == TARGET_HZ
809 return ticks;
810 #else
811 return ((int64_t)ticks * TARGET_HZ) / HOST_HZ;
812 #endif
813 }
814
815 static inline abi_long host_to_target_rusage(abi_ulong target_addr,
816 const struct rusage *rusage)
817 {
818 struct target_rusage *target_rusage;
819
820 if (!lock_user_struct(VERIFY_WRITE, target_rusage, target_addr, 0))
821 return -TARGET_EFAULT;
822 target_rusage->ru_utime.tv_sec = tswapal(rusage->ru_utime.tv_sec);
823 target_rusage->ru_utime.tv_usec = tswapal(rusage->ru_utime.tv_usec);
824 target_rusage->ru_stime.tv_sec = tswapal(rusage->ru_stime.tv_sec);
825 target_rusage->ru_stime.tv_usec = tswapal(rusage->ru_stime.tv_usec);
826 target_rusage->ru_maxrss = tswapal(rusage->ru_maxrss);
827 target_rusage->ru_ixrss = tswapal(rusage->ru_ixrss);
828 target_rusage->ru_idrss = tswapal(rusage->ru_idrss);
829 target_rusage->ru_isrss = tswapal(rusage->ru_isrss);
830 target_rusage->ru_minflt = tswapal(rusage->ru_minflt);
831 target_rusage->ru_majflt = tswapal(rusage->ru_majflt);
832 target_rusage->ru_nswap = tswapal(rusage->ru_nswap);
833 target_rusage->ru_inblock = tswapal(rusage->ru_inblock);
834 target_rusage->ru_oublock = tswapal(rusage->ru_oublock);
835 target_rusage->ru_msgsnd = tswapal(rusage->ru_msgsnd);
836 target_rusage->ru_msgrcv = tswapal(rusage->ru_msgrcv);
837 target_rusage->ru_nsignals = tswapal(rusage->ru_nsignals);
838 target_rusage->ru_nvcsw = tswapal(rusage->ru_nvcsw);
839 target_rusage->ru_nivcsw = tswapal(rusage->ru_nivcsw);
840 unlock_user_struct(target_rusage, target_addr, 1);
841
842 return 0;
843 }
844
845 static inline rlim_t target_to_host_rlim(abi_ulong target_rlim)
846 {
847 abi_ulong target_rlim_swap;
848 rlim_t result;
849
850 target_rlim_swap = tswapal(target_rlim);
851 if (target_rlim_swap == TARGET_RLIM_INFINITY)
852 return RLIM_INFINITY;
853
854 result = target_rlim_swap;
855 if (target_rlim_swap != (rlim_t)result)
856 return RLIM_INFINITY;
857
858 return result;
859 }
860
861 static inline abi_ulong host_to_target_rlim(rlim_t rlim)
862 {
863 abi_ulong target_rlim_swap;
864 abi_ulong result;
865
866 if (rlim == RLIM_INFINITY || rlim != (abi_long)rlim)
867 target_rlim_swap = TARGET_RLIM_INFINITY;
868 else
869 target_rlim_swap = rlim;
870 result = tswapal(target_rlim_swap);
871
872 return result;
873 }
874
875 static inline int target_to_host_resource(int code)
876 {
877 switch (code) {
878 case TARGET_RLIMIT_AS:
879 return RLIMIT_AS;
880 case TARGET_RLIMIT_CORE:
881 return RLIMIT_CORE;
882 case TARGET_RLIMIT_CPU:
883 return RLIMIT_CPU;
884 case TARGET_RLIMIT_DATA:
885 return RLIMIT_DATA;
886 case TARGET_RLIMIT_FSIZE:
887 return RLIMIT_FSIZE;
888 case TARGET_RLIMIT_LOCKS:
889 return RLIMIT_LOCKS;
890 case TARGET_RLIMIT_MEMLOCK:
891 return RLIMIT_MEMLOCK;
892 case TARGET_RLIMIT_MSGQUEUE:
893 return RLIMIT_MSGQUEUE;
894 case TARGET_RLIMIT_NICE:
895 return RLIMIT_NICE;
896 case TARGET_RLIMIT_NOFILE:
897 return RLIMIT_NOFILE;
898 case TARGET_RLIMIT_NPROC:
899 return RLIMIT_NPROC;
900 case TARGET_RLIMIT_RSS:
901 return RLIMIT_RSS;
902 case TARGET_RLIMIT_RTPRIO:
903 return RLIMIT_RTPRIO;
904 case TARGET_RLIMIT_SIGPENDING:
905 return RLIMIT_SIGPENDING;
906 case TARGET_RLIMIT_STACK:
907 return RLIMIT_STACK;
908 default:
909 return code;
910 }
911 }
912
913 static inline abi_long copy_from_user_timeval(struct timeval *tv,
914 abi_ulong target_tv_addr)
915 {
916 struct target_timeval *target_tv;
917
918 if (!lock_user_struct(VERIFY_READ, target_tv, target_tv_addr, 1))
919 return -TARGET_EFAULT;
920
921 __get_user(tv->tv_sec, &target_tv->tv_sec);
922 __get_user(tv->tv_usec, &target_tv->tv_usec);
923
924 unlock_user_struct(target_tv, target_tv_addr, 0);
925
926 return 0;
927 }
928
929 static inline abi_long copy_to_user_timeval(abi_ulong target_tv_addr,
930 const struct timeval *tv)
931 {
932 struct target_timeval *target_tv;
933
934 if (!lock_user_struct(VERIFY_WRITE, target_tv, target_tv_addr, 0))
935 return -TARGET_EFAULT;
936
937 __put_user(tv->tv_sec, &target_tv->tv_sec);
938 __put_user(tv->tv_usec, &target_tv->tv_usec);
939
940 unlock_user_struct(target_tv, target_tv_addr, 1);
941
942 return 0;
943 }
944
945 static inline abi_long copy_from_user_timezone(struct timezone *tz,
946 abi_ulong target_tz_addr)
947 {
948 struct target_timezone *target_tz;
949
950 if (!lock_user_struct(VERIFY_READ, target_tz, target_tz_addr, 1)) {
951 return -TARGET_EFAULT;
952 }
953
954 __get_user(tz->tz_minuteswest, &target_tz->tz_minuteswest);
955 __get_user(tz->tz_dsttime, &target_tz->tz_dsttime);
956
957 unlock_user_struct(target_tz, target_tz_addr, 0);
958
959 return 0;
960 }
961
962 #if defined(TARGET_NR_mq_open) && defined(__NR_mq_open)
963 #include <mqueue.h>
964
965 static inline abi_long copy_from_user_mq_attr(struct mq_attr *attr,
966 abi_ulong target_mq_attr_addr)
967 {
968 struct target_mq_attr *target_mq_attr;
969
970 if (!lock_user_struct(VERIFY_READ, target_mq_attr,
971 target_mq_attr_addr, 1))
972 return -TARGET_EFAULT;
973
974 __get_user(attr->mq_flags, &target_mq_attr->mq_flags);
975 __get_user(attr->mq_maxmsg, &target_mq_attr->mq_maxmsg);
976 __get_user(attr->mq_msgsize, &target_mq_attr->mq_msgsize);
977 __get_user(attr->mq_curmsgs, &target_mq_attr->mq_curmsgs);
978
979 unlock_user_struct(target_mq_attr, target_mq_attr_addr, 0);
980
981 return 0;
982 }
983
984 static inline abi_long copy_to_user_mq_attr(abi_ulong target_mq_attr_addr,
985 const struct mq_attr *attr)
986 {
987 struct target_mq_attr *target_mq_attr;
988
989 if (!lock_user_struct(VERIFY_WRITE, target_mq_attr,
990 target_mq_attr_addr, 0))
991 return -TARGET_EFAULT;
992
993 __put_user(attr->mq_flags, &target_mq_attr->mq_flags);
994 __put_user(attr->mq_maxmsg, &target_mq_attr->mq_maxmsg);
995 __put_user(attr->mq_msgsize, &target_mq_attr->mq_msgsize);
996 __put_user(attr->mq_curmsgs, &target_mq_attr->mq_curmsgs);
997
998 unlock_user_struct(target_mq_attr, target_mq_attr_addr, 1);
999
1000 return 0;
1001 }
1002 #endif
1003
1004 #if defined(TARGET_NR_select) || defined(TARGET_NR__newselect)
1005 /* do_select() must return target values and target errnos. */
1006 static abi_long do_select(int n,
1007 abi_ulong rfd_addr, abi_ulong wfd_addr,
1008 abi_ulong efd_addr, abi_ulong target_tv_addr)
1009 {
1010 fd_set rfds, wfds, efds;
1011 fd_set *rfds_ptr, *wfds_ptr, *efds_ptr;
1012 struct timeval tv, *tv_ptr;
1013 abi_long ret;
1014
1015 ret = copy_from_user_fdset_ptr(&rfds, &rfds_ptr, rfd_addr, n);
1016 if (ret) {
1017 return ret;
1018 }
1019 ret = copy_from_user_fdset_ptr(&wfds, &wfds_ptr, wfd_addr, n);
1020 if (ret) {
1021 return ret;
1022 }
1023 ret = copy_from_user_fdset_ptr(&efds, &efds_ptr, efd_addr, n);
1024 if (ret) {
1025 return ret;
1026 }
1027
1028 if (target_tv_addr) {
1029 if (copy_from_user_timeval(&tv, target_tv_addr))
1030 return -TARGET_EFAULT;
1031 tv_ptr = &tv;
1032 } else {
1033 tv_ptr = NULL;
1034 }
1035
1036 ret = get_errno(select(n, rfds_ptr, wfds_ptr, efds_ptr, tv_ptr));
1037
1038 if (!is_error(ret)) {
1039 if (rfd_addr && copy_to_user_fdset(rfd_addr, &rfds, n))
1040 return -TARGET_EFAULT;
1041 if (wfd_addr && copy_to_user_fdset(wfd_addr, &wfds, n))
1042 return -TARGET_EFAULT;
1043 if (efd_addr && copy_to_user_fdset(efd_addr, &efds, n))
1044 return -TARGET_EFAULT;
1045
1046 if (target_tv_addr && copy_to_user_timeval(target_tv_addr, &tv))
1047 return -TARGET_EFAULT;
1048 }
1049
1050 return ret;
1051 }
1052 #endif
1053
1054 static abi_long do_pipe2(int host_pipe[], int flags)
1055 {
1056 #ifdef CONFIG_PIPE2
1057 return pipe2(host_pipe, flags);
1058 #else
1059 return -ENOSYS;
1060 #endif
1061 }
1062
1063 static abi_long do_pipe(void *cpu_env, abi_ulong pipedes,
1064 int flags, int is_pipe2)
1065 {
1066 int host_pipe[2];
1067 abi_long ret;
1068 ret = flags ? do_pipe2(host_pipe, flags) : pipe(host_pipe);
1069
1070 if (is_error(ret))
1071 return get_errno(ret);
1072
1073 /* Several targets have special calling conventions for the original
1074 pipe syscall, but didn't replicate this into the pipe2 syscall. */
1075 if (!is_pipe2) {
1076 #if defined(TARGET_ALPHA)
1077 ((CPUAlphaState *)cpu_env)->ir[IR_A4] = host_pipe[1];
1078 return host_pipe[0];
1079 #elif defined(TARGET_MIPS)
1080 ((CPUMIPSState*)cpu_env)->active_tc.gpr[3] = host_pipe[1];
1081 return host_pipe[0];
1082 #elif defined(TARGET_SH4)
1083 ((CPUSH4State*)cpu_env)->gregs[1] = host_pipe[1];
1084 return host_pipe[0];
1085 #elif defined(TARGET_SPARC)
1086 ((CPUSPARCState*)cpu_env)->regwptr[1] = host_pipe[1];
1087 return host_pipe[0];
1088 #endif
1089 }
1090
1091 if (put_user_s32(host_pipe[0], pipedes)
1092 || put_user_s32(host_pipe[1], pipedes + sizeof(host_pipe[0])))
1093 return -TARGET_EFAULT;
1094 return get_errno(ret);
1095 }
1096
1097 static inline abi_long target_to_host_ip_mreq(struct ip_mreqn *mreqn,
1098 abi_ulong target_addr,
1099 socklen_t len)
1100 {
1101 struct target_ip_mreqn *target_smreqn;
1102
1103 target_smreqn = lock_user(VERIFY_READ, target_addr, len, 1);
1104 if (!target_smreqn)
1105 return -TARGET_EFAULT;
1106 mreqn->imr_multiaddr.s_addr = target_smreqn->imr_multiaddr.s_addr;
1107 mreqn->imr_address.s_addr = target_smreqn->imr_address.s_addr;
1108 if (len == sizeof(struct target_ip_mreqn))
1109 mreqn->imr_ifindex = tswapal(target_smreqn->imr_ifindex);
1110 unlock_user(target_smreqn, target_addr, 0);
1111
1112 return 0;
1113 }
1114
1115 static inline abi_long target_to_host_sockaddr(struct sockaddr *addr,
1116 abi_ulong target_addr,
1117 socklen_t len)
1118 {
1119 const socklen_t unix_maxlen = sizeof (struct sockaddr_un);
1120 sa_family_t sa_family;
1121 struct target_sockaddr *target_saddr;
1122
1123 target_saddr = lock_user(VERIFY_READ, target_addr, len, 1);
1124 if (!target_saddr)
1125 return -TARGET_EFAULT;
1126
1127 sa_family = tswap16(target_saddr->sa_family);
1128
1129 /* Oops. The caller might send a incomplete sun_path; sun_path
1130 * must be terminated by \0 (see the manual page), but
1131 * unfortunately it is quite common to specify sockaddr_un
1132 * length as "strlen(x->sun_path)" while it should be
1133 * "strlen(...) + 1". We'll fix that here if needed.
1134 * Linux kernel has a similar feature.
1135 */
1136
1137 if (sa_family == AF_UNIX) {
1138 if (len < unix_maxlen && len > 0) {
1139 char *cp = (char*)target_saddr;
1140
1141 if ( cp[len-1] && !cp[len] )
1142 len++;
1143 }
1144 if (len > unix_maxlen)
1145 len = unix_maxlen;
1146 }
1147
1148 memcpy(addr, target_saddr, len);
1149 addr->sa_family = sa_family;
1150 if (sa_family == AF_PACKET) {
1151 struct target_sockaddr_ll *lladdr;
1152
1153 lladdr = (struct target_sockaddr_ll *)addr;
1154 lladdr->sll_ifindex = tswap32(lladdr->sll_ifindex);
1155 lladdr->sll_hatype = tswap16(lladdr->sll_hatype);
1156 }
1157 unlock_user(target_saddr, target_addr, 0);
1158
1159 return 0;
1160 }
1161
1162 static inline abi_long host_to_target_sockaddr(abi_ulong target_addr,
1163 struct sockaddr *addr,
1164 socklen_t len)
1165 {
1166 struct target_sockaddr *target_saddr;
1167
1168 target_saddr = lock_user(VERIFY_WRITE, target_addr, len, 0);
1169 if (!target_saddr)
1170 return -TARGET_EFAULT;
1171 memcpy(target_saddr, addr, len);
1172 target_saddr->sa_family = tswap16(addr->sa_family);
1173 unlock_user(target_saddr, target_addr, len);
1174
1175 return 0;
1176 }
1177
1178 static inline abi_long target_to_host_cmsg(struct msghdr *msgh,
1179 struct target_msghdr *target_msgh)
1180 {
1181 struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
1182 abi_long msg_controllen;
1183 abi_ulong target_cmsg_addr;
1184 struct target_cmsghdr *target_cmsg;
1185 socklen_t space = 0;
1186
1187 msg_controllen = tswapal(target_msgh->msg_controllen);
1188 if (msg_controllen < sizeof (struct target_cmsghdr))
1189 goto the_end;
1190 target_cmsg_addr = tswapal(target_msgh->msg_control);
1191 target_cmsg = lock_user(VERIFY_READ, target_cmsg_addr, msg_controllen, 1);
1192 if (!target_cmsg)
1193 return -TARGET_EFAULT;
1194
1195 while (cmsg && target_cmsg) {
1196 void *data = CMSG_DATA(cmsg);
1197 void *target_data = TARGET_CMSG_DATA(target_cmsg);
1198
1199 int len = tswapal(target_cmsg->cmsg_len)
1200 - TARGET_CMSG_ALIGN(sizeof (struct target_cmsghdr));
1201
1202 space += CMSG_SPACE(len);
1203 if (space > msgh->msg_controllen) {
1204 space -= CMSG_SPACE(len);
1205 gemu_log("Host cmsg overflow\n");
1206 break;
1207 }
1208
1209 if (tswap32(target_cmsg->cmsg_level) == TARGET_SOL_SOCKET) {
1210 cmsg->cmsg_level = SOL_SOCKET;
1211 } else {
1212 cmsg->cmsg_level = tswap32(target_cmsg->cmsg_level);
1213 }
1214 cmsg->cmsg_type = tswap32(target_cmsg->cmsg_type);
1215 cmsg->cmsg_len = CMSG_LEN(len);
1216
1217 if (cmsg->cmsg_level != SOL_SOCKET || cmsg->cmsg_type != SCM_RIGHTS) {
1218 gemu_log("Unsupported ancillary data: %d/%d\n", cmsg->cmsg_level, cmsg->cmsg_type);
1219 memcpy(data, target_data, len);
1220 } else {
1221 int *fd = (int *)data;
1222 int *target_fd = (int *)target_data;
1223 int i, numfds = len / sizeof(int);
1224
1225 for (i = 0; i < numfds; i++)
1226 fd[i] = tswap32(target_fd[i]);
1227 }
1228
1229 cmsg = CMSG_NXTHDR(msgh, cmsg);
1230 target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
1231 }
1232 unlock_user(target_cmsg, target_cmsg_addr, 0);
1233 the_end:
1234 msgh->msg_controllen = space;
1235 return 0;
1236 }
1237
1238 static inline abi_long host_to_target_cmsg(struct target_msghdr *target_msgh,
1239 struct msghdr *msgh)
1240 {
1241 struct cmsghdr *cmsg = CMSG_FIRSTHDR(msgh);
1242 abi_long msg_controllen;
1243 abi_ulong target_cmsg_addr;
1244 struct target_cmsghdr *target_cmsg;
1245 socklen_t space = 0;
1246
1247 msg_controllen = tswapal(target_msgh->msg_controllen);
1248 if (msg_controllen < sizeof (struct target_cmsghdr))
1249 goto the_end;
1250 target_cmsg_addr = tswapal(target_msgh->msg_control);
1251 target_cmsg = lock_user(VERIFY_WRITE, target_cmsg_addr, msg_controllen, 0);
1252 if (!target_cmsg)
1253 return -TARGET_EFAULT;
1254
1255 while (cmsg && target_cmsg) {
1256 void *data = CMSG_DATA(cmsg);
1257 void *target_data = TARGET_CMSG_DATA(target_cmsg);
1258
1259 int len = cmsg->cmsg_len - CMSG_ALIGN(sizeof (struct cmsghdr));
1260
1261 space += TARGET_CMSG_SPACE(len);
1262 if (space > msg_controllen) {
1263 space -= TARGET_CMSG_SPACE(len);
1264 gemu_log("Target cmsg overflow\n");
1265 break;
1266 }
1267
1268 if (cmsg->cmsg_level == SOL_SOCKET) {
1269 target_cmsg->cmsg_level = tswap32(TARGET_SOL_SOCKET);
1270 } else {
1271 target_cmsg->cmsg_level = tswap32(cmsg->cmsg_level);
1272 }
1273 target_cmsg->cmsg_type = tswap32(cmsg->cmsg_type);
1274 target_cmsg->cmsg_len = tswapal(TARGET_CMSG_LEN(len));
1275
1276 switch (cmsg->cmsg_level) {
1277 case SOL_SOCKET:
1278 switch (cmsg->cmsg_type) {
1279 case SCM_RIGHTS:
1280 {
1281 int *fd = (int *)data;
1282 int *target_fd = (int *)target_data;
1283 int i, numfds = len / sizeof(int);
1284
1285 for (i = 0; i < numfds; i++)
1286 target_fd[i] = tswap32(fd[i]);
1287 break;
1288 }
1289 case SO_TIMESTAMP:
1290 {
1291 struct timeval *tv = (struct timeval *)data;
1292 struct target_timeval *target_tv =
1293 (struct target_timeval *)target_data;
1294
1295 if (len != sizeof(struct timeval))
1296 goto unimplemented;
1297
1298 /* copy struct timeval to target */
1299 target_tv->tv_sec = tswapal(tv->tv_sec);
1300 target_tv->tv_usec = tswapal(tv->tv_usec);
1301 break;
1302 }
1303 case SCM_CREDENTIALS:
1304 {
1305 struct ucred *cred = (struct ucred *)data;
1306 struct target_ucred *target_cred =
1307 (struct target_ucred *)target_data;
1308
1309 __put_user(cred->pid, &target_cred->pid);
1310 __put_user(cred->uid, &target_cred->uid);
1311 __put_user(cred->gid, &target_cred->gid);
1312 break;
1313 }
1314 default:
1315 goto unimplemented;
1316 }
1317 break;
1318
1319 default:
1320 unimplemented:
1321 gemu_log("Unsupported ancillary data: %d/%d\n",
1322 cmsg->cmsg_level, cmsg->cmsg_type);
1323 memcpy(target_data, data, len);
1324 }
1325
1326 cmsg = CMSG_NXTHDR(msgh, cmsg);
1327 target_cmsg = TARGET_CMSG_NXTHDR(target_msgh, target_cmsg);
1328 }
1329 unlock_user(target_cmsg, target_cmsg_addr, space);
1330 the_end:
1331 target_msgh->msg_controllen = tswapal(space);
1332 return 0;
1333 }
1334
1335 /* do_setsockopt() Must return target values and target errnos. */
1336 static abi_long do_setsockopt(int sockfd, int level, int optname,
1337 abi_ulong optval_addr, socklen_t optlen)
1338 {
1339 abi_long ret;
1340 int val;
1341 struct ip_mreqn *ip_mreq;
1342 struct ip_mreq_source *ip_mreq_source;
1343
1344 switch(level) {
1345 case SOL_TCP:
1346 /* TCP options all take an 'int' value. */
1347 if (optlen < sizeof(uint32_t))
1348 return -TARGET_EINVAL;
1349
1350 if (get_user_u32(val, optval_addr))
1351 return -TARGET_EFAULT;
1352 ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
1353 break;
1354 case SOL_IP:
1355 switch(optname) {
1356 case IP_TOS:
1357 case IP_TTL:
1358 case IP_HDRINCL:
1359 case IP_ROUTER_ALERT:
1360 case IP_RECVOPTS:
1361 case IP_RETOPTS:
1362 case IP_PKTINFO:
1363 case IP_MTU_DISCOVER:
1364 case IP_RECVERR:
1365 case IP_RECVTOS:
1366 #ifdef IP_FREEBIND
1367 case IP_FREEBIND:
1368 #endif
1369 case IP_MULTICAST_TTL:
1370 case IP_MULTICAST_LOOP:
1371 val = 0;
1372 if (optlen >= sizeof(uint32_t)) {
1373 if (get_user_u32(val, optval_addr))
1374 return -TARGET_EFAULT;
1375 } else if (optlen >= 1) {
1376 if (get_user_u8(val, optval_addr))
1377 return -TARGET_EFAULT;
1378 }
1379 ret = get_errno(setsockopt(sockfd, level, optname, &val, sizeof(val)));
1380 break;
1381 case IP_ADD_MEMBERSHIP:
1382 case IP_DROP_MEMBERSHIP:
1383 if (optlen < sizeof (struct target_ip_mreq) ||
1384 optlen > sizeof (struct target_ip_mreqn))
1385 return -TARGET_EINVAL;
1386
1387 ip_mreq = (struct ip_mreqn *) alloca(optlen);
1388 target_to_host_ip_mreq(ip_mreq, optval_addr, optlen);
1389 ret = get_errno(setsockopt(sockfd, level, optname, ip_mreq, optlen));
1390 break;
1391
1392 case IP_BLOCK_SOURCE:
1393 case IP_UNBLOCK_SOURCE:
1394 case IP_ADD_SOURCE_MEMBERSHIP:
1395 case IP_DROP_SOURCE_MEMBERSHIP:
1396 if (optlen != sizeof (struct target_ip_mreq_source))
1397 return -TARGET_EINVAL;
1398
1399 ip_mreq_source = lock_user(VERIFY_READ, optval_addr, optlen, 1);
1400 ret = get_errno(setsockopt(sockfd, level, optname, ip_mreq_source, optlen));
1401 unlock_user (ip_mreq_source, optval_addr, 0);
1402 break;
1403
1404 default:
1405 goto unimplemented;
1406 }
1407 break;
1408 case SOL_IPV6:
1409 switch (optname) {
1410 case IPV6_MTU_DISCOVER:
1411 case IPV6_MTU:
1412 case IPV6_V6ONLY:
1413 case IPV6_RECVPKTINFO:
1414 val = 0;
1415 if (optlen < sizeof(uint32_t)) {
1416 return -TARGET_EINVAL;
1417 }
1418 if (get_user_u32(val, optval_addr)) {
1419 return -TARGET_EFAULT;
1420 }
1421 ret = get_errno(setsockopt(sockfd, level, optname,
1422 &val, sizeof(val)));
1423 break;
1424 default:
1425 goto unimplemented;
1426 }
1427 break;
1428 case SOL_RAW:
1429 switch (optname) {
1430 case ICMP_FILTER:
1431 /* struct icmp_filter takes an u32 value */
1432 if (optlen < sizeof(uint32_t)) {
1433 return -TARGET_EINVAL;
1434 }
1435
1436 if (get_user_u32(val, optval_addr)) {
1437 return -TARGET_EFAULT;
1438 }
1439 ret = get_errno(setsockopt(sockfd, level, optname,
1440 &val, sizeof(val)));
1441 break;
1442
1443 default:
1444 goto unimplemented;
1445 }
1446 break;
1447 case TARGET_SOL_SOCKET:
1448 switch (optname) {
1449 case TARGET_SO_RCVTIMEO:
1450 {
1451 struct timeval tv;
1452
1453 optname = SO_RCVTIMEO;
1454
1455 set_timeout:
1456 if (optlen != sizeof(struct target_timeval)) {
1457 return -TARGET_EINVAL;
1458 }
1459
1460 if (copy_from_user_timeval(&tv, optval_addr)) {
1461 return -TARGET_EFAULT;
1462 }
1463
1464 ret = get_errno(setsockopt(sockfd, SOL_SOCKET, optname,
1465 &tv, sizeof(tv)));
1466 return ret;
1467 }
1468 case TARGET_SO_SNDTIMEO:
1469 optname = SO_SNDTIMEO;
1470 goto set_timeout;
1471 case TARGET_SO_ATTACH_FILTER:
1472 {
1473 struct target_sock_fprog *tfprog;
1474 struct target_sock_filter *tfilter;
1475 struct sock_fprog fprog;
1476 struct sock_filter *filter;
1477 int i;
1478
1479 if (optlen != sizeof(*tfprog)) {
1480 return -TARGET_EINVAL;
1481 }
1482 if (!lock_user_struct(VERIFY_READ, tfprog, optval_addr, 0)) {
1483 return -TARGET_EFAULT;
1484 }
1485 if (!lock_user_struct(VERIFY_READ, tfilter,
1486 tswapal(tfprog->filter), 0)) {
1487 unlock_user_struct(tfprog, optval_addr, 1);
1488 return -TARGET_EFAULT;
1489 }
1490
1491 fprog.len = tswap16(tfprog->len);
1492 filter = malloc(fprog.len * sizeof(*filter));
1493 if (filter == NULL) {
1494 unlock_user_struct(tfilter, tfprog->filter, 1);
1495 unlock_user_struct(tfprog, optval_addr, 1);
1496 return -TARGET_ENOMEM;
1497 }
1498 for (i = 0; i < fprog.len; i++) {
1499 filter[i].code = tswap16(tfilter[i].code);
1500 filter[i].jt = tfilter[i].jt;
1501 filter[i].jf = tfilter[i].jf;
1502 filter[i].k = tswap32(tfilter[i].k);
1503 }
1504 fprog.filter = filter;
1505
1506 ret = get_errno(setsockopt(sockfd, SOL_SOCKET,
1507 SO_ATTACH_FILTER, &fprog, sizeof(fprog)));
1508 free(filter);
1509
1510 unlock_user_struct(tfilter, tfprog->filter, 1);
1511 unlock_user_struct(tfprog, optval_addr, 1);
1512 return ret;
1513 }
1514 case TARGET_SO_BINDTODEVICE:
1515 {
1516 char *dev_ifname, *addr_ifname;
1517
1518 if (optlen > IFNAMSIZ - 1) {
1519 optlen = IFNAMSIZ - 1;
1520 }
1521 dev_ifname = lock_user(VERIFY_READ, optval_addr, optlen, 1);
1522 if (!dev_ifname) {
1523 return -TARGET_EFAULT;
1524 }
1525 optname = SO_BINDTODEVICE;
1526 addr_ifname = alloca(IFNAMSIZ);
1527 memcpy(addr_ifname, dev_ifname, optlen);
1528 addr_ifname[optlen] = 0;
1529 ret = get_errno(setsockopt(sockfd, level, optname, addr_ifname, optlen));
1530 unlock_user (dev_ifname, optval_addr, 0);
1531 return ret;
1532 }
1533 /* Options with 'int' argument. */
1534 case TARGET_SO_DEBUG:
1535 optname = SO_DEBUG;
1536 break;
1537 case TARGET_SO_REUSEADDR:
1538 optname = SO_REUSEADDR;
1539 break;
1540 case TARGET_SO_TYPE:
1541 optname = SO_TYPE;
1542 break;
1543 case TARGET_SO_ERROR:
1544 optname = SO_ERROR;
1545 break;
1546 case TARGET_SO_DONTROUTE:
1547 optname = SO_DONTROUTE;
1548 break;
1549 case TARGET_SO_BROADCAST:
1550 optname = SO_BROADCAST;
1551 break;
1552 case TARGET_SO_SNDBUF:
1553 optname = SO_SNDBUF;
1554 break;
1555 case TARGET_SO_SNDBUFFORCE:
1556 optname = SO_SNDBUFFORCE;
1557 break;
1558 case TARGET_SO_RCVBUF:
1559 optname = SO_RCVBUF;
1560 break;
1561 case TARGET_SO_RCVBUFFORCE:
1562 optname = SO_RCVBUFFORCE;
1563 break;
1564 case TARGET_SO_KEEPALIVE:
1565 optname = SO_KEEPALIVE;
1566 break;
1567 case TARGET_SO_OOBINLINE:
1568 optname = SO_OOBINLINE;
1569 break;
1570 case TARGET_SO_NO_CHECK:
1571 optname = SO_NO_CHECK;
1572 break;
1573 case TARGET_SO_PRIORITY:
1574 optname = SO_PRIORITY;
1575 break;
1576 #ifdef SO_BSDCOMPAT
1577 case TARGET_SO_BSDCOMPAT:
1578 optname = SO_BSDCOMPAT;
1579 break;
1580 #endif
1581 case TARGET_SO_PASSCRED:
1582 optname = SO_PASSCRED;
1583 break;
1584 case TARGET_SO_PASSSEC:
1585 optname = SO_PASSSEC;
1586 break;
1587 case TARGET_SO_TIMESTAMP:
1588 optname = SO_TIMESTAMP;
1589 break;
1590 case TARGET_SO_RCVLOWAT:
1591 optname = SO_RCVLOWAT;
1592 break;
1593 break;
1594 default:
1595 goto unimplemented;
1596 }
1597 if (optlen < sizeof(uint32_t))
1598 return -TARGET_EINVAL;
1599
1600 if (get_user_u32(val, optval_addr))
1601 return -TARGET_EFAULT;
1602 ret = get_errno(setsockopt(sockfd, SOL_SOCKET, optname, &val, sizeof(val)));
1603 break;
1604 default:
1605 unimplemented:
1606 gemu_log("Unsupported setsockopt level=%d optname=%d\n", level, optname);
1607 ret = -TARGET_ENOPROTOOPT;
1608 }
1609 return ret;
1610 }
1611
1612 /* do_getsockopt() Must return target values and target errnos. */
1613 static abi_long do_getsockopt(int sockfd, int level, int optname,
1614 abi_ulong optval_addr, abi_ulong optlen)
1615 {
1616 abi_long ret;
1617 int len, val;
1618 socklen_t lv;
1619
1620 switch(level) {
1621 case TARGET_SOL_SOCKET:
1622 level = SOL_SOCKET;
1623 switch (optname) {
1624 /* These don't just return a single integer */
1625 case TARGET_SO_LINGER:
1626 case TARGET_SO_RCVTIMEO:
1627 case TARGET_SO_SNDTIMEO:
1628 case TARGET_SO_PEERNAME:
1629 goto unimplemented;
1630 case TARGET_SO_PEERCRED: {
1631 struct ucred cr;
1632 socklen_t crlen;
1633 struct target_ucred *tcr;
1634
1635 if (get_user_u32(len, optlen)) {
1636 return -TARGET_EFAULT;
1637 }
1638 if (len < 0) {
1639 return -TARGET_EINVAL;
1640 }
1641
1642 crlen = sizeof(cr);
1643 ret = get_errno(getsockopt(sockfd, level, SO_PEERCRED,
1644 &cr, &crlen));
1645 if (ret < 0) {
1646 return ret;
1647 }
1648 if (len > crlen) {
1649 len = crlen;
1650 }
1651 if (!lock_user_struct(VERIFY_WRITE, tcr, optval_addr, 0)) {
1652 return -TARGET_EFAULT;
1653 }
1654 __put_user(cr.pid, &tcr->pid);
1655 __put_user(cr.uid, &tcr->uid);
1656 __put_user(cr.gid, &tcr->gid);
1657 unlock_user_struct(tcr, optval_addr, 1);
1658 if (put_user_u32(len, optlen)) {
1659 return -TARGET_EFAULT;
1660 }
1661 break;
1662 }
1663 /* Options with 'int' argument. */
1664 case TARGET_SO_DEBUG:
1665 optname = SO_DEBUG;
1666 goto int_case;
1667 case TARGET_SO_REUSEADDR:
1668 optname = SO_REUSEADDR;
1669 goto int_case;
1670 case TARGET_SO_TYPE:
1671 optname = SO_TYPE;
1672 goto int_case;
1673 case TARGET_SO_ERROR:
1674 optname = SO_ERROR;
1675 goto int_case;
1676 case TARGET_SO_DONTROUTE:
1677 optname = SO_DONTROUTE;
1678 goto int_case;
1679 case TARGET_SO_BROADCAST:
1680 optname = SO_BROADCAST;
1681 goto int_case;
1682 case TARGET_SO_SNDBUF:
1683 optname = SO_SNDBUF;
1684 goto int_case;
1685 case TARGET_SO_RCVBUF:
1686 optname = SO_RCVBUF;
1687 goto int_case;
1688 case TARGET_SO_KEEPALIVE:
1689 optname = SO_KEEPALIVE;
1690 goto int_case;
1691 case TARGET_SO_OOBINLINE:
1692 optname = SO_OOBINLINE;
1693 goto int_case;
1694 case TARGET_SO_NO_CHECK:
1695 optname = SO_NO_CHECK;
1696 goto int_case;
1697 case TARGET_SO_PRIORITY:
1698 optname = SO_PRIORITY;
1699 goto int_case;
1700 #ifdef SO_BSDCOMPAT
1701 case TARGET_SO_BSDCOMPAT:
1702 optname = SO_BSDCOMPAT;
1703 goto int_case;
1704 #endif
1705 case TARGET_SO_PASSCRED:
1706 optname = SO_PASSCRED;
1707 goto int_case;
1708 case TARGET_SO_TIMESTAMP:
1709 optname = SO_TIMESTAMP;
1710 goto int_case;
1711 case TARGET_SO_RCVLOWAT:
1712 optname = SO_RCVLOWAT;
1713 goto int_case;
1714 case TARGET_SO_ACCEPTCONN:
1715 optname = SO_ACCEPTCONN;
1716 goto int_case;
1717 default:
1718 goto int_case;
1719 }
1720 break;
1721 case SOL_TCP:
1722 /* TCP options all take an 'int' value. */
1723 int_case:
1724 if (get_user_u32(len, optlen))
1725 return -TARGET_EFAULT;
1726 if (len < 0)
1727 return -TARGET_EINVAL;
1728 lv = sizeof(lv);
1729 ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
1730 if (ret < 0)
1731 return ret;
1732 if (optname == SO_TYPE) {
1733 val = host_to_target_sock_type(val);
1734 }
1735 if (len > lv)
1736 len = lv;
1737 if (len == 4) {
1738 if (put_user_u32(val, optval_addr))
1739 return -TARGET_EFAULT;
1740 } else {
1741 if (put_user_u8(val, optval_addr))
1742 return -TARGET_EFAULT;
1743 }
1744 if (put_user_u32(len, optlen))
1745 return -TARGET_EFAULT;
1746 break;
1747 case SOL_IP:
1748 switch(optname) {
1749 case IP_TOS:
1750 case IP_TTL:
1751 case IP_HDRINCL:
1752 case IP_ROUTER_ALERT:
1753 case IP_RECVOPTS:
1754 case IP_RETOPTS:
1755 case IP_PKTINFO:
1756 case IP_MTU_DISCOVER:
1757 case IP_RECVERR:
1758 case IP_RECVTOS:
1759 #ifdef IP_FREEBIND
1760 case IP_FREEBIND:
1761 #endif
1762 case IP_MULTICAST_TTL:
1763 case IP_MULTICAST_LOOP:
1764 if (get_user_u32(len, optlen))
1765 return -TARGET_EFAULT;
1766 if (len < 0)
1767 return -TARGET_EINVAL;
1768 lv = sizeof(lv);
1769 ret = get_errno(getsockopt(sockfd, level, optname, &val, &lv));
1770 if (ret < 0)
1771 return ret;
1772 if (len < sizeof(int) && len > 0 && val >= 0 && val < 255) {
1773 len = 1;
1774 if (put_user_u32(len, optlen)
1775 || put_user_u8(val, optval_addr))
1776 return -TARGET_EFAULT;
1777 } else {
1778 if (len > sizeof(int))
1779 len = sizeof(int);
1780 if (put_user_u32(len, optlen)
1781 || put_user_u32(val, optval_addr))
1782 return -TARGET_EFAULT;
1783 }
1784 break;
1785 default:
1786 ret = -TARGET_ENOPROTOOPT;
1787 break;
1788 }
1789 break;
1790 default:
1791 unimplemented:
1792 gemu_log("getsockopt level=%d optname=%d not yet supported\n",
1793 level, optname);
1794 ret = -TARGET_EOPNOTSUPP;
1795 break;
1796 }
1797 return ret;
1798 }
1799
1800 static struct iovec *lock_iovec(int type, abi_ulong target_addr,
1801 int count, int copy)
1802 {
1803 struct target_iovec *target_vec;
1804 struct iovec *vec;
1805 abi_ulong total_len, max_len;
1806 int i;
1807 int err = 0;
1808 bool bad_address = false;
1809
1810 if (count == 0) {
1811 errno = 0;
1812 return NULL;
1813 }
1814 if (count < 0 || count > IOV_MAX) {
1815 errno = EINVAL;
1816 return NULL;
1817 }
1818
1819 vec = calloc(count, sizeof(struct iovec));
1820 if (vec == NULL) {
1821 errno = ENOMEM;
1822 return NULL;
1823 }
1824
1825 target_vec = lock_user(VERIFY_READ, target_addr,
1826 count * sizeof(struct target_iovec), 1);
1827 if (target_vec == NULL) {
1828 err = EFAULT;
1829 goto fail2;
1830 }
1831
1832 /* ??? If host page size > target page size, this will result in a
1833 value larger than what we can actually support. */
1834 max_len = 0x7fffffff & TARGET_PAGE_MASK;
1835 total_len = 0;
1836
1837 for (i = 0; i < count; i++) {
1838 abi_ulong base = tswapal(target_vec[i].iov_base);
1839 abi_long len = tswapal(target_vec[i].iov_len);
1840
1841 if (len < 0) {
1842 err = EINVAL;
1843 goto fail;
1844 } else if (len == 0) {
1845 /* Zero length pointer is ignored. */
1846 vec[i].iov_base = 0;
1847 } else {
1848 vec[i].iov_base = lock_user(type, base, len, copy);
1849 /* If the first buffer pointer is bad, this is a fault. But
1850 * subsequent bad buffers will result in a partial write; this
1851 * is realized by filling the vector with null pointers and
1852 * zero lengths. */
1853 if (!vec[i].iov_base) {
1854 if (i == 0) {
1855 err = EFAULT;
1856 goto fail;
1857 } else {
1858 bad_address = true;
1859 }
1860 }
1861 if (bad_address) {
1862 len = 0;
1863 }
1864 if (len > max_len - total_len) {
1865 len = max_len - total_len;
1866 }
1867 }
1868 vec[i].iov_len = len;
1869 total_len += len;
1870 }
1871
1872 unlock_user(target_vec, target_addr, 0);
1873 return vec;
1874
1875 fail:
1876 unlock_user(target_vec, target_addr, 0);
1877 fail2:
1878 free(vec);
1879 errno = err;
1880 return NULL;
1881 }
1882
1883 static void unlock_iovec(struct iovec *vec, abi_ulong target_addr,
1884 int count, int copy)
1885 {
1886 struct target_iovec *target_vec;
1887 int i;
1888
1889 target_vec = lock_user(VERIFY_READ, target_addr,
1890 count * sizeof(struct target_iovec), 1);
1891 if (target_vec) {
1892 for (i = 0; i < count; i++) {
1893 abi_ulong base = tswapal(target_vec[i].iov_base);
1894 abi_long len = tswapal(target_vec[i].iov_base);
1895 if (len < 0) {
1896 break;
1897 }
1898 unlock_user(vec[i].iov_base, base, copy ? vec[i].iov_len : 0);
1899 }
1900 unlock_user(target_vec, target_addr, 0);
1901 }
1902
1903 free(vec);
1904 }
1905
1906 static inline int target_to_host_sock_type(int *type)
1907 {
1908 int host_type = 0;
1909 int target_type = *type;
1910
1911 switch (target_type & TARGET_SOCK_TYPE_MASK) {
1912 case TARGET_SOCK_DGRAM:
1913 host_type = SOCK_DGRAM;
1914 break;
1915 case TARGET_SOCK_STREAM:
1916 host_type = SOCK_STREAM;
1917 break;
1918 default:
1919 host_type = target_type & TARGET_SOCK_TYPE_MASK;
1920 break;
1921 }
1922 if (target_type & TARGET_SOCK_CLOEXEC) {
1923 #if defined(SOCK_CLOEXEC)
1924 host_type |= SOCK_CLOEXEC;
1925 #else
1926 return -TARGET_EINVAL;
1927 #endif
1928 }
1929 if (target_type & TARGET_SOCK_NONBLOCK) {
1930 #if defined(SOCK_NONBLOCK)
1931 host_type |= SOCK_NONBLOCK;
1932 #elif !defined(O_NONBLOCK)
1933 return -TARGET_EINVAL;
1934 #endif
1935 }
1936 *type = host_type;
1937 return 0;
1938 }
1939
1940 /* Try to emulate socket type flags after socket creation. */
1941 static int sock_flags_fixup(int fd, int target_type)
1942 {
1943 #if !defined(SOCK_NONBLOCK) && defined(O_NONBLOCK)
1944 if (target_type & TARGET_SOCK_NONBLOCK) {
1945 int flags = fcntl(fd, F_GETFL);
1946 if (fcntl(fd, F_SETFL, O_NONBLOCK | flags) == -1) {
1947 close(fd);
1948 return -TARGET_EINVAL;
1949 }
1950 }
1951 #endif
1952 return fd;
1953 }
1954
1955 /* do_socket() Must return target values and target errnos. */
1956 static abi_long do_socket(int domain, int type, int protocol)
1957 {
1958 int target_type = type;
1959 int ret;
1960
1961 ret = target_to_host_sock_type(&type);
1962 if (ret) {
1963 return ret;
1964 }
1965
1966 if (domain == PF_NETLINK)
1967 return -TARGET_EAFNOSUPPORT;
1968 ret = get_errno(socket(domain, type, protocol));
1969 if (ret >= 0) {
1970 ret = sock_flags_fixup(ret, target_type);
1971 }
1972 return ret;
1973 }
1974
1975 /* do_bind() Must return target values and target errnos. */
1976 static abi_long do_bind(int sockfd, abi_ulong target_addr,
1977 socklen_t addrlen)
1978 {
1979 void *addr;
1980 abi_long ret;
1981
1982 if ((int)addrlen < 0) {
1983 return -TARGET_EINVAL;
1984 }
1985
1986 addr = alloca(addrlen+1);
1987
1988 ret = target_to_host_sockaddr(addr, target_addr, addrlen);
1989 if (ret)
1990 return ret;
1991
1992 return get_errno(bind(sockfd, addr, addrlen));
1993 }
1994
1995 /* do_connect() Must return target values and target errnos. */
1996 static abi_long do_connect(int sockfd, abi_ulong target_addr,
1997 socklen_t addrlen)
1998 {
1999 void *addr;
2000 abi_long ret;
2001
2002 if ((int)addrlen < 0) {
2003 return -TARGET_EINVAL;
2004 }
2005
2006 addr = alloca(addrlen+1);
2007
2008 ret = target_to_host_sockaddr(addr, target_addr, addrlen);
2009 if (ret)
2010 return ret;
2011
2012 return get_errno(connect(sockfd, addr, addrlen));
2013 }
2014
2015 /* do_sendrecvmsg_locked() Must return target values and target errnos. */
2016 static abi_long do_sendrecvmsg_locked(int fd, struct target_msghdr *msgp,
2017 int flags, int send)
2018 {
2019 abi_long ret, len;
2020 struct msghdr msg;
2021 int count;
2022 struct iovec *vec;
2023 abi_ulong target_vec;
2024
2025 if (msgp->msg_name) {
2026 msg.msg_namelen = tswap32(msgp->msg_namelen);
2027 msg.msg_name = alloca(msg.msg_namelen+1);
2028 ret = target_to_host_sockaddr(msg.msg_name, tswapal(msgp->msg_name),
2029 msg.msg_namelen);
2030 if (ret) {
2031 goto out2;
2032 }
2033 } else {
2034 msg.msg_name = NULL;
2035 msg.msg_namelen = 0;
2036 }
2037 msg.msg_controllen = 2 * tswapal(msgp->msg_controllen);
2038 msg.msg_control = alloca(msg.msg_controllen);
2039 msg.msg_flags = tswap32(msgp->msg_flags);
2040
2041 count = tswapal(msgp->msg_iovlen);
2042 target_vec = tswapal(msgp->msg_iov);
2043 vec = lock_iovec(send ? VERIFY_READ : VERIFY_WRITE,
2044 target_vec, count, send);
2045 if (vec == NULL) {
2046 ret = -host_to_target_errno(errno);
2047 goto out2;
2048 }
2049 msg.msg_iovlen = count;
2050 msg.msg_iov = vec;
2051
2052 if (send) {
2053 ret = target_to_host_cmsg(&msg, msgp);
2054 if (ret == 0)
2055 ret = get_errno(sendmsg(fd, &msg, flags));
2056 } else {
2057 ret = get_errno(recvmsg(fd, &msg, flags));
2058 if (!is_error(ret)) {
2059 len = ret;
2060 ret = host_to_target_cmsg(msgp, &msg);
2061 if (!is_error(ret)) {
2062 msgp->msg_namelen = tswap32(msg.msg_namelen);
2063 if (msg.msg_name != NULL) {
2064 ret = host_to_target_sockaddr(tswapal(msgp->msg_name),
2065 msg.msg_name, msg.msg_namelen);
2066 if (ret) {
2067 goto out;
2068 }
2069 }
2070
2071 ret = len;
2072 }
2073 }
2074 }
2075
2076 out:
2077 unlock_iovec(vec, target_vec, count, !send);
2078 out2:
2079 return ret;
2080 }
2081
2082 static abi_long do_sendrecvmsg(int fd, abi_ulong target_msg,
2083 int flags, int send)
2084 {
2085 abi_long ret;
2086 struct target_msghdr *msgp;
2087
2088 if (!lock_user_struct(send ? VERIFY_READ : VERIFY_WRITE,
2089 msgp,
2090 target_msg,
2091 send ? 1 : 0)) {
2092 return -TARGET_EFAULT;
2093 }
2094 ret = do_sendrecvmsg_locked(fd, msgp, flags, send);
2095 unlock_user_struct(msgp, target_msg, send ? 0 : 1);
2096 return ret;
2097 }
2098
2099 #ifdef TARGET_NR_sendmmsg
2100 /* We don't rely on the C library to have sendmmsg/recvmmsg support,
2101 * so it might not have this *mmsg-specific flag either.
2102 */
2103 #ifndef MSG_WAITFORONE
2104 #define MSG_WAITFORONE 0x10000
2105 #endif
2106
2107 static abi_long do_sendrecvmmsg(int fd, abi_ulong target_msgvec,
2108 unsigned int vlen, unsigned int flags,
2109 int send)
2110 {
2111 struct target_mmsghdr *mmsgp;
2112 abi_long ret = 0;
2113 int i;
2114
2115 if (vlen > UIO_MAXIOV) {
2116 vlen = UIO_MAXIOV;
2117 }
2118
2119 mmsgp = lock_user(VERIFY_WRITE, target_msgvec, sizeof(*mmsgp) * vlen, 1);
2120 if (!mmsgp) {
2121 return -TARGET_EFAULT;
2122 }
2123
2124 for (i = 0; i < vlen; i++) {
2125 ret = do_sendrecvmsg_locked(fd, &mmsgp[i].msg_hdr, flags, send);
2126 if (is_error(ret)) {
2127 break;
2128 }
2129 mmsgp[i].msg_len = tswap32(ret);
2130 /* MSG_WAITFORONE turns on MSG_DONTWAIT after one packet */
2131 if (flags & MSG_WAITFORONE) {
2132 flags |= MSG_DONTWAIT;
2133 }
2134 }
2135
2136 unlock_user(mmsgp, target_msgvec, sizeof(*mmsgp) * i);
2137
2138 /* Return number of datagrams sent if we sent any at all;
2139 * otherwise return the error.
2140 */
2141 if (i) {
2142 return i;
2143 }
2144 return ret;
2145 }
2146 #endif
2147
2148 /* If we don't have a system accept4() then just call accept.
2149 * The callsites to do_accept4() will ensure that they don't
2150 * pass a non-zero flags argument in this config.
2151 */
2152 #ifndef CONFIG_ACCEPT4
2153 static inline int accept4(int sockfd, struct sockaddr *addr,
2154 socklen_t *addrlen, int flags)
2155 {
2156 assert(flags == 0);
2157 return accept(sockfd, addr, addrlen);
2158 }
2159 #endif
2160
2161 /* do_accept4() Must return target values and target errnos. */
2162 static abi_long do_accept4(int fd, abi_ulong target_addr,
2163 abi_ulong target_addrlen_addr, int flags)
2164 {
2165 socklen_t addrlen;
2166 void *addr;
2167 abi_long ret;
2168 int host_flags;
2169
2170 host_flags = target_to_host_bitmask(flags, fcntl_flags_tbl);
2171
2172 if (target_addr == 0) {
2173 return get_errno(accept4(fd, NULL, NULL, host_flags));
2174 }
2175
2176 /* linux returns EINVAL if addrlen pointer is invalid */
2177 if (get_user_u32(addrlen, target_addrlen_addr))
2178 return -TARGET_EINVAL;
2179
2180 if ((int)addrlen < 0) {
2181 return -TARGET_EINVAL;
2182 }
2183
2184 if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
2185 return -TARGET_EINVAL;
2186
2187 addr = alloca(addrlen);
2188
2189 ret = get_errno(accept4(fd, addr, &addrlen, host_flags));
2190 if (!is_error(ret)) {
2191 host_to_target_sockaddr(target_addr, addr, addrlen);
2192 if (put_user_u32(addrlen, target_addrlen_addr))
2193 ret = -TARGET_EFAULT;
2194 }
2195 return ret;
2196 }
2197
2198 /* do_getpeername() Must return target values and target errnos. */
2199 static abi_long do_getpeername(int fd, abi_ulong target_addr,
2200 abi_ulong target_addrlen_addr)
2201 {
2202 socklen_t addrlen;
2203 void *addr;
2204 abi_long ret;
2205
2206 if (get_user_u32(addrlen, target_addrlen_addr))
2207 return -TARGET_EFAULT;
2208
2209 if ((int)addrlen < 0) {
2210 return -TARGET_EINVAL;
2211 }
2212
2213 if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
2214 return -TARGET_EFAULT;
2215
2216 addr = alloca(addrlen);
2217
2218 ret = get_errno(getpeername(fd, addr, &addrlen));
2219 if (!is_error(ret)) {
2220 host_to_target_sockaddr(target_addr, addr, addrlen);
2221 if (put_user_u32(addrlen, target_addrlen_addr))
2222 ret = -TARGET_EFAULT;
2223 }
2224 return ret;
2225 }
2226
2227 /* do_getsockname() Must return target values and target errnos. */
2228 static abi_long do_getsockname(int fd, abi_ulong target_addr,
2229 abi_ulong target_addrlen_addr)
2230 {
2231 socklen_t addrlen;
2232 void *addr;
2233 abi_long ret;
2234
2235 if (get_user_u32(addrlen, target_addrlen_addr))
2236 return -TARGET_EFAULT;
2237
2238 if ((int)addrlen < 0) {
2239 return -TARGET_EINVAL;
2240 }
2241
2242 if (!access_ok(VERIFY_WRITE, target_addr, addrlen))
2243 return -TARGET_EFAULT;
2244
2245 addr = alloca(addrlen);
2246
2247 ret = get_errno(getsockname(fd, addr, &addrlen));
2248 if (!is_error(ret)) {
2249 host_to_target_sockaddr(target_addr, addr, addrlen);
2250 if (put_user_u32(addrlen, target_addrlen_addr))
2251 ret = -TARGET_EFAULT;
2252 }
2253 return ret;
2254 }
2255
2256 /* do_socketpair() Must return target values and target errnos. */
2257 static abi_long do_socketpair(int domain, int type, int protocol,
2258 abi_ulong target_tab_addr)
2259 {
2260 int tab[2];
2261 abi_long ret;
2262
2263 target_to_host_sock_type(&type);
2264
2265 ret = get_errno(socketpair(domain, type, protocol, tab));
2266 if (!is_error(ret)) {
2267 if (put_user_s32(tab[0], target_tab_addr)
2268 || put_user_s32(tab[1], target_tab_addr + sizeof(tab[0])))
2269 ret = -TARGET_EFAULT;
2270 }
2271 return ret;
2272 }
2273
2274 /* do_sendto() Must return target values and target errnos. */
2275 static abi_long do_sendto(int fd, abi_ulong msg, size_t len, int flags,
2276 abi_ulong target_addr, socklen_t addrlen)
2277 {
2278 void *addr;
2279 void *host_msg;
2280 abi_long ret;
2281
2282 if ((int)addrlen < 0) {
2283 return -TARGET_EINVAL;
2284 }
2285
2286 host_msg = lock_user(VERIFY_READ, msg, len, 1);
2287 if (!host_msg)
2288 return -TARGET_EFAULT;
2289 if (target_addr) {
2290 addr = alloca(addrlen+1);
2291 ret = target_to_host_sockaddr(addr, target_addr, addrlen);
2292 if (ret) {
2293 unlock_user(host_msg, msg, 0);
2294 return ret;
2295 }
2296 ret = get_errno(sendto(fd, host_msg, len, flags, addr, addrlen));
2297 } else {
2298 ret = get_errno(send(fd, host_msg, len, flags));
2299 }
2300 unlock_user(host_msg, msg, 0);
2301 return ret;
2302 }
2303
2304 /* do_recvfrom() Must return target values and target errnos. */
2305 static abi_long do_recvfrom(int fd, abi_ulong msg, size_t len, int flags,
2306 abi_ulong target_addr,
2307 abi_ulong target_addrlen)
2308 {
2309 socklen_t addrlen;
2310 void *addr;
2311 void *host_msg;
2312 abi_long ret;
2313
2314 host_msg = lock_user(VERIFY_WRITE, msg, len, 0);
2315 if (!host_msg)
2316 return -TARGET_EFAULT;
2317 if (target_addr) {
2318 if (get_user_u32(addrlen, target_addrlen)) {
2319 ret = -TARGET_EFAULT;
2320 goto fail;
2321 }
2322 if ((int)addrlen < 0) {
2323 ret = -TARGET_EINVAL;
2324 goto fail;
2325 }
2326 addr = alloca(addrlen);
2327 ret = get_errno(recvfrom(fd, host_msg, len, flags, addr, &addrlen));
2328 } else {
2329 addr = NULL; /* To keep compiler quiet. */
2330 ret = get_errno(qemu_recv(fd, host_msg, len, flags));
2331 }
2332 if (!is_error(ret)) {
2333 if (target_addr) {
2334 host_to_target_sockaddr(target_addr, addr, addrlen);
2335 if (put_user_u32(addrlen, target_addrlen)) {
2336 ret = -TARGET_EFAULT;
2337 goto fail;
2338 }
2339 }
2340 unlock_user(host_msg, msg, len);
2341 } else {
2342 fail:
2343 unlock_user(host_msg, msg, 0);
2344 }
2345 return ret;
2346 }
2347
2348 #ifdef TARGET_NR_socketcall
2349 /* do_socketcall() Must return target values and target errnos. */
2350 static abi_long do_socketcall(int num, abi_ulong vptr)
2351 {
2352 static const unsigned ac[] = { /* number of arguments per call */
2353 [SOCKOP_socket] = 3, /* domain, type, protocol */
2354 [SOCKOP_bind] = 3, /* sockfd, addr, addrlen */
2355 [SOCKOP_connect] = 3, /* sockfd, addr, addrlen */
2356 [SOCKOP_listen] = 2, /* sockfd, backlog */
2357 [SOCKOP_accept] = 3, /* sockfd, addr, addrlen */
2358 [SOCKOP_accept4] = 4, /* sockfd, addr, addrlen, flags */
2359 [SOCKOP_getsockname] = 3, /* sockfd, addr, addrlen */
2360 [SOCKOP_getpeername] = 3, /* sockfd, addr, addrlen */
2361 [SOCKOP_socketpair] = 4, /* domain, type, protocol, tab */
2362 [SOCKOP_send] = 4, /* sockfd, msg, len, flags */
2363 [SOCKOP_recv] = 4, /* sockfd, msg, len, flags */
2364 [SOCKOP_sendto] = 6, /* sockfd, msg, len, flags, addr, addrlen */
2365 [SOCKOP_recvfrom] = 6, /* sockfd, msg, len, flags, addr, addrlen */
2366 [SOCKOP_shutdown] = 2, /* sockfd, how */
2367 [SOCKOP_sendmsg] = 3, /* sockfd, msg, flags */
2368 [SOCKOP_recvmsg] = 3, /* sockfd, msg, flags */
2369 [SOCKOP_setsockopt] = 5, /* sockfd, level, optname, optval, optlen */
2370 [SOCKOP_getsockopt] = 5, /* sockfd, level, optname, optval, optlen */
2371 };
2372 abi_long a[6]; /* max 6 args */
2373
2374 /* first, collect the arguments in a[] according to ac[] */
2375 if (num >= 0 && num < ARRAY_SIZE(ac)) {
2376 unsigned i;
2377 assert(ARRAY_SIZE(a) >= ac[num]); /* ensure we have space for args */
2378 for (i = 0; i < ac[num]; ++i) {
2379 if (get_user_ual(a[i], vptr + i * sizeof(abi_long)) != 0) {
2380 return -TARGET_EFAULT;
2381 }
2382 }
2383 }
2384
2385 /* now when we have the args, actually handle the call */
2386 switch (num) {
2387 case SOCKOP_socket: /* domain, type, protocol */
2388 return do_socket(a[0], a[1], a[2]);
2389 case SOCKOP_bind: /* sockfd, addr, addrlen */
2390 return do_bind(a[0], a[1], a[2]);
2391 case SOCKOP_connect: /* sockfd, addr, addrlen */
2392 return do_connect(a[0], a[1], a[2]);
2393 case SOCKOP_listen: /* sockfd, backlog */
2394 return get_errno(listen(a[0], a[1]));
2395 case SOCKOP_accept: /* sockfd, addr, addrlen */
2396 return do_accept4(a[0], a[1], a[2], 0);
2397 case SOCKOP_accept4: /* sockfd, addr, addrlen, flags */
2398 return do_accept4(a[0], a[1], a[2], a[3]);
2399 case SOCKOP_getsockname: /* sockfd, addr, addrlen */
2400 return do_getsockname(a[0], a[1], a[2]);
2401 case SOCKOP_getpeername: /* sockfd, addr, addrlen */
2402 return do_getpeername(a[0], a[1], a[2]);
2403 case SOCKOP_socketpair: /* domain, type, protocol, tab */
2404 return do_socketpair(a[0], a[1], a[2], a[3]);
2405 case SOCKOP_send: /* sockfd, msg, len, flags */
2406 return do_sendto(a[0], a[1], a[2], a[3], 0, 0);
2407 case SOCKOP_recv: /* sockfd, msg, len, flags */
2408 return do_recvfrom(a[0], a[1], a[2], a[3], 0, 0);
2409 case SOCKOP_sendto: /* sockfd, msg, len, flags, addr, addrlen */
2410 return do_sendto(a[0], a[1], a[2], a[3], a[4], a[5]);
2411 case SOCKOP_recvfrom: /* sockfd, msg, len, flags, addr, addrlen */
2412 return do_recvfrom(a[0], a[1], a[2], a[3], a[4], a[5]);
2413 case SOCKOP_shutdown: /* sockfd, how */
2414 return get_errno(shutdown(a[0], a[1]));
2415 case SOCKOP_sendmsg: /* sockfd, msg, flags */
2416 return do_sendrecvmsg(a[0], a[1], a[2], 1);
2417 case SOCKOP_recvmsg: /* sockfd, msg, flags */
2418 return do_sendrecvmsg(a[0], a[1], a[2], 0);
2419 case SOCKOP_setsockopt: /* sockfd, level, optname, optval, optlen */
2420 return do_setsockopt(a[0], a[1], a[2], a[3], a[4]);
2421 case SOCKOP_getsockopt: /* sockfd, level, optname, optval, optlen */
2422 return do_getsockopt(a[0], a[1], a[2], a[3], a[4]);
2423 default:
2424 gemu_log("Unsupported socketcall: %d\n", num);
2425 return -TARGET_ENOSYS;
2426 }
2427 }
2428 #endif
2429
2430 #define N_SHM_REGIONS 32
2431
2432 static struct shm_region {
2433 abi_ulong start;
2434 abi_ulong size;
2435 } shm_regions[N_SHM_REGIONS];
2436
2437 struct target_semid_ds
2438 {
2439 struct target_ipc_perm sem_perm;
2440 abi_ulong sem_otime;
2441 #if !defined(TARGET_PPC64)
2442 abi_ulong __unused1;
2443 #endif
2444 abi_ulong sem_ctime;
2445 #if !defined(TARGET_PPC64)
2446 abi_ulong __unused2;
2447 #endif
2448 abi_ulong sem_nsems;
2449 abi_ulong __unused3;
2450 abi_ulong __unused4;
2451 };
2452
2453 static inline abi_long target_to_host_ipc_perm(struct ipc_perm *host_ip,
2454 abi_ulong target_addr)
2455 {
2456 struct target_ipc_perm *target_ip;
2457 struct target_semid_ds *target_sd;
2458
2459 if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2460 return -TARGET_EFAULT;
2461 target_ip = &(target_sd->sem_perm);
2462 host_ip->__key = tswap32(target_ip->__key);
2463 host_ip->uid = tswap32(target_ip->uid);
2464 host_ip->gid = tswap32(target_ip->gid);
2465 host_ip->cuid = tswap32(target_ip->cuid);
2466 host_ip->cgid = tswap32(target_ip->cgid);
2467 #if defined(TARGET_ALPHA) || defined(TARGET_MIPS) || defined(TARGET_PPC)
2468 host_ip->mode = tswap32(target_ip->mode);
2469 #else
2470 host_ip->mode = tswap16(target_ip->mode);
2471 #endif
2472 #if defined(TARGET_PPC)
2473 host_ip->__seq = tswap32(target_ip->__seq);
2474 #else
2475 host_ip->__seq = tswap16(target_ip->__seq);
2476 #endif
2477 unlock_user_struct(target_sd, target_addr, 0);
2478 return 0;
2479 }
2480
2481 static inline abi_long host_to_target_ipc_perm(abi_ulong target_addr,
2482 struct ipc_perm *host_ip)
2483 {
2484 struct target_ipc_perm *target_ip;
2485 struct target_semid_ds *target_sd;
2486
2487 if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2488 return -TARGET_EFAULT;
2489 target_ip = &(target_sd->sem_perm);
2490 target_ip->__key = tswap32(host_ip->__key);
2491 target_ip->uid = tswap32(host_ip->uid);
2492 target_ip->gid = tswap32(host_ip->gid);
2493 target_ip->cuid = tswap32(host_ip->cuid);
2494 target_ip->cgid = tswap32(host_ip->cgid);
2495 #if defined(TARGET_ALPHA) || defined(TARGET_MIPS) || defined(TARGET_PPC)
2496 target_ip->mode = tswap32(host_ip->mode);
2497 #else
2498 target_ip->mode = tswap16(host_ip->mode);
2499 #endif
2500 #if defined(TARGET_PPC)
2501 target_ip->__seq = tswap32(host_ip->__seq);
2502 #else
2503 target_ip->__seq = tswap16(host_ip->__seq);
2504 #endif
2505 unlock_user_struct(target_sd, target_addr, 1);
2506 return 0;
2507 }
2508
2509 static inline abi_long target_to_host_semid_ds(struct semid_ds *host_sd,
2510 abi_ulong target_addr)
2511 {
2512 struct target_semid_ds *target_sd;
2513
2514 if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2515 return -TARGET_EFAULT;
2516 if (target_to_host_ipc_perm(&(host_sd->sem_perm),target_addr))
2517 return -TARGET_EFAULT;
2518 host_sd->sem_nsems = tswapal(target_sd->sem_nsems);
2519 host_sd->sem_otime = tswapal(target_sd->sem_otime);
2520 host_sd->sem_ctime = tswapal(target_sd->sem_ctime);
2521 unlock_user_struct(target_sd, target_addr, 0);
2522 return 0;
2523 }
2524
2525 static inline abi_long host_to_target_semid_ds(abi_ulong target_addr,
2526 struct semid_ds *host_sd)
2527 {
2528 struct target_semid_ds *target_sd;
2529
2530 if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2531 return -TARGET_EFAULT;
2532 if (host_to_target_ipc_perm(target_addr,&(host_sd->sem_perm)))
2533 return -TARGET_EFAULT;
2534 target_sd->sem_nsems = tswapal(host_sd->sem_nsems);
2535 target_sd->sem_otime = tswapal(host_sd->sem_otime);
2536 target_sd->sem_ctime = tswapal(host_sd->sem_ctime);
2537 unlock_user_struct(target_sd, target_addr, 1);
2538 return 0;
2539 }
2540
2541 struct target_seminfo {
2542 int semmap;
2543 int semmni;
2544 int semmns;
2545 int semmnu;
2546 int semmsl;
2547 int semopm;
2548 int semume;
2549 int semusz;
2550 int semvmx;
2551 int semaem;
2552 };
2553
2554 static inline abi_long host_to_target_seminfo(abi_ulong target_addr,
2555 struct seminfo *host_seminfo)
2556 {
2557 struct target_seminfo *target_seminfo;
2558 if (!lock_user_struct(VERIFY_WRITE, target_seminfo, target_addr, 0))
2559 return -TARGET_EFAULT;
2560 __put_user(host_seminfo->semmap, &target_seminfo->semmap);
2561 __put_user(host_seminfo->semmni, &target_seminfo->semmni);
2562 __put_user(host_seminfo->semmns, &target_seminfo->semmns);
2563 __put_user(host_seminfo->semmnu, &target_seminfo->semmnu);
2564 __put_user(host_seminfo->semmsl, &target_seminfo->semmsl);
2565 __put_user(host_seminfo->semopm, &target_seminfo->semopm);
2566 __put_user(host_seminfo->semume, &target_seminfo->semume);
2567 __put_user(host_seminfo->semusz, &target_seminfo->semusz);
2568 __put_user(host_seminfo->semvmx, &target_seminfo->semvmx);
2569 __put_user(host_seminfo->semaem, &target_seminfo->semaem);
2570 unlock_user_struct(target_seminfo, target_addr, 1);
2571 return 0;
2572 }
2573
2574 union semun {
2575 int val;
2576 struct semid_ds *buf;
2577 unsigned short *array;
2578 struct seminfo *__buf;
2579 };
2580
2581 union target_semun {
2582 int val;
2583 abi_ulong buf;
2584 abi_ulong array;
2585 abi_ulong __buf;
2586 };
2587
2588 static inline abi_long target_to_host_semarray(int semid, unsigned short **host_array,
2589 abi_ulong target_addr)
2590 {
2591 int nsems;
2592 unsigned short *array;
2593 union semun semun;
2594 struct semid_ds semid_ds;
2595 int i, ret;
2596
2597 semun.buf = &semid_ds;
2598
2599 ret = semctl(semid, 0, IPC_STAT, semun);
2600 if (ret == -1)
2601 return get_errno(ret);
2602
2603 nsems = semid_ds.sem_nsems;
2604
2605 *host_array = malloc(nsems*sizeof(unsigned short));
2606 if (!*host_array) {
2607 return -TARGET_ENOMEM;
2608 }
2609 array = lock_user(VERIFY_READ, target_addr,
2610 nsems*sizeof(unsigned short), 1);
2611 if (!array) {
2612 free(*host_array);
2613 return -TARGET_EFAULT;
2614 }
2615
2616 for(i=0; i<nsems; i++) {
2617 __get_user((*host_array)[i], &array[i]);
2618 }
2619 unlock_user(array, target_addr, 0);
2620
2621 return 0;
2622 }
2623
2624 static inline abi_long host_to_target_semarray(int semid, abi_ulong target_addr,
2625 unsigned short **host_array)
2626 {
2627 int nsems;
2628 unsigned short *array;
2629 union semun semun;
2630 struct semid_ds semid_ds;
2631 int i, ret;
2632
2633 semun.buf = &semid_ds;
2634
2635 ret = semctl(semid, 0, IPC_STAT, semun);
2636 if (ret == -1)
2637 return get_errno(ret);
2638
2639 nsems = semid_ds.sem_nsems;
2640
2641 array = lock_user(VERIFY_WRITE, target_addr,
2642 nsems*sizeof(unsigned short), 0);
2643 if (!array)
2644 return -TARGET_EFAULT;
2645
2646 for(i=0; i<nsems; i++) {
2647 __put_user((*host_array)[i], &array[i]);
2648 }
2649 free(*host_array);
2650 unlock_user(array, target_addr, 1);
2651
2652 return 0;
2653 }
2654
2655 static inline abi_long do_semctl(int semid, int semnum, int cmd,
2656 union target_semun target_su)
2657 {
2658 union semun arg;
2659 struct semid_ds dsarg;
2660 unsigned short *array = NULL;
2661 struct seminfo seminfo;
2662 abi_long ret = -TARGET_EINVAL;
2663 abi_long err;
2664 cmd &= 0xff;
2665
2666 switch( cmd ) {
2667 case GETVAL:
2668 case SETVAL:
2669 /* In 64 bit cross-endian situations, we will erroneously pick up
2670 * the wrong half of the union for the "val" element. To rectify
2671 * this, the entire 8-byte structure is byteswapped, followed by
2672 * a swap of the 4 byte val field. In other cases, the data is
2673 * already in proper host byte order. */
2674 if (sizeof(target_su.val) != (sizeof(target_su.buf))) {
2675 target_su.buf = tswapal(target_su.buf);
2676 arg.val = tswap32(target_su.val);
2677 } else {
2678 arg.val = target_su.val;
2679 }
2680 ret = get_errno(semctl(semid, semnum, cmd, arg));
2681 break;
2682 case GETALL:
2683 case SETALL:
2684 err = target_to_host_semarray(semid, &array, target_su.array);
2685 if (err)
2686 return err;
2687 arg.array = array;
2688 ret = get_errno(semctl(semid, semnum, cmd, arg));
2689 err = host_to_target_semarray(semid, target_su.array, &array);
2690 if (err)
2691 return err;
2692 break;
2693 case IPC_STAT:
2694 case IPC_SET:
2695 case SEM_STAT:
2696 err = target_to_host_semid_ds(&dsarg, target_su.buf);
2697 if (err)
2698 return err;
2699 arg.buf = &dsarg;
2700 ret = get_errno(semctl(semid, semnum, cmd, arg));
2701 err = host_to_target_semid_ds(target_su.buf, &dsarg);
2702 if (err)
2703 return err;
2704 break;
2705 case IPC_INFO:
2706 case SEM_INFO:
2707 arg.__buf = &seminfo;
2708 ret = get_errno(semctl(semid, semnum, cmd, arg));
2709 err = host_to_target_seminfo(target_su.__buf, &seminfo);
2710 if (err)
2711 return err;
2712 break;
2713 case IPC_RMID:
2714 case GETPID:
2715 case GETNCNT:
2716 case GETZCNT:
2717 ret = get_errno(semctl(semid, semnum, cmd, NULL));
2718 break;
2719 }
2720
2721 return ret;
2722 }
2723
2724 struct target_sembuf {
2725 unsigned short sem_num;
2726 short sem_op;
2727 short sem_flg;
2728 };
2729
2730 static inline abi_long target_to_host_sembuf(struct sembuf *host_sembuf,
2731 abi_ulong target_addr,
2732 unsigned nsops)
2733 {
2734 struct target_sembuf *target_sembuf;
2735 int i;
2736
2737 target_sembuf = lock_user(VERIFY_READ, target_addr,
2738 nsops*sizeof(struct target_sembuf), 1);
2739 if (!target_sembuf)
2740 return -TARGET_EFAULT;
2741
2742 for(i=0; i<nsops; i++) {
2743 __get_user(host_sembuf[i].sem_num, &target_sembuf[i].sem_num);
2744 __get_user(host_sembuf[i].sem_op, &target_sembuf[i].sem_op);
2745 __get_user(host_sembuf[i].sem_flg, &target_sembuf[i].sem_flg);
2746 }
2747
2748 unlock_user(target_sembuf, target_addr, 0);
2749
2750 return 0;
2751 }
2752
2753 static inline abi_long do_semop(int semid, abi_long ptr, unsigned nsops)
2754 {
2755 struct sembuf sops[nsops];
2756
2757 if (target_to_host_sembuf(sops, ptr, nsops))
2758 return -TARGET_EFAULT;
2759
2760 return get_errno(semop(semid, sops, nsops));
2761 }
2762
2763 struct target_msqid_ds
2764 {
2765 struct target_ipc_perm msg_perm;
2766 abi_ulong msg_stime;
2767 #if TARGET_ABI_BITS == 32
2768 abi_ulong __unused1;
2769 #endif
2770 abi_ulong msg_rtime;
2771 #if TARGET_ABI_BITS == 32
2772 abi_ulong __unused2;
2773 #endif
2774 abi_ulong msg_ctime;
2775 #if TARGET_ABI_BITS == 32
2776 abi_ulong __unused3;
2777 #endif
2778 abi_ulong __msg_cbytes;
2779 abi_ulong msg_qnum;
2780 abi_ulong msg_qbytes;
2781 abi_ulong msg_lspid;
2782 abi_ulong msg_lrpid;
2783 abi_ulong __unused4;
2784 abi_ulong __unused5;
2785 };
2786
2787 static inline abi_long target_to_host_msqid_ds(struct msqid_ds *host_md,
2788 abi_ulong target_addr)
2789 {
2790 struct target_msqid_ds *target_md;
2791
2792 if (!lock_user_struct(VERIFY_READ, target_md, target_addr, 1))
2793 return -TARGET_EFAULT;
2794 if (target_to_host_ipc_perm(&(host_md->msg_perm),target_addr))
2795 return -TARGET_EFAULT;
2796 host_md->msg_stime = tswapal(target_md->msg_stime);
2797 host_md->msg_rtime = tswapal(target_md->msg_rtime);
2798 host_md->msg_ctime = tswapal(target_md->msg_ctime);
2799 host_md->__msg_cbytes = tswapal(target_md->__msg_cbytes);
2800 host_md->msg_qnum = tswapal(target_md->msg_qnum);
2801 host_md->msg_qbytes = tswapal(target_md->msg_qbytes);
2802 host_md->msg_lspid = tswapal(target_md->msg_lspid);
2803 host_md->msg_lrpid = tswapal(target_md->msg_lrpid);
2804 unlock_user_struct(target_md, target_addr, 0);
2805 return 0;
2806 }
2807
2808 static inline abi_long host_to_target_msqid_ds(abi_ulong target_addr,
2809 struct msqid_ds *host_md)
2810 {
2811 struct target_msqid_ds *target_md;
2812
2813 if (!lock_user_struct(VERIFY_WRITE, target_md, target_addr, 0))
2814 return -TARGET_EFAULT;
2815 if (host_to_target_ipc_perm(target_addr,&(host_md->msg_perm)))
2816 return -TARGET_EFAULT;
2817 target_md->msg_stime = tswapal(host_md->msg_stime);
2818 target_md->msg_rtime = tswapal(host_md->msg_rtime);
2819 target_md->msg_ctime = tswapal(host_md->msg_ctime);
2820 target_md->__msg_cbytes = tswapal(host_md->__msg_cbytes);
2821 target_md->msg_qnum = tswapal(host_md->msg_qnum);
2822 target_md->msg_qbytes = tswapal(host_md->msg_qbytes);
2823 target_md->msg_lspid = tswapal(host_md->msg_lspid);
2824 target_md->msg_lrpid = tswapal(host_md->msg_lrpid);
2825 unlock_user_struct(target_md, target_addr, 1);
2826 return 0;
2827 }
2828
2829 struct target_msginfo {
2830 int msgpool;
2831 int msgmap;
2832 int msgmax;
2833 int msgmnb;
2834 int msgmni;
2835 int msgssz;
2836 int msgtql;
2837 unsigned short int msgseg;
2838 };
2839
2840 static inline abi_long host_to_target_msginfo(abi_ulong target_addr,
2841 struct msginfo *host_msginfo)
2842 {
2843 struct target_msginfo *target_msginfo;
2844 if (!lock_user_struct(VERIFY_WRITE, target_msginfo, target_addr, 0))
2845 return -TARGET_EFAULT;
2846 __put_user(host_msginfo->msgpool, &target_msginfo->msgpool);
2847 __put_user(host_msginfo->msgmap, &target_msginfo->msgmap);
2848 __put_user(host_msginfo->msgmax, &target_msginfo->msgmax);
2849 __put_user(host_msginfo->msgmnb, &target_msginfo->msgmnb);
2850 __put_user(host_msginfo->msgmni, &target_msginfo->msgmni);
2851 __put_user(host_msginfo->msgssz, &target_msginfo->msgssz);
2852 __put_user(host_msginfo->msgtql, &target_msginfo->msgtql);
2853 __put_user(host_msginfo->msgseg, &target_msginfo->msgseg);
2854 unlock_user_struct(target_msginfo, target_addr, 1);
2855 return 0;
2856 }
2857
2858 static inline abi_long do_msgctl(int msgid, int cmd, abi_long ptr)
2859 {
2860 struct msqid_ds dsarg;
2861 struct msginfo msginfo;
2862 abi_long ret = -TARGET_EINVAL;
2863
2864 cmd &= 0xff;
2865
2866 switch (cmd) {
2867 case IPC_STAT:
2868 case IPC_SET:
2869 case MSG_STAT:
2870 if (target_to_host_msqid_ds(&dsarg,ptr))
2871 return -TARGET_EFAULT;
2872 ret = get_errno(msgctl(msgid, cmd, &dsarg));
2873 if (host_to_target_msqid_ds(ptr,&dsarg))
2874 return -TARGET_EFAULT;
2875 break;
2876 case IPC_RMID:
2877 ret = get_errno(msgctl(msgid, cmd, NULL));
2878 break;
2879 case IPC_INFO:
2880 case MSG_INFO:
2881 ret = get_errno(msgctl(msgid, cmd, (struct msqid_ds *)&msginfo));
2882 if (host_to_target_msginfo(ptr, &msginfo))
2883 return -TARGET_EFAULT;
2884 break;
2885 }
2886
2887 return ret;
2888 }
2889
2890 struct target_msgbuf {
2891 abi_long mtype;
2892 char mtext[1];
2893 };
2894
2895 static inline abi_long do_msgsnd(int msqid, abi_long msgp,
2896 ssize_t msgsz, int msgflg)
2897 {
2898 struct target_msgbuf *target_mb;
2899 struct msgbuf *host_mb;
2900 abi_long ret = 0;
2901
2902 if (msgsz < 0) {
2903 return -TARGET_EINVAL;
2904 }
2905
2906 if (!lock_user_struct(VERIFY_READ, target_mb, msgp, 0))
2907 return -TARGET_EFAULT;
2908 host_mb = malloc(msgsz+sizeof(long));
2909 if (!host_mb) {
2910 unlock_user_struct(target_mb, msgp, 0);
2911 return -TARGET_ENOMEM;
2912 }
2913 host_mb->mtype = (abi_long) tswapal(target_mb->mtype);
2914 memcpy(host_mb->mtext, target_mb->mtext, msgsz);
2915 ret = get_errno(msgsnd(msqid, host_mb, msgsz, msgflg));
2916 free(host_mb);
2917 unlock_user_struct(target_mb, msgp, 0);
2918
2919 return ret;
2920 }
2921
2922 static inline abi_long do_msgrcv(int msqid, abi_long msgp,
2923 unsigned int msgsz, abi_long msgtyp,
2924 int msgflg)
2925 {
2926 struct target_msgbuf *target_mb;
2927 char *target_mtext;
2928 struct msgbuf *host_mb;
2929 abi_long ret = 0;
2930
2931 if (!lock_user_struct(VERIFY_WRITE, target_mb, msgp, 0))
2932 return -TARGET_EFAULT;
2933
2934 host_mb = g_malloc(msgsz+sizeof(long));
2935 ret = get_errno(msgrcv(msqid, host_mb, msgsz, msgtyp, msgflg));
2936
2937 if (ret > 0) {
2938 abi_ulong target_mtext_addr = msgp + sizeof(abi_ulong);
2939 target_mtext = lock_user(VERIFY_WRITE, target_mtext_addr, ret, 0);
2940 if (!target_mtext) {
2941 ret = -TARGET_EFAULT;
2942 goto end;
2943 }
2944 memcpy(target_mb->mtext, host_mb->mtext, ret);
2945 unlock_user(target_mtext, target_mtext_addr, ret);
2946 }
2947
2948 target_mb->mtype = tswapal(host_mb->mtype);
2949
2950 end:
2951 if (target_mb)
2952 unlock_user_struct(target_mb, msgp, 1);
2953 g_free(host_mb);
2954 return ret;
2955 }
2956
2957 static inline abi_long target_to_host_shmid_ds(struct shmid_ds *host_sd,
2958 abi_ulong target_addr)
2959 {
2960 struct target_shmid_ds *target_sd;
2961
2962 if (!lock_user_struct(VERIFY_READ, target_sd, target_addr, 1))
2963 return -TARGET_EFAULT;
2964 if (target_to_host_ipc_perm(&(host_sd->shm_perm), target_addr))
2965 return -TARGET_EFAULT;
2966 __get_user(host_sd->shm_segsz, &target_sd->shm_segsz);
2967 __get_user(host_sd->shm_atime, &target_sd->shm_atime);
2968 __get_user(host_sd->shm_dtime, &target_sd->shm_dtime);
2969 __get_user(host_sd->shm_ctime, &target_sd->shm_ctime);
2970 __get_user(host_sd->shm_cpid, &target_sd->shm_cpid);
2971 __get_user(host_sd->shm_lpid, &target_sd->shm_lpid);
2972 __get_user(host_sd->shm_nattch, &target_sd->shm_nattch);
2973 unlock_user_struct(target_sd, target_addr, 0);
2974 return 0;
2975 }
2976
2977 static inline abi_long host_to_target_shmid_ds(abi_ulong target_addr,
2978 struct shmid_ds *host_sd)
2979 {
2980 struct target_shmid_ds *target_sd;
2981
2982 if (!lock_user_struct(VERIFY_WRITE, target_sd, target_addr, 0))
2983 return -TARGET_EFAULT;
2984 if (host_to_target_ipc_perm(target_addr, &(host_sd->shm_perm)))
2985 return -TARGET_EFAULT;
2986 __put_user(host_sd->shm_segsz, &target_sd->shm_segsz);
2987 __put_user(host_sd->shm_atime, &target_sd->shm_atime);
2988 __put_user(host_sd->shm_dtime, &target_sd->shm_dtime);
2989 __put_user(host_sd->shm_ctime, &target_sd->shm_ctime);
2990 __put_user(host_sd->shm_cpid, &target_sd->shm_cpid);
2991 __put_user(host_sd->shm_lpid, &target_sd->shm_lpid);
2992 __put_user(host_sd->shm_nattch, &target_sd->shm_nattch);
2993 unlock_user_struct(target_sd, target_addr, 1);
2994 return 0;
2995 }
2996
2997 struct target_shminfo {
2998 abi_ulong shmmax;
2999 abi_ulong shmmin;
3000 abi_ulong shmmni;
3001 abi_ulong shmseg;
3002 abi_ulong shmall;
3003 };
3004
3005 static inline abi_long host_to_target_shminfo(abi_ulong target_addr,
3006 struct shminfo *host_shminfo)
3007 {
3008 struct target_shminfo *target_shminfo;
3009 if (!lock_user_struct(VERIFY_WRITE, target_shminfo, target_addr, 0))
3010 return -TARGET_EFAULT;
3011 __put_user(host_shminfo->shmmax, &target_shminfo->shmmax);
3012 __put_user(host_shminfo->shmmin, &target_shminfo->shmmin);
3013 __put_user(host_shminfo->shmmni, &target_shminfo->shmmni);
3014 __put_user(host_shminfo->shmseg, &target_shminfo->shmseg);
3015 __put_user(host_shminfo->shmall, &target_shminfo->shmall);
3016 unlock_user_struct(target_shminfo, target_addr, 1);
3017 return 0;
3018 }
3019
3020 struct target_shm_info {
3021 int used_ids;
3022 abi_ulong shm_tot;
3023 abi_ulong shm_rss;
3024 abi_ulong shm_swp;
3025 abi_ulong swap_attempts;
3026 abi_ulong swap_successes;
3027 };
3028
3029 static inline abi_long host_to_target_shm_info(abi_ulong target_addr,
3030 struct shm_info *host_shm_info)
3031 {
3032 struct target_shm_info *target_shm_info;
3033 if (!lock_user_struct(VERIFY_WRITE, target_shm_info, target_addr, 0))
3034 return -TARGET_EFAULT;
3035 __put_user(host_shm_info->used_ids, &target_shm_info->used_ids);
3036 __put_user(host_shm_info->shm_tot, &target_shm_info->shm_tot);
3037 __put_user(host_shm_info->shm_rss, &target_shm_info->shm_rss);
3038 __put_user(host_shm_info->shm_swp, &target_shm_info->shm_swp);
3039 __put_user(host_shm_info->swap_attempts, &target_shm_info->swap_attempts);
3040 __put_user(host_shm_info->swap_successes, &target_shm_info->swap_successes);
3041 unlock_user_struct(target_shm_info, target_addr, 1);
3042 return 0;
3043 }
3044
3045 static inline abi_long do_shmctl(int shmid, int cmd, abi_long buf)
3046 {
3047 struct shmid_ds dsarg;
3048 struct shminfo shminfo;
3049 struct shm_info shm_info;
3050 abi_long ret = -TARGET_EINVAL;
3051
3052 cmd &= 0xff;
3053
3054 switch(cmd) {
3055 case IPC_STAT:
3056 case IPC_SET:
3057 case SHM_STAT:
3058 if (target_to_host_shmid_ds(&dsarg, buf))
3059 return -TARGET_EFAULT;
3060 ret = get_errno(shmctl(shmid, cmd, &dsarg));
3061 if (host_to_target_shmid_ds(buf, &dsarg))
3062 return -TARGET_EFAULT;
3063 break;
3064 case IPC_INFO:
3065 ret = get_errno(shmctl(shmid, cmd, (struct shmid_ds *)&shminfo));
3066 if (host_to_target_shminfo(buf, &shminfo))
3067 return -TARGET_EFAULT;
3068 break;
3069 case SHM_INFO:
3070 ret = get_errno(shmctl(shmid, cmd, (struct shmid_ds *)&shm_info));
3071 if (host_to_target_shm_info(buf, &shm_info))
3072 return -TARGET_EFAULT;
3073 break;
3074 case IPC_RMID:
3075 case SHM_LOCK:
3076 case SHM_UNLOCK:
3077 ret = get_errno(shmctl(shmid, cmd, NULL));
3078 break;
3079 }
3080
3081 return ret;
3082 }
3083
3084 static inline abi_ulong do_shmat(int shmid, abi_ulong shmaddr, int shmflg)
3085 {
3086 abi_long raddr;
3087 void *host_raddr;
3088 struct shmid_ds shm_info;
3089 int i,ret;
3090
3091 /* find out the length of the shared memory segment */
3092 ret = get_errno(shmctl(shmid, IPC_STAT, &shm_info));
3093 if (is_error(ret)) {
3094 /* can't get length, bail out */
3095 return ret;
3096 }
3097
3098 mmap_lock();
3099
3100 if (shmaddr)
3101 host_raddr = shmat(shmid, (void *)g2h(shmaddr), shmflg);
3102 else {
3103 abi_ulong mmap_start;
3104
3105 mmap_start = mmap_find_vma(0, shm_info.shm_segsz);
3106
3107 if (mmap_start == -1) {
3108 errno = ENOMEM;
3109 host_raddr = (void *)-1;
3110 } else
3111 host_raddr = shmat(shmid, g2h(mmap_start), shmflg | SHM_REMAP);
3112 }
3113
3114 if (host_raddr == (void *)-1) {
3115 mmap_unlock();
3116 return get_errno((long)host_raddr);
3117 }
3118 raddr=h2g((unsigned long)host_raddr);
3119
3120 page_set_flags(raddr, raddr + shm_info.shm_segsz,
3121 PAGE_VALID | PAGE_READ |
3122 ((shmflg & SHM_RDONLY)? 0 : PAGE_WRITE));
3123
3124 for (i = 0; i < N_SHM_REGIONS; i++) {
3125 if (shm_regions[i].start == 0) {
3126 shm_regions[i].start = raddr;
3127 shm_regions[i].size = shm_info.shm_segsz;
3128 break;
3129 }
3130 }
3131
3132 mmap_unlock();
3133 return raddr;
3134
3135 }
3136
3137 static inline abi_long do_shmdt(abi_ulong shmaddr)
3138 {
3139 int i;
3140
3141 for (i = 0; i < N_SHM_REGIONS; ++i) {
3142 if (shm_regions[i].start == shmaddr) {
3143 shm_regions[i].start = 0;
3144 page_set_flags(shmaddr, shmaddr + shm_regions[i].size, 0);
3145 break;
3146 }
3147 }
3148
3149 return get_errno(shmdt(g2h(shmaddr)));
3150 }
3151
3152 #ifdef TARGET_NR_ipc
3153 /* ??? This only works with linear mappings. */
3154 /* do_ipc() must return target values and target errnos. */
3155 static abi_long do_ipc(unsigned int call, abi_long first,
3156 abi_long second, abi_long third,
3157 abi_long ptr, abi_long fifth)
3158 {
3159 int version;
3160 abi_long ret = 0;
3161
3162 version = call >> 16;
3163 call &= 0xffff;
3164
3165 switch (call) {
3166 case IPCOP_semop:
3167 ret = do_semop(first, ptr, second);
3168 break;
3169
3170 case IPCOP_semget:
3171 ret = get_errno(semget(first, second, third));
3172 break;
3173
3174 case IPCOP_semctl: {
3175 /* The semun argument to semctl is passed by value, so dereference the
3176 * ptr argument. */
3177 abi_ulong atptr;
3178 get_user_ual(atptr, ptr);
3179 ret = do_semctl(first, second, third,
3180 (union target_semun) atptr);
3181 break;
3182 }
3183
3184 case IPCOP_msgget:
3185 ret = get_errno(msgget(first, second));
3186 break;
3187
3188 case IPCOP_msgsnd:
3189 ret = do_msgsnd(first, ptr, second, third);
3190 break;
3191
3192 case IPCOP_msgctl:
3193 ret = do_msgctl(first, second, ptr);
3194 break;
3195
3196 case IPCOP_msgrcv:
3197 switch (version) {
3198 case 0:
3199 {
3200 struct target_ipc_kludge {
3201 abi_long msgp;
3202 abi_long msgtyp;
3203 } *tmp;
3204
3205 if (!lock_user_struct(VERIFY_READ, tmp, ptr, 1)) {
3206 ret = -TARGET_EFAULT;
3207 break;
3208 }
3209
3210 ret = do_msgrcv(first, tswapal(tmp->msgp), second, tswapal(tmp->msgtyp), third);
3211
3212 unlock_user_struct(tmp, ptr, 0);
3213 break;
3214 }
3215 default:
3216 ret = do_msgrcv(first, ptr, second, fifth, third);
3217 }
3218 break;
3219
3220 case IPCOP_shmat:
3221 switch (version) {
3222 default:
3223 {
3224 abi_ulong raddr;
3225 raddr = do_shmat(first, ptr, second);
3226 if (is_error(raddr))
3227 return get_errno(raddr);
3228 if (put_user_ual(raddr, third))
3229 return -TARGET_EFAULT;
3230 break;
3231 }
3232 case 1:
3233 ret = -TARGET_EINVAL;
3234 break;
3235 }
3236 break;
3237 case IPCOP_shmdt:
3238 ret = do_shmdt(ptr);
3239 break;
3240
3241 case IPCOP_shmget:
3242 /* IPC_* flag values are the same on all linux platforms */
3243 ret = get_errno(shmget(first, second, third));
3244 break;
3245
3246 /* IPC_* and SHM_* command values are the same on all linux platforms */
3247 case IPCOP_shmctl:
3248 ret = do_shmctl(first, second, ptr);
3249 break;
3250 default:
3251 gemu_log("Unsupported ipc call: %d (version %d)\n", call, version);
3252 ret = -TARGET_ENOSYS;
3253 break;
3254 }
3255 return ret;
3256 }
3257 #endif
3258
3259 /* kernel structure types definitions */
3260
3261 #define STRUCT(name, ...) STRUCT_ ## name,
3262 #define STRUCT_SPECIAL(name) STRUCT_ ## name,
3263 enum {
3264 #include "syscall_types.h"
3265 };
3266 #undef STRUCT
3267 #undef STRUCT_SPECIAL
3268
3269 #define STRUCT(name, ...) static const argtype struct_ ## name ## _def[] = { __VA_ARGS__, TYPE_NULL };
3270 #define STRUCT_SPECIAL(name)
3271 #include "syscall_types.h"
3272 #undef STRUCT
3273 #undef STRUCT_SPECIAL
3274
3275 typedef struct IOCTLEntry IOCTLEntry;
3276
3277 typedef abi_long do_ioctl_fn(const IOCTLEntry *ie, uint8_t *buf_temp,
3278 int fd, abi_long cmd, abi_long arg);
3279
3280 struct IOCTLEntry {
3281 unsigned int target_cmd;
3282 unsigned int host_cmd;
3283 const char *name;
3284 int access;
3285 do_ioctl_fn *do_ioctl;
3286 const argtype arg_type[5];
3287 };
3288
3289 #define IOC_R 0x0001
3290 #define IOC_W 0x0002
3291 #define IOC_RW (IOC_R | IOC_W)
3292
3293 #define MAX_STRUCT_SIZE 4096
3294
3295 #ifdef CONFIG_FIEMAP
3296 /* So fiemap access checks don't overflow on 32 bit systems.
3297 * This is very slightly smaller than the limit imposed by
3298 * the underlying kernel.
3299 */
3300 #define FIEMAP_MAX_EXTENTS ((UINT_MAX - sizeof(struct fiemap)) \