1 /* $NetBSD: netbsd32_netbsd.c,v 1.19 1999/10/11 01:36:23 eeh Exp $ */ 2 3 /* 4 * Copyright (c) 1998 Matthew R. Green 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. The name of the author may not be used to endorse or promote products 16 * derived from this software without specific prior written permission. 17 * 18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 19 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 20 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 21 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 23 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 24 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 25 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 26 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 * SUCH DAMAGE. 29 */ 30 31 #include "opt_ktrace.h" 32 #include "opt_ntp.h" 33 #include "opt_compat_freebsd.h" 34 #include "opt_compat_linux.h" 35 #include "opt_compat_sunos.h" 36 #include "opt_compat_43.h" 37 #if defined(COMPAT_43) || defined(COMPAT_SUNOS) || defined(COMPAT_LINUX) || \ 38 defined(COMPAT_FREEBSD) 39 #define COMPAT_OLDSOCK /* used by <sys/socket.h> */ 40 #endif 41 42 #include "fs_lfs.h" 43 #include "fs_nfs.h" 44 45 #include <sys/param.h> 46 #include <sys/systm.h> 47 #include <sys/kernel.h> 48 #include <sys/ipc.h> 49 #include <sys/msg.h> 50 #define msg __msg /* Don't ask me! */ 51 #include <sys/sem.h> 52 #include <sys/shm.h> 53 #include <sys/malloc.h> 54 #include <sys/mount.h> 55 #include <sys/socket.h> 56 #include <sys/sockio.h> 57 #include <sys/socketvar.h> 58 #include <sys/mbuf.h> 59 #include <sys/stat.h> 60 #include <sys/time.h> 61 #include <sys/timex.h> 62 #include <sys/signalvar.h> 63 #include <sys/wait.h> 64 #include <sys/ptrace.h> 65 #include <sys/ktrace.h> 66 #include <sys/trace.h> 67 #include <sys/resourcevar.h> 68 #include <sys/pool.h> 69 #include <sys/vnode.h> 70 #include <sys/file.h> 71 #include <sys/filedesc.h> 72 #include <sys/namei.h> 73 74 #include <vm/vm.h> 75 #include <sys/syscallargs.h> 76 #include <sys/proc.h> 77 #include <sys/sysctl.h> 78 79 #include <net/if.h> 80 81 #include <compat/netbsd32/netbsd32.h> 82 #include <compat/netbsd32/netbsd32_syscallargs.h> 83 84 #include <machine/frame.h> 85 86 static __inline void netbsd32_from_timeval __P((struct timeval *, struct netbsd32_timeval *)); 87 static __inline void netbsd32_to_timeval __P((struct netbsd32_timeval *, struct timeval *)); 88 static __inline void netbsd32_from_itimerval __P((struct itimerval *, struct netbsd32_itimerval *)); 89 static __inline void netbsd32_to_itimerval __P((struct netbsd32_itimerval *, struct itimerval *)); 90 static __inline void netbsd32_to_timespec __P((struct netbsd32_timespec *, struct timespec *)); 91 static __inline void netbsd32_from_timespec __P((struct timespec *, struct netbsd32_timespec *)); 92 static __inline void netbsd32_from_rusage __P((struct rusage *, struct netbsd32_rusage *)); 93 static __inline void netbsd32_to_rusage __P((struct netbsd32_rusage *, struct rusage *)); 94 static __inline int netbsd32_to_iovecin __P((struct netbsd32_iovec *, struct iovec *, int)); 95 static __inline void netbsd32_to_msghdr __P((struct netbsd32_msghdr *, struct msghdr *)); 96 static __inline void netbsd32_from_msghdr __P((struct netbsd32_msghdr *, struct msghdr *)); 97 static __inline void netbsd32_from_statfs __P((struct statfs *, struct netbsd32_statfs *)); 98 static __inline void netbsd32_from_timex __P((struct timex *, struct netbsd32_timex *)); 99 static __inline void netbsd32_to_timex __P((struct netbsd32_timex *, struct timex *)); 100 static __inline void netbsd32_from___stat13 __P((struct stat *, struct netbsd32_stat *)); 101 static __inline void netbsd32_to_ipc_perm __P((struct netbsd32_ipc_perm *, struct ipc_perm *)); 102 static __inline void netbsd32_from_ipc_perm __P((struct ipc_perm *, struct netbsd32_ipc_perm *)); 103 static __inline void netbsd32_to_msg __P((struct netbsd32_msg *, struct msg *)); 104 static __inline void netbsd32_from_msg __P((struct msg *, struct netbsd32_msg *)); 105 static __inline void netbsd32_to_msqid_ds __P((struct netbsd32_msqid_ds *, struct msqid_ds *)); 106 static __inline void netbsd32_from_msqid_ds __P((struct msqid_ds *, struct netbsd32_msqid_ds *)); 107 static __inline void netbsd32_to_shmid_ds __P((struct netbsd32_shmid_ds *, struct shmid_ds *)); 108 static __inline void netbsd32_from_shmid_ds __P((struct shmid_ds *, struct netbsd32_shmid_ds *)); 109 static __inline void netbsd32_to_semid_ds __P((struct netbsd32_semid_ds *, struct semid_ds *)); 110 static __inline void netbsd32_from_semid_ds __P((struct semid_ds *, struct netbsd32_semid_ds *)); 111 112 113 static int recvit32 __P((struct proc *, int, struct netbsd32_msghdr *, struct iovec *, caddr_t, 114 register_t *)); 115 static int dofilereadv32 __P((struct proc *, int, struct file *, struct netbsd32_iovec *, 116 int, off_t *, int, register_t *)); 117 static int dofilewritev32 __P((struct proc *, int, struct file *, struct netbsd32_iovec *, 118 int, off_t *, int, register_t *)); 119 static int change_utimes32 __P((struct vnode *, struct timeval *, struct proc *)); 120 121 /* converters for structures that we need */ 122 static __inline void 123 netbsd32_from_timeval(tv, tv32) 124 struct timeval *tv; 125 struct netbsd32_timeval *tv32; 126 { 127 128 tv32->tv_sec = (netbsd32_long)tv->tv_sec; 129 tv32->tv_usec = (netbsd32_long)tv->tv_usec; 130 } 131 132 static __inline void 133 netbsd32_to_timeval(tv32, tv) 134 struct netbsd32_timeval *tv32; 135 struct timeval *tv; 136 { 137 138 tv->tv_sec = (long)tv32->tv_sec; 139 tv->tv_usec = (long)tv32->tv_usec; 140 } 141 142 static __inline void 143 netbsd32_from_itimerval(itv, itv32) 144 struct itimerval *itv; 145 struct netbsd32_itimerval *itv32; 146 { 147 148 netbsd32_from_timeval(&itv->it_interval, 149 &itv32->it_interval); 150 netbsd32_from_timeval(&itv->it_value, 151 &itv32->it_value); 152 } 153 154 static __inline void 155 netbsd32_to_itimerval(itv32, itv) 156 struct netbsd32_itimerval *itv32; 157 struct itimerval *itv; 158 { 159 160 netbsd32_to_timeval(&itv32->it_interval, &itv->it_interval); 161 netbsd32_to_timeval(&itv32->it_value, &itv->it_value); 162 } 163 164 static __inline void 165 netbsd32_to_timespec(s32p, p) 166 struct netbsd32_timespec *s32p; 167 struct timespec *p; 168 { 169 170 p->tv_sec = s32p->tv_sec; 171 p->tv_nsec = (long)s32p->tv_nsec; 172 } 173 174 static __inline void 175 netbsd32_from_timespec(p, s32p) 176 struct timespec *p; 177 struct netbsd32_timespec *s32p; 178 { 179 180 s32p->tv_sec = p->tv_sec; 181 s32p->tv_nsec = (netbsd32_long)p->tv_nsec; 182 } 183 184 static __inline void 185 netbsd32_from_rusage(rup, ru32p) 186 struct rusage *rup; 187 struct netbsd32_rusage *ru32p; 188 { 189 190 netbsd32_from_timeval(&rup->ru_utime, &ru32p->ru_utime); 191 netbsd32_from_timeval(&rup->ru_stime, &ru32p->ru_stime); 192 #define C(var) ru32p->var = (netbsd32_long)rup->var 193 C(ru_maxrss); 194 C(ru_ixrss); 195 C(ru_idrss); 196 C(ru_isrss); 197 C(ru_minflt); 198 C(ru_majflt); 199 C(ru_nswap); 200 C(ru_inblock); 201 C(ru_oublock); 202 C(ru_msgsnd); 203 C(ru_msgrcv); 204 C(ru_nsignals); 205 C(ru_nvcsw); 206 C(ru_nivcsw); 207 #undef C 208 } 209 210 static __inline void 211 netbsd32_to_rusage(ru32p, rup) 212 struct netbsd32_rusage *ru32p; 213 struct rusage *rup; 214 { 215 216 netbsd32_to_timeval(&ru32p->ru_utime, &rup->ru_utime); 217 netbsd32_to_timeval(&ru32p->ru_stime, &rup->ru_stime); 218 #define C(var) rup->var = (long)ru32p->var 219 C(ru_maxrss); 220 C(ru_ixrss); 221 C(ru_idrss); 222 C(ru_isrss); 223 C(ru_minflt); 224 C(ru_majflt); 225 C(ru_nswap); 226 C(ru_inblock); 227 C(ru_oublock); 228 C(ru_msgsnd); 229 C(ru_msgrcv); 230 C(ru_nsignals); 231 C(ru_nvcsw); 232 C(ru_nivcsw); 233 #undef C 234 } 235 236 static __inline int 237 netbsd32_to_iovecin(iov32p, iovp, len) 238 struct netbsd32_iovec *iov32p; 239 struct iovec *iovp; 240 int len; 241 { 242 int i, error=0; 243 u_int32_t iov_base; 244 u_int32_t iov_len; 245 /* 246 * We could allocate an iov32p, do a copyin, and translate 247 * each field and then free it all up, or we could copyin 248 * each field separately. I'm doing the latter to reduce 249 * the number of MALLOC()s. 250 */ 251 printf("converting iovec at %p len %lx to %p\n", iov32p, len, iovp); 252 for (i = 0; i < len; i++, iovp++, iov32p++) { 253 if ((error = copyin((caddr_t)&iov32p->iov_base, &iov_base, sizeof(iov_base)))) 254 return (error); 255 if ((error = copyin((caddr_t)&iov32p->iov_len, &iov_len, sizeof(iov_len)))) 256 return (error); 257 iovp->iov_base = (void *)(u_long)iov_base; 258 iovp->iov_len = (size_t)iov_len; 259 printf("iovec slot %d base %p len %lx\n", i, iovp->iov_base, iovp->iov_len); 260 } 261 } 262 263 /* msg_iov must be done separately */ 264 static __inline void 265 netbsd32_to_msghdr(mhp32, mhp) 266 struct netbsd32_msghdr *mhp32; 267 struct msghdr *mhp; 268 { 269 270 mhp->msg_name = (caddr_t)(u_long)mhp32->msg_name; 271 mhp->msg_namelen = mhp32->msg_namelen; 272 mhp->msg_iovlen = (size_t)mhp32->msg_iovlen; 273 mhp->msg_control = (caddr_t)(u_long)mhp32->msg_control; 274 mhp->msg_controllen = mhp32->msg_controllen; 275 mhp->msg_flags = mhp32->msg_flags; 276 } 277 278 /* msg_iov must be done separately */ 279 static __inline void 280 netbsd32_from_msghdr(mhp32, mhp) 281 struct netbsd32_msghdr *mhp32; 282 struct msghdr *mhp; 283 { 284 285 mhp32->msg_name = mhp32->msg_name; 286 mhp32->msg_namelen = mhp32->msg_namelen; 287 mhp32->msg_iovlen = mhp32->msg_iovlen; 288 mhp32->msg_control = mhp32->msg_control; 289 mhp32->msg_controllen = mhp->msg_controllen; 290 mhp32->msg_flags = mhp->msg_flags; 291 } 292 293 static __inline void 294 netbsd32_from_statfs(sbp, sb32p) 295 struct statfs *sbp; 296 struct netbsd32_statfs *sb32p; 297 { 298 299 sb32p->f_type = sbp->f_type; 300 sb32p->f_flags = sbp->f_flags; 301 sb32p->f_bsize = (netbsd32_long)sbp->f_bsize; 302 sb32p->f_iosize = (netbsd32_long)sbp->f_iosize; 303 sb32p->f_blocks = (netbsd32_long)sbp->f_blocks; 304 sb32p->f_bfree = (netbsd32_long)sbp->f_bfree; 305 sb32p->f_bavail = (netbsd32_long)sbp->f_bavail; 306 sb32p->f_files = (netbsd32_long)sbp->f_files; 307 sb32p->f_ffree = (netbsd32_long)sbp->f_ffree; 308 sb32p->f_fsid = sbp->f_fsid; 309 sb32p->f_owner = sbp->f_owner; 310 sb32p->f_spare[0] = 0; 311 sb32p->f_spare[1] = 0; 312 sb32p->f_spare[2] = 0; 313 sb32p->f_spare[3] = 0; 314 #if 1 315 /* May as well do the whole batch in one go */ 316 memcpy(sb32p->f_fstypename, sbp->f_fstypename, MFSNAMELEN+MNAMELEN+MNAMELEN); 317 #else 318 /* If we want to be careful */ 319 memcpy(sb32p->f_fstypename, sbp->f_fstypename, MFSNAMELEN); 320 memcpy(sb32p->f_mntonname, sbp->f_mntonname, MNAMELEN); 321 memcpy(sb32p->f_mntfromname, sbp->f_mntfromname, MNAMELEN); 322 #endif 323 } 324 325 static __inline void 326 netbsd32_from_timex(txp, tx32p) 327 struct timex *txp; 328 struct netbsd32_timex *tx32p; 329 { 330 331 tx32p->modes = txp->modes; 332 tx32p->offset = (netbsd32_long)txp->offset; 333 tx32p->freq = (netbsd32_long)txp->freq; 334 tx32p->maxerror = (netbsd32_long)txp->maxerror; 335 tx32p->esterror = (netbsd32_long)txp->esterror; 336 tx32p->status = txp->status; 337 tx32p->constant = (netbsd32_long)txp->constant; 338 tx32p->precision = (netbsd32_long)txp->precision; 339 tx32p->tolerance = (netbsd32_long)txp->tolerance; 340 tx32p->ppsfreq = (netbsd32_long)txp->ppsfreq; 341 tx32p->jitter = (netbsd32_long)txp->jitter; 342 tx32p->shift = txp->shift; 343 tx32p->stabil = (netbsd32_long)txp->stabil; 344 tx32p->jitcnt = (netbsd32_long)txp->jitcnt; 345 tx32p->calcnt = (netbsd32_long)txp->calcnt; 346 tx32p->errcnt = (netbsd32_long)txp->errcnt; 347 tx32p->stbcnt = (netbsd32_long)txp->stbcnt; 348 } 349 350 static __inline void 351 netbsd32_to_timex(tx32p, txp) 352 struct netbsd32_timex *tx32p; 353 struct timex *txp; 354 { 355 356 txp->modes = tx32p->modes; 357 txp->offset = (long)tx32p->offset; 358 txp->freq = (long)tx32p->freq; 359 txp->maxerror = (long)tx32p->maxerror; 360 txp->esterror = (long)tx32p->esterror; 361 txp->status = tx32p->status; 362 txp->constant = (long)tx32p->constant; 363 txp->precision = (long)tx32p->precision; 364 txp->tolerance = (long)tx32p->tolerance; 365 txp->ppsfreq = (long)tx32p->ppsfreq; 366 txp->jitter = (long)tx32p->jitter; 367 txp->shift = tx32p->shift; 368 txp->stabil = (long)tx32p->stabil; 369 txp->jitcnt = (long)tx32p->jitcnt; 370 txp->calcnt = (long)tx32p->calcnt; 371 txp->errcnt = (long)tx32p->errcnt; 372 txp->stbcnt = (long)tx32p->stbcnt; 373 } 374 375 static __inline void 376 netbsd32_from___stat13(sbp, sb32p) 377 struct stat *sbp; 378 struct netbsd32_stat *sb32p; 379 { 380 sb32p->st_dev = sbp->st_dev; 381 sb32p->st_ino = sbp->st_ino; 382 sb32p->st_mode = sbp->st_mode; 383 sb32p->st_nlink = sbp->st_nlink; 384 sb32p->st_uid = sbp->st_uid; 385 sb32p->st_gid = sbp->st_gid; 386 sb32p->st_rdev = sbp->st_rdev; 387 if (sbp->st_size < (quad_t)1 << 32) 388 sb32p->st_size = sbp->st_size; 389 else 390 sb32p->st_size = -2; 391 sb32p->st_atimespec.tv_sec = sbp->st_atimespec.tv_sec; 392 sb32p->st_atimespec.tv_nsec = (netbsd32_long)sbp->st_atimespec.tv_nsec; 393 sb32p->st_mtimespec.tv_sec = sbp->st_mtimespec.tv_sec; 394 sb32p->st_mtimespec.tv_nsec = (netbsd32_long)sbp->st_mtimespec.tv_nsec; 395 sb32p->st_ctimespec.tv_sec = sbp->st_ctimespec.tv_sec; 396 sb32p->st_ctimespec.tv_nsec = (netbsd32_long)sbp->st_ctimespec.tv_nsec; 397 sb32p->st_blksize = sbp->st_blksize; 398 sb32p->st_blocks = sbp->st_blocks; 399 sb32p->st_flags = sbp->st_flags; 400 sb32p->st_gen = sbp->st_gen; 401 } 402 403 static __inline void 404 netbsd32_to_ipc_perm(ip32p, ipp) 405 struct netbsd32_ipc_perm *ip32p; 406 struct ipc_perm *ipp; 407 { 408 409 ipp->cuid = ip32p->cuid; 410 ipp->cgid = ip32p->cgid; 411 ipp->uid = ip32p->uid; 412 ipp->gid = ip32p->gid; 413 ipp->mode = ip32p->mode; 414 ipp->_seq = ip32p->_seq; 415 ipp->_key = (key_t)ip32p->_key; 416 } 417 418 static __inline void 419 netbsd32_from_ipc_perm(ipp, ip32p) 420 struct ipc_perm *ipp; 421 struct netbsd32_ipc_perm *ip32p; 422 { 423 424 ip32p->cuid = ipp->cuid; 425 ip32p->cgid = ipp->cgid; 426 ip32p->uid = ipp->uid; 427 ip32p->gid = ipp->gid; 428 ip32p->mode = ipp->mode; 429 ip32p->_seq = ipp->_seq; 430 ip32p->_key = (netbsd32_key_t)ipp->_key; 431 } 432 433 static __inline void 434 netbsd32_to_msg(m32p, mp) 435 struct netbsd32_msg *m32p; 436 struct msg *mp; 437 { 438 439 mp->msg_next = (struct msg *)(u_long)m32p->msg_next; 440 mp->msg_type = (long)m32p->msg_type; 441 mp->msg_ts = m32p->msg_ts; 442 mp->msg_spot = m32p->msg_spot; 443 } 444 445 static __inline void 446 netbsd32_from_msg(mp, m32p) 447 struct msg *mp; 448 struct netbsd32_msg *m32p; 449 { 450 451 m32p->msg_next = (netbsd32_msgp_t)(u_long)mp->msg_next; 452 m32p->msg_type = (netbsd32_long)mp->msg_type; 453 m32p->msg_ts = mp->msg_ts; 454 m32p->msg_spot = mp->msg_spot; 455 } 456 457 static __inline void 458 netbsd32_to_msqid_ds(ds32p, dsp) 459 struct netbsd32_msqid_ds *ds32p; 460 struct msqid_ds *dsp; 461 { 462 463 netbsd32_to_ipc_perm(&ds32p->msg_perm, &dsp->msg_perm); 464 netbsd32_to_msg((struct netbsd32_msg *)(u_long)ds32p->_msg_first, dsp->_msg_first); 465 netbsd32_to_msg((struct netbsd32_msg *)(u_long)ds32p->_msg_last, dsp->_msg_last); 466 dsp->_msg_cbytes = (u_long)ds32p->_msg_cbytes; 467 dsp->msg_qnum = (u_long)ds32p->msg_qnum; 468 dsp->msg_qbytes = (u_long)ds32p->msg_qbytes; 469 dsp->msg_lspid = ds32p->msg_lspid; 470 dsp->msg_lrpid = ds32p->msg_lrpid; 471 dsp->msg_rtime = (time_t)ds32p->msg_rtime; 472 dsp->msg_stime = (time_t)ds32p->msg_stime; 473 dsp->msg_ctime = (time_t)ds32p->msg_ctime; 474 } 475 476 static __inline void 477 netbsd32_from_msqid_ds(dsp, ds32p) 478 struct msqid_ds *dsp; 479 struct netbsd32_msqid_ds *ds32p; 480 { 481 482 netbsd32_from_ipc_perm(&dsp->msg_perm, &ds32p->msg_perm); 483 netbsd32_from_msg(dsp->_msg_first, (struct netbsd32_msg *)(u_long)ds32p->_msg_first); 484 netbsd32_from_msg(dsp->_msg_last, (struct netbsd32_msg *)(u_long)ds32p->_msg_last); 485 ds32p->_msg_cbytes = (netbsd32_u_long)dsp->_msg_cbytes; 486 ds32p->msg_qnum = (netbsd32_u_long)dsp->msg_qnum; 487 ds32p->msg_qbytes = (netbsd32_u_long)dsp->msg_qbytes; 488 ds32p->msg_lspid = dsp->msg_lspid; 489 ds32p->msg_lrpid = dsp->msg_lrpid; 490 ds32p->msg_rtime = dsp->msg_rtime; 491 ds32p->msg_stime = dsp->msg_stime; 492 ds32p->msg_ctime = dsp->msg_ctime; 493 } 494 495 static __inline void 496 netbsd32_to_shmid_ds(ds32p, dsp) 497 struct netbsd32_shmid_ds *ds32p; 498 struct shmid_ds *dsp; 499 { 500 501 netbsd32_to_ipc_perm(&ds32p->shm_perm, &dsp->shm_perm); 502 dsp->shm_segsz = ds32p->shm_segsz; 503 dsp->shm_lpid = ds32p->shm_lpid; 504 dsp->shm_cpid = ds32p->shm_cpid; 505 dsp->shm_nattch = ds32p->shm_nattch; 506 dsp->shm_atime = (long)ds32p->shm_atime; 507 dsp->shm_dtime = (long)ds32p->shm_dtime; 508 dsp->shm_ctime = (long)ds32p->shm_ctime; 509 dsp->_shm_internal = (void *)(u_long)ds32p->_shm_internal; 510 } 511 512 static __inline void 513 netbsd32_from_shmid_ds(dsp, ds32p) 514 struct shmid_ds *dsp; 515 struct netbsd32_shmid_ds *ds32p; 516 { 517 518 netbsd32_from_ipc_perm(&dsp->shm_perm, &ds32p->shm_perm); 519 ds32p->shm_segsz = dsp->shm_segsz; 520 ds32p->shm_lpid = dsp->shm_lpid; 521 ds32p->shm_cpid = dsp->shm_cpid; 522 ds32p->shm_nattch = dsp->shm_nattch; 523 ds32p->shm_atime = (netbsd32_long)dsp->shm_atime; 524 ds32p->shm_dtime = (netbsd32_long)dsp->shm_dtime; 525 ds32p->shm_ctime = (netbsd32_long)dsp->shm_ctime; 526 ds32p->_shm_internal = (netbsd32_voidp)(u_long)dsp->_shm_internal; 527 } 528 529 static __inline void 530 netbsd32_to_semid_ds(s32dsp, dsp) 531 struct netbsd32_semid_ds *s32dsp; 532 struct semid_ds *dsp; 533 { 534 535 netbsd32_from_ipc_perm(&dsp->sem_perm, &s32dsp->sem_perm); 536 dsp->_sem_base = (struct __sem *)(u_long)s32dsp->_sem_base; 537 dsp->sem_nsems = s32dsp->sem_nsems; 538 dsp->sem_otime = s32dsp->sem_otime; 539 dsp->sem_ctime = s32dsp->sem_ctime; 540 } 541 542 static __inline void 543 netbsd32_from_semid_ds(dsp, s32dsp) 544 struct semid_ds *dsp; 545 struct netbsd32_semid_ds *s32dsp; 546 { 547 548 netbsd32_to_ipc_perm(&s32dsp->sem_perm, &dsp->sem_perm); 549 s32dsp->_sem_base = (netbsd32_semp_t)(u_long)dsp->_sem_base; 550 s32dsp->sem_nsems = dsp->sem_nsems; 551 s32dsp->sem_otime = dsp->sem_otime; 552 s32dsp->sem_ctime = dsp->sem_ctime; 553 } 554 555 /* 556 * below are all the standard NetBSD system calls, in the 32bit 557 * environment, witht he necessary conversions to 64bit before 558 * calling the real syscall. 559 */ 560 561 562 int 563 netbsd32_exit(p, v, retval) 564 struct proc *p; 565 void *v; 566 register_t *retval; 567 { 568 struct netbsd32_exit_args /* { 569 syscallarg(int) rval; 570 } */ *uap = v; 571 struct sys_exit_args ua; 572 573 NETBSD32TO64_UAP(rval); 574 sys_exit(p, &ua, retval); 575 } 576 577 int 578 netbsd32_read(p, v, retval) 579 struct proc *p; 580 void *v; 581 register_t *retval; 582 { 583 struct netbsd32_read_args /* { 584 syscallarg(int) fd; 585 syscallarg(netbsd32_voidp) buf; 586 syscallarg(netbsd32_size_t) nbyte; 587 } */ *uap = v; 588 struct sys_read_args ua; 589 590 NETBSD32TO64_UAP(fd); 591 NETBSD32TOP_UAP(buf, void *); 592 NETBSD32TOX_UAP(nbyte, size_t); 593 return sys_read(p, &ua, retval); 594 } 595 596 int 597 netbsd32_write(p, v, retval) 598 struct proc *p; 599 void *v; 600 register_t *retval; 601 { 602 struct netbsd32_write_args /* { 603 syscallarg(int) fd; 604 syscallarg(const netbsd32_voidp) buf; 605 syscallarg(netbsd32_size_t) nbyte; 606 } */ *uap = v; 607 struct sys_write_args ua; 608 609 NETBSD32TO64_UAP(fd); 610 NETBSD32TOP_UAP(buf, void *); 611 NETBSD32TOX_UAP(nbyte, size_t); 612 return sys_write(p, &ua, retval); 613 } 614 615 int 616 netbsd32_close(p, v, retval) 617 struct proc *p; 618 void *v; 619 register_t *retval; 620 { 621 struct netbsd32_close_args /* { 622 syscallarg(int) fd; 623 } */ *uap = v; 624 struct sys_close_args ua; 625 626 NETBSD32TO64_UAP(fd); 627 return sys_write(p, &ua, retval); 628 } 629 630 int 631 netbsd32_open(p, v, retval) 632 struct proc *p; 633 void *v; 634 register_t *retval; 635 { 636 struct netbsd32_open_args /* { 637 syscallarg(const netbsd32_charp) path; 638 syscallarg(int) flags; 639 syscallarg(mode_t) mode; 640 } */ *uap = v; 641 struct sys_open_args ua; 642 caddr_t sg; 643 644 NETBSD32TOP_UAP(path, const char); 645 NETBSD32TO64_UAP(flags); 646 NETBSD32TO64_UAP(mode); 647 sg = stackgap_init(p->p_emul); 648 NETBSD32_CHECK_ALT_EXIST(p, &sg, SCARG(&ua, path)); 649 650 return (sys_open(p, &ua, retval)); 651 } 652 653 int 654 netbsd32_wait4(q, v, retval) 655 struct proc *q; 656 void *v; 657 register_t *retval; 658 { 659 struct netbsd32_wait4_args /* { 660 syscallarg(int) pid; 661 syscallarg(netbsd32_intp) status; 662 syscallarg(int) options; 663 syscallarg(netbsd32_rusagep_t) rusage; 664 } */ *uap = v; 665 struct netbsd32_rusage ru32; 666 register int nfound; 667 register struct proc *p, *t; 668 int status, error; 669 670 if (SCARG(uap, pid) == 0) 671 SCARG(uap, pid) = -q->p_pgid; 672 if (SCARG(uap, options) &~ (WUNTRACED|WNOHANG)) 673 return (EINVAL); 674 675 loop: 676 nfound = 0; 677 for (p = q->p_children.lh_first; p != 0; p = p->p_sibling.le_next) { 678 if (SCARG(uap, pid) != WAIT_ANY && 679 p->p_pid != SCARG(uap, pid) && 680 p->p_pgid != -SCARG(uap, pid)) 681 continue; 682 nfound++; 683 if (p->p_stat == SZOMB) { 684 retval[0] = p->p_pid; 685 686 if (SCARG(uap, status)) { 687 status = p->p_xstat; /* convert to int */ 688 error = copyout((caddr_t)&status, 689 (caddr_t)(u_long)SCARG(uap, status), 690 sizeof(status)); 691 if (error) 692 return (error); 693 } 694 if (SCARG(uap, rusage)) { 695 netbsd32_from_rusage(p->p_ru, &ru32); 696 if ((error = copyout((caddr_t)&ru32, 697 (caddr_t)(u_long)SCARG(uap, rusage), 698 sizeof(struct netbsd32_rusage)))) 699 return (error); 700 } 701 /* 702 * If we got the child via ptrace(2) or procfs, and 703 * the parent is different (meaning the process was 704 * attached, rather than run as a child), then we need 705 * to give it back to the old parent, and send the 706 * parent a SIGCHLD. The rest of the cleanup will be 707 * done when the old parent waits on the child. 708 */ 709 if ((p->p_flag & P_TRACED) && 710 p->p_oppid != p->p_pptr->p_pid) { 711 t = pfind(p->p_oppid); 712 proc_reparent(p, t ? t : initproc); 713 p->p_oppid = 0; 714 p->p_flag &= ~(P_TRACED|P_WAITED|P_FSTRACE); 715 psignal(p->p_pptr, SIGCHLD); 716 wakeup((caddr_t)p->p_pptr); 717 return (0); 718 } 719 p->p_xstat = 0; 720 ruadd(&q->p_stats->p_cru, p->p_ru); 721 pool_put(&rusage_pool, p->p_ru); 722 723 /* 724 * Finally finished with old proc entry. 725 * Unlink it from its process group and free it. 726 */ 727 leavepgrp(p); 728 729 LIST_REMOVE(p, p_list); /* off zombproc */ 730 731 LIST_REMOVE(p, p_sibling); 732 733 /* 734 * Decrement the count of procs running with this uid. 735 */ 736 (void)chgproccnt(p->p_cred->p_ruid, -1); 737 738 /* 739 * Free up credentials. 740 */ 741 if (--p->p_cred->p_refcnt == 0) { 742 crfree(p->p_cred->pc_ucred); 743 pool_put(&pcred_pool, p->p_cred); 744 } 745 746 /* 747 * Release reference to text vnode 748 */ 749 if (p->p_textvp) 750 vrele(p->p_textvp); 751 752 pool_put(&proc_pool, p); 753 nprocs--; 754 return (0); 755 } 756 if (p->p_stat == SSTOP && (p->p_flag & P_WAITED) == 0 && 757 (p->p_flag & P_TRACED || SCARG(uap, options) & WUNTRACED)) { 758 p->p_flag |= P_WAITED; 759 retval[0] = p->p_pid; 760 761 if (SCARG(uap, status)) { 762 status = W_STOPCODE(p->p_xstat); 763 error = copyout((caddr_t)&status, 764 (caddr_t)(u_long)SCARG(uap, status), 765 sizeof(status)); 766 } else 767 error = 0; 768 return (error); 769 } 770 } 771 if (nfound == 0) 772 return (ECHILD); 773 if (SCARG(uap, options) & WNOHANG) { 774 retval[0] = 0; 775 return (0); 776 } 777 if ((error = tsleep((caddr_t)q, PWAIT | PCATCH, "wait", 0)) != 0) 778 return (error); 779 goto loop; 780 } 781 782 int 783 netbsd32_link(p, v, retval) 784 struct proc *p; 785 void *v; 786 register_t *retval; 787 { 788 struct netbsd32_link_args /* { 789 syscallarg(const netbsd32_charp) path; 790 syscallarg(const netbsd32_charp) link; 791 } */ *uap = v; 792 struct sys_link_args ua; 793 794 NETBSD32TOP_UAP(path, const char); 795 NETBSD32TOP_UAP(link, const char); 796 return (sys_link(p, &ua, retval)); 797 } 798 799 int 800 netbsd32_unlink(p, v, retval) 801 struct proc *p; 802 void *v; 803 register_t *retval; 804 { 805 struct netbsd32_unlink_args /* { 806 syscallarg(const netbsd32_charp) path; 807 } */ *uap = v; 808 struct sys_unlink_args ua; 809 810 NETBSD32TOP_UAP(path, const char); 811 812 return (sys_unlink(p, &ua, retval)); 813 } 814 815 int 816 netbsd32_chdir(p, v, retval) 817 struct proc *p; 818 void *v; 819 register_t *retval; 820 { 821 struct netbsd32_chdir_args /* { 822 syscallarg(const netbsd32_charp) path; 823 } */ *uap = v; 824 struct sys_chdir_args ua; 825 826 NETBSD32TOP_UAP(path, const char); 827 828 return (sys_chdir(p, &ua, retval)); 829 } 830 831 int 832 netbsd32_fchdir(p, v, retval) 833 struct proc *p; 834 void *v; 835 register_t *retval; 836 { 837 struct netbsd32_fchdir_args /* { 838 syscallarg(int) fd; 839 } */ *uap = v; 840 struct sys_fchdir_args ua; 841 842 NETBSD32TO64_UAP(fd); 843 844 return (sys_fchdir(p, &ua, retval)); 845 } 846 847 int 848 netbsd32_mknod(p, v, retval) 849 struct proc *p; 850 void *v; 851 register_t *retval; 852 { 853 struct netbsd32_mknod_args /* { 854 syscallarg(const netbsd32_charp) path; 855 syscallarg(mode_t) mode; 856 syscallarg(dev_t) dev; 857 } */ *uap = v; 858 struct sys_mknod_args ua; 859 860 NETBSD32TOP_UAP(path, const char); 861 NETBSD32TO64_UAP(dev); 862 NETBSD32TO64_UAP(mode); 863 864 return (sys_mknod(p, &ua, retval)); 865 } 866 867 int 868 netbsd32_chmod(p, v, retval) 869 struct proc *p; 870 void *v; 871 register_t *retval; 872 { 873 struct netbsd32_chmod_args /* { 874 syscallarg(const netbsd32_charp) path; 875 syscallarg(mode_t) mode; 876 } */ *uap = v; 877 struct sys_chmod_args ua; 878 879 NETBSD32TOP_UAP(path, const char); 880 NETBSD32TO64_UAP(mode); 881 882 return (sys_chmod(p, &ua, retval)); 883 } 884 885 int 886 netbsd32_chown(p, v, retval) 887 struct proc *p; 888 void *v; 889 register_t *retval; 890 { 891 struct netbsd32_chown_args /* { 892 syscallarg(const netbsd32_charp) path; 893 syscallarg(uid_t) uid; 894 syscallarg(gid_t) gid; 895 } */ *uap = v; 896 struct sys_chown_args ua; 897 898 NETBSD32TOP_UAP(path, const char); 899 NETBSD32TO64_UAP(uid); 900 NETBSD32TO64_UAP(gid); 901 902 return (sys_chown(p, &ua, retval)); 903 } 904 905 int 906 netbsd32_break(p, v, retval) 907 struct proc *p; 908 void *v; 909 register_t *retval; 910 { 911 struct netbsd32_break_args /* { 912 syscallarg(netbsd32_charp) nsize; 913 } */ *uap = v; 914 struct sys_obreak_args ua; 915 916 SCARG(&ua, nsize) = (char *)(u_long)SCARG(uap, nsize); 917 NETBSD32TOP_UAP(nsize, char); 918 return (sys_obreak(p, &ua, retval)); 919 } 920 921 int 922 netbsd32_getfsstat(p, v, retval) 923 struct proc *p; 924 void *v; 925 register_t *retval; 926 { 927 struct netbsd32_getfsstat_args /* { 928 syscallarg(netbsd32_statfsp_t) buf; 929 syscallarg(netbsd32_long) bufsize; 930 syscallarg(int) flags; 931 } */ *uap = v; 932 struct sys_getfsstat_args ua; 933 struct statfs sb; 934 struct netbsd32_statfs *sb32p; 935 int error; 936 937 sb32p = (struct netbsd32_statfs *)(u_long)SCARG(uap, buf); 938 if (sb32p) 939 SCARG(&ua, buf) = &sb; 940 else 941 SCARG(&ua, buf) = NULL; 942 NETBSD32TOX_UAP(bufsize, long); 943 NETBSD32TO64_UAP(flags); 944 error = sys_getfsstat(p, &ua, retval); 945 if (error) 946 return (error); 947 948 if (sb32p) { 949 struct netbsd32_statfs sb32; 950 netbsd32_from_statfs(&sb, &sb32); 951 if (copyout(&sb32, sb32p, sizeof(sb32))) 952 return EFAULT; 953 } 954 return (0); 955 } 956 957 int 958 netbsd32_mount(p, v, retval) 959 struct proc *p; 960 void *v; 961 register_t *retval; 962 { 963 struct netbsd32_mount_args /* { 964 syscallarg(const netbsd32_charp) type; 965 syscallarg(const netbsd32_charp) path; 966 syscallarg(int) flags; 967 syscallarg(netbsd32_voidp) data; 968 } */ *uap = v; 969 struct sys_mount_args ua; 970 971 NETBSD32TOP_UAP(type, const char); 972 NETBSD32TOP_UAP(path, const char); 973 NETBSD32TO64_UAP(flags); 974 NETBSD32TOP_UAP(data, void); 975 return (sys_mount(p, &ua, retval)); 976 } 977 978 int 979 netbsd32_unmount(p, v, retval) 980 struct proc *p; 981 void *v; 982 register_t *retval; 983 { 984 struct netbsd32_unmount_args /* { 985 syscallarg(const netbsd32_charp) path; 986 syscallarg(int) flags; 987 } */ *uap = v; 988 struct sys_unmount_args ua; 989 990 NETBSD32TOP_UAP(path, const char); 991 NETBSD32TO64_UAP(flags); 992 return (sys_unmount(p, &ua, retval)); 993 } 994 995 int 996 netbsd32_setuid(p, v, retval) 997 struct proc *p; 998 void *v; 999 register_t *retval; 1000 { 1001 struct netbsd32_setuid_args /* { 1002 syscallarg(uid_t) uid; 1003 } */ *uap = v; 1004 struct sys_setuid_args ua; 1005 1006 NETBSD32TO64_UAP(uid); 1007 return (sys_setuid(p, &ua, retval)); 1008 } 1009 1010 int 1011 netbsd32_ptrace(p, v, retval) 1012 struct proc *p; 1013 void *v; 1014 register_t *retval; 1015 { 1016 struct netbsd32_ptrace_args /* { 1017 syscallarg(int) req; 1018 syscallarg(pid_t) pid; 1019 syscallarg(netbsd32_caddr_t) addr; 1020 syscallarg(int) data; 1021 } */ *uap = v; 1022 struct sys_ptrace_args ua; 1023 1024 NETBSD32TO64_UAP(req); 1025 NETBSD32TO64_UAP(pid); 1026 NETBSD32TOX64_UAP(addr, caddr_t); 1027 NETBSD32TO64_UAP(data); 1028 return (sys_ptrace(p, &ua, retval)); 1029 } 1030 1031 int 1032 netbsd32_recvmsg(p, v, retval) 1033 struct proc *p; 1034 void *v; 1035 register_t *retval; 1036 { 1037 struct netbsd32_recvmsg_args /* { 1038 syscallarg(int) s; 1039 syscallarg(netbsd32_msghdrp_t) msg; 1040 syscallarg(int) flags; 1041 } */ *uap = v; 1042 struct netbsd32_msghdr msg; 1043 struct iovec aiov[UIO_SMALLIOV], *uiov, *iov; 1044 register int error; 1045 1046 error = copyin((caddr_t)(u_long)SCARG(uap, msg), (caddr_t)&msg, 1047 sizeof(msg)); 1048 /* netbsd32_msghdr needs the iov pre-allocated */ 1049 if (error) 1050 return (error); 1051 if ((u_int)msg.msg_iovlen > UIO_SMALLIOV) { 1052 if ((u_int)msg.msg_iovlen > IOV_MAX) 1053 return (EMSGSIZE); 1054 MALLOC(iov, struct iovec *, 1055 sizeof(struct iovec) * (u_int)msg.msg_iovlen, M_IOV, 1056 M_WAITOK); 1057 } else if ((u_int)msg.msg_iovlen > 0) 1058 iov = aiov; 1059 else 1060 return (EMSGSIZE); 1061 #ifdef COMPAT_OLDSOCK 1062 msg.msg_flags = SCARG(uap, flags) &~ MSG_COMPAT; 1063 #else 1064 msg.msg_flags = SCARG(uap, flags); 1065 #endif 1066 uiov = (struct iovec *)(u_long)msg.msg_iov; 1067 error = netbsd32_to_iovecin((struct netbsd32_iovec *)uiov, 1068 iov, msg.msg_iovlen); 1069 if (error) 1070 goto done; 1071 if ((error = recvit32(p, SCARG(uap, s), &msg, iov, (caddr_t)0, retval)) == 0) { 1072 error = copyout((caddr_t)&msg, (caddr_t)(u_long)SCARG(uap, msg), 1073 sizeof(msg)); 1074 } 1075 done: 1076 if (iov != aiov) 1077 FREE(iov, M_IOV); 1078 return (error); 1079 } 1080 1081 int 1082 recvit32(p, s, mp, iov, namelenp, retsize) 1083 struct proc *p; 1084 int s; 1085 struct netbsd32_msghdr *mp; 1086 struct iovec *iov; 1087 caddr_t namelenp; 1088 register_t *retsize; 1089 { 1090 struct file *fp; 1091 struct uio auio; 1092 register int i; 1093 int len, error; 1094 struct mbuf *from = 0, *control = 0; 1095 struct socket *so; 1096 #ifdef KTRACE 1097 struct iovec *ktriov = NULL; 1098 #endif 1099 1100 /* getsock() will use the descriptor for us */ 1101 if ((error = getsock(p->p_fd, s, &fp)) != 0) 1102 return (error); 1103 auio.uio_iov = (struct iovec *)(u_long)mp->msg_iov; 1104 auio.uio_iovcnt = mp->msg_iovlen; 1105 auio.uio_segflg = UIO_USERSPACE; 1106 auio.uio_rw = UIO_READ; 1107 auio.uio_procp = p; 1108 auio.uio_offset = 0; /* XXX */ 1109 auio.uio_resid = 0; 1110 for (i = 0; i < mp->msg_iovlen; i++, iov++) { 1111 #if 0 1112 /* cannot happen iov_len is unsigned */ 1113 if (iov->iov_len < 0) { 1114 error = EINVAL; 1115 goto out1; 1116 } 1117 #endif 1118 /* 1119 * Reads return ssize_t because -1 is returned on error. 1120 * Therefore we must restrict the length to SSIZE_MAX to 1121 * avoid garbage return values. 1122 */ 1123 auio.uio_resid += iov->iov_len; 1124 if (iov->iov_len > SSIZE_MAX || auio.uio_resid > SSIZE_MAX) { 1125 error = EINVAL; 1126 goto out1; 1127 } 1128 } 1129 #ifdef KTRACE 1130 if (KTRPOINT(p, KTR_GENIO)) { 1131 int iovlen = auio.uio_iovcnt * sizeof(struct iovec); 1132 1133 MALLOC(ktriov, struct iovec *, iovlen, M_TEMP, M_WAITOK); 1134 memcpy((caddr_t)ktriov, (caddr_t)auio.uio_iov, iovlen); 1135 } 1136 #endif 1137 len = auio.uio_resid; 1138 so = (struct socket *)fp->f_data; 1139 error = (*so->so_receive)(so, &from, &auio, NULL, 1140 mp->msg_control ? &control : NULL, &mp->msg_flags); 1141 if (error) { 1142 if (auio.uio_resid != len && (error == ERESTART || 1143 error == EINTR || error == EWOULDBLOCK)) 1144 error = 0; 1145 } 1146 #ifdef KTRACE 1147 if (ktriov != NULL) { 1148 if (error == 0) 1149 ktrgenio(p->p_tracep, s, UIO_READ, 1150 ktriov, len - auio.uio_resid, error); 1151 FREE(ktriov, M_TEMP); 1152 } 1153 #endif 1154 if (error) 1155 goto out; 1156 *retsize = len - auio.uio_resid; 1157 if (mp->msg_name) { 1158 len = mp->msg_namelen; 1159 if (len <= 0 || from == 0) 1160 len = 0; 1161 else { 1162 #ifdef COMPAT_OLDSOCK 1163 if (mp->msg_flags & MSG_COMPAT) 1164 mtod(from, struct osockaddr *)->sa_family = 1165 mtod(from, struct sockaddr *)->sa_family; 1166 #endif 1167 if (len > from->m_len) 1168 len = from->m_len; 1169 /* else if len < from->m_len ??? */ 1170 error = copyout(mtod(from, caddr_t), 1171 (caddr_t)(u_long)mp->msg_name, (unsigned)len); 1172 if (error) 1173 goto out; 1174 } 1175 mp->msg_namelen = len; 1176 if (namelenp && 1177 (error = copyout((caddr_t)&len, namelenp, sizeof(int)))) { 1178 #ifdef COMPAT_OLDSOCK 1179 if (mp->msg_flags & MSG_COMPAT) 1180 error = 0; /* old recvfrom didn't check */ 1181 else 1182 #endif 1183 goto out; 1184 } 1185 } 1186 if (mp->msg_control) { 1187 #ifdef COMPAT_OLDSOCK 1188 /* 1189 * We assume that old recvmsg calls won't receive access 1190 * rights and other control info, esp. as control info 1191 * is always optional and those options didn't exist in 4.3. 1192 * If we receive rights, trim the cmsghdr; anything else 1193 * is tossed. 1194 */ 1195 if (control && mp->msg_flags & MSG_COMPAT) { 1196 if (mtod(control, struct cmsghdr *)->cmsg_level != 1197 SOL_SOCKET || 1198 mtod(control, struct cmsghdr *)->cmsg_type != 1199 SCM_RIGHTS) { 1200 mp->msg_controllen = 0; 1201 goto out; 1202 } 1203 control->m_len -= sizeof(struct cmsghdr); 1204 control->m_data += sizeof(struct cmsghdr); 1205 } 1206 #endif 1207 len = mp->msg_controllen; 1208 if (len <= 0 || control == 0) 1209 len = 0; 1210 else { 1211 struct mbuf *m = control; 1212 caddr_t p = (caddr_t)(u_long)mp->msg_control; 1213 1214 do { 1215 i = m->m_len; 1216 if (len < i) { 1217 mp->msg_flags |= MSG_CTRUNC; 1218 i = len; 1219 } 1220 error = copyout(mtod(m, caddr_t), p, 1221 (unsigned)i); 1222 if (m->m_next) 1223 i = ALIGN(i); 1224 p += i; 1225 len -= i; 1226 if (error != 0 || len <= 0) 1227 break; 1228 } while ((m = m->m_next) != NULL); 1229 len = p - (caddr_t)(u_long)mp->msg_control; 1230 } 1231 mp->msg_controllen = len; 1232 } 1233 out: 1234 if (from) 1235 m_freem(from); 1236 if (control) 1237 m_freem(control); 1238 out1: 1239 FILE_UNUSE(fp, p); 1240 return (error); 1241 } 1242 1243 1244 int 1245 netbsd32_sendmsg(p, v, retval) 1246 struct proc *p; 1247 void *v; 1248 register_t *retval; 1249 { 1250 struct netbsd32_sendmsg_args /* { 1251 syscallarg(int) s; 1252 syscallarg(const netbsd32_msghdrp_t) msg; 1253 syscallarg(int) flags; 1254 } */ *uap = v; 1255 struct msghdr msg; 1256 struct netbsd32_msghdr msg32; 1257 struct iovec aiov[UIO_SMALLIOV], *iov; 1258 int error; 1259 1260 error = copyin((caddr_t)(u_long)SCARG(uap, msg), 1261 (caddr_t)&msg32, sizeof(msg32)); 1262 if (error) 1263 return (error); 1264 netbsd32_to_msghdr(&msg32, &msg); 1265 if ((u_int)msg.msg_iovlen > UIO_SMALLIOV) { 1266 if ((u_int)msg.msg_iovlen > IOV_MAX) 1267 return (EMSGSIZE); 1268 MALLOC(iov, struct iovec *, 1269 sizeof(struct iovec) * (u_int)msg.msg_iovlen, M_IOV, 1270 M_WAITOK); 1271 } else if ((u_int)msg.msg_iovlen > 0) 1272 iov = aiov; 1273 else 1274 return (EMSGSIZE); 1275 error = netbsd32_to_iovecin((struct netbsd32_iovec *)msg.msg_iov, 1276 iov, msg.msg_iovlen); 1277 if (error) 1278 goto done; 1279 msg.msg_iov = iov; 1280 #ifdef COMPAT_OLDSOCK 1281 msg.msg_flags = 0; 1282 #endif 1283 /* Luckily we can use this directly */ 1284 error = sendit(p, SCARG(uap, s), &msg, SCARG(uap, flags), retval); 1285 done: 1286 if (iov != aiov) 1287 FREE(iov, M_IOV); 1288 return (error); 1289 } 1290 1291 int 1292 netbsd32_recvfrom(p, v, retval) 1293 struct proc *p; 1294 void *v; 1295 register_t *retval; 1296 { 1297 struct netbsd32_recvfrom_args /* { 1298 syscallarg(int) s; 1299 syscallarg(netbsd32_voidp) buf; 1300 syscallarg(netbsd32_size_t) len; 1301 syscallarg(int) flags; 1302 syscallarg(netbsd32_sockaddrp_t) from; 1303 syscallarg(netbsd32_intp) fromlenaddr; 1304 } */ *uap = v; 1305 struct netbsd32_msghdr msg; 1306 struct iovec aiov; 1307 int error; 1308 1309 if (SCARG(uap, fromlenaddr)) { 1310 error = copyin((caddr_t)(u_long)SCARG(uap, fromlenaddr), 1311 (caddr_t)&msg.msg_namelen, 1312 sizeof(msg.msg_namelen)); 1313 if (error) 1314 return (error); 1315 } else 1316 msg.msg_namelen = 0; 1317 msg.msg_name = SCARG(uap, from); 1318 msg.msg_iov = NULL; /* We can't store a real pointer here */ 1319 msg.msg_iovlen = 1; 1320 aiov.iov_base = (caddr_t)(u_long)SCARG(uap, buf); 1321 aiov.iov_len = (u_long)SCARG(uap, len); 1322 msg.msg_control = 0; 1323 msg.msg_flags = SCARG(uap, flags); 1324 return (recvit32(p, SCARG(uap, s), &msg, &aiov, 1325 (caddr_t)(u_long)SCARG(uap, fromlenaddr), retval)); 1326 } 1327 1328 int 1329 netbsd32_sendto(p, v, retval) 1330 struct proc *p; 1331 void *v; 1332 register_t *retval; 1333 { 1334 struct netbsd32_sendto_args /* { 1335 syscallarg(int) s; 1336 syscallarg(const netbsd32_voidp) buf; 1337 syscallarg(netbsd32_size_t) len; 1338 syscallarg(int) flags; 1339 syscallarg(const netbsd32_sockaddrp_t) to; 1340 syscallarg(int) tolen; 1341 } */ *uap = v; 1342 struct msghdr msg; 1343 struct iovec aiov; 1344 1345 msg.msg_name = (caddr_t)(u_long)SCARG(uap, to); /* XXX kills const */ 1346 msg.msg_namelen = SCARG(uap, tolen); 1347 msg.msg_iov = &aiov; 1348 msg.msg_iovlen = 1; 1349 msg.msg_control = 0; 1350 #ifdef COMPAT_OLDSOCK 1351 msg.msg_flags = 0; 1352 #endif 1353 aiov.iov_base = (char *)(u_long)SCARG(uap, buf); /* XXX kills const */ 1354 aiov.iov_len = SCARG(uap, len); 1355 return (sendit(p, SCARG(uap, s), &msg, SCARG(uap, flags), retval)); 1356 } 1357 1358 int 1359 netbsd32_accept(p, v, retval) 1360 struct proc *p; 1361 void *v; 1362 register_t *retval; 1363 { 1364 struct netbsd32_accept_args /* { 1365 syscallarg(int) s; 1366 syscallarg(netbsd32_sockaddrp_t) name; 1367 syscallarg(netbsd32_intp) anamelen; 1368 } */ *uap = v; 1369 struct sys_accept_args ua; 1370 1371 NETBSD32TO64_UAP(s); 1372 NETBSD32TOP_UAP(name, struct sockaddr); 1373 NETBSD32TOP_UAP(anamelen, int); 1374 return (sys_accept(p, &ua, retval)); 1375 } 1376 1377 int 1378 netbsd32_getpeername(p, v, retval) 1379 struct proc *p; 1380 void *v; 1381 register_t *retval; 1382 { 1383 struct netbsd32_getpeername_args /* { 1384 syscallarg(int) fdes; 1385 syscallarg(netbsd32_sockaddrp_t) asa; 1386 syscallarg(netbsd32_intp) alen; 1387 } */ *uap = v; 1388 struct sys_getpeername_args ua; 1389 1390 NETBSD32TO64_UAP(fdes); 1391 NETBSD32TOP_UAP(asa, struct sockaddr); 1392 NETBSD32TOP_UAP(alen, int); 1393 /* NB: do the protocol specific sockaddrs need to be converted? */ 1394 return (sys_getpeername(p, &ua, retval)); 1395 } 1396 1397 int 1398 netbsd32_getsockname(p, v, retval) 1399 struct proc *p; 1400 void *v; 1401 register_t *retval; 1402 { 1403 struct netbsd32_getsockname_args /* { 1404 syscallarg(int) fdes; 1405 syscallarg(netbsd32_sockaddrp_t) asa; 1406 syscallarg(netbsd32_intp) alen; 1407 } */ *uap = v; 1408 struct sys_getsockname_args ua; 1409 1410 NETBSD32TO64_UAP(fdes); 1411 NETBSD32TOP_UAP(asa, struct sockaddr); 1412 NETBSD32TOP_UAP(alen, int); 1413 return (sys_getsockname(p, &ua, retval)); 1414 } 1415 1416 int 1417 netbsd32_access(p, v, retval) 1418 struct proc *p; 1419 void *v; 1420 register_t *retval; 1421 { 1422 struct netbsd32_access_args /* { 1423 syscallarg(const netbsd32_charp) path; 1424 syscallarg(int) flags; 1425 } */ *uap = v; 1426 struct sys_access_args ua; 1427 caddr_t sg; 1428 1429 NETBSD32TOP_UAP(path, const char); 1430 NETBSD32TO64_UAP(flags); 1431 sg = stackgap_init(p->p_emul); 1432 NETBSD32_CHECK_ALT_EXIST(p, &sg, SCARG(&ua, path)); 1433 1434 return (sys_access(p, &ua, retval)); 1435 } 1436 1437 int 1438 netbsd32_chflags(p, v, retval) 1439 struct proc *p; 1440 void *v; 1441 register_t *retval; 1442 { 1443 struct netbsd32_chflags_args /* { 1444 syscallarg(const netbsd32_charp) path; 1445 syscallarg(netbsd32_u_long) flags; 1446 } */ *uap = v; 1447 struct sys_chflags_args ua; 1448 1449 NETBSD32TOP_UAP(path, const char); 1450 NETBSD32TO64_UAP(flags); 1451 1452 return (sys_chflags(p, &ua, retval)); 1453 } 1454 1455 int 1456 netbsd32_fchflags(p, v, retval) 1457 struct proc *p; 1458 void *v; 1459 register_t *retval; 1460 { 1461 struct netbsd32_fchflags_args /* { 1462 syscallarg(int) fd; 1463 syscallarg(netbsd32_u_long) flags; 1464 } */ *uap = v; 1465 struct sys_fchflags_args ua; 1466 1467 NETBSD32TO64_UAP(fd); 1468 NETBSD32TO64_UAP(flags); 1469 1470 return (sys_fchflags(p, &ua, retval)); 1471 } 1472 1473 int 1474 netbsd32_kill(p, v, retval) 1475 struct proc *p; 1476 void *v; 1477 register_t *retval; 1478 { 1479 struct netbsd32_kill_args /* { 1480 syscallarg(int) pid; 1481 syscallarg(int) signum; 1482 } */ *uap = v; 1483 struct sys_kill_args ua; 1484 1485 NETBSD32TO64_UAP(pid); 1486 NETBSD32TO64_UAP(signum); 1487 1488 return (sys_kill(p, &ua, retval)); 1489 } 1490 1491 int 1492 netbsd32_dup(p, v, retval) 1493 struct proc *p; 1494 void *v; 1495 register_t *retval; 1496 { 1497 struct netbsd32_dup_args /* { 1498 syscallarg(int) fd; 1499 } */ *uap = v; 1500 struct sys_dup_args ua; 1501 1502 NETBSD32TO64_UAP(fd); 1503 1504 return (sys_dup(p, &ua, retval)); 1505 } 1506 1507 int 1508 netbsd32_profil(p, v, retval) 1509 struct proc *p; 1510 void *v; 1511 register_t *retval; 1512 { 1513 struct netbsd32_profil_args /* { 1514 syscallarg(netbsd32_caddr_t) samples; 1515 syscallarg(netbsd32_size_t) size; 1516 syscallarg(netbsd32_u_long) offset; 1517 syscallarg(u_int) scale; 1518 } */ *uap = v; 1519 struct sys_profil_args ua; 1520 1521 NETBSD32TOX64_UAP(samples, caddr_t); 1522 NETBSD32TOX_UAP(size, size_t); 1523 NETBSD32TOX_UAP(offset, u_long); 1524 NETBSD32TO64_UAP(scale); 1525 return (sys_profil(p, &ua, retval)); 1526 } 1527 1528 int 1529 netbsd32_ktrace(p, v, retval) 1530 struct proc *p; 1531 void *v; 1532 register_t *retval; 1533 { 1534 struct netbsd32_ktrace_args /* { 1535 syscallarg(const netbsd32_charp) fname; 1536 syscallarg(int) ops; 1537 syscallarg(int) facs; 1538 syscallarg(int) pid; 1539 } */ *uap = v; 1540 struct sys_ktrace_args ua; 1541 1542 NETBSD32TOP_UAP(fname, const char); 1543 NETBSD32TO64_UAP(ops); 1544 NETBSD32TO64_UAP(facs); 1545 NETBSD32TO64_UAP(pid); 1546 return (sys_ktrace(p, &ua, retval)); 1547 } 1548 1549 int 1550 netbsd32_sigaction(p, v, retval) 1551 struct proc *p; 1552 void *v; 1553 register_t *retval; 1554 { 1555 struct netbsd32_sigaction_args /* { 1556 syscallarg(int) signum; 1557 syscallarg(const netbsd32_sigactionp_t) nsa; 1558 syscallarg(netbsd32_sigactionp_t) osa; 1559 } */ *uap = v; 1560 struct sigaction nsa, osa; 1561 struct netbsd32_sigaction *sa32p, sa32; 1562 int error; 1563 1564 if (SCARG(uap, nsa)) { 1565 sa32p = (struct netbsd32_sigaction *)(u_long)SCARG(uap, nsa); 1566 if (copyin(sa32p, &sa32, sizeof(sa32))) 1567 return EFAULT; 1568 nsa.sa_handler = (void *)(u_long)sa32.sa_handler; 1569 nsa.sa_mask = sa32.sa_mask; 1570 nsa.sa_flags = sa32.sa_flags; 1571 } 1572 error = sigaction1(p, SCARG(uap, signum), 1573 SCARG(uap, nsa) ? &nsa : 0, 1574 SCARG(uap, osa) ? &osa : 0); 1575 1576 if (error) 1577 return (error); 1578 1579 if (SCARG(uap, osa)) { 1580 sa32.sa_handler = (netbsd32_sigactionp_t)(u_long)osa.sa_handler; 1581 sa32.sa_mask = osa.sa_mask; 1582 sa32.sa_flags = osa.sa_flags; 1583 sa32p = (struct netbsd32_sigaction *)(u_long)SCARG(uap, osa); 1584 if (copyout(&sa32, sa32p, sizeof(sa32))) 1585 return EFAULT; 1586 } 1587 1588 return (0); 1589 } 1590 1591 int 1592 netbsd32___getlogin(p, v, retval) 1593 struct proc *p; 1594 void *v; 1595 register_t *retval; 1596 { 1597 struct netbsd32___getlogin_args /* { 1598 syscallarg(netbsd32_charp) namebuf; 1599 syscallarg(u_int) namelen; 1600 } */ *uap = v; 1601 struct sys___getlogin_args ua; 1602 1603 NETBSD32TOP_UAP(namebuf, char); 1604 NETBSD32TO64_UAP(namelen); 1605 return (sys___getlogin(p, &ua, retval)); 1606 } 1607 1608 int 1609 netbsd32_setlogin(p, v, retval) 1610 struct proc *p; 1611 void *v; 1612 register_t *retval; 1613 { 1614 struct netbsd32_setlogin_args /* { 1615 syscallarg(const netbsd32_charp) namebuf; 1616 } */ *uap = v; 1617 struct sys_setlogin_args ua; 1618 1619 NETBSD32TOP_UAP(namebuf, char); 1620 return (sys_setlogin(p, &ua, retval)); 1621 } 1622 1623 int 1624 netbsd32_acct(p, v, retval) 1625 struct proc *p; 1626 void *v; 1627 register_t *retval; 1628 { 1629 struct netbsd32_acct_args /* { 1630 syscallarg(const netbsd32_charp) path; 1631 } */ *uap = v; 1632 struct sys_acct_args ua; 1633 1634 NETBSD32TOP_UAP(path, const char); 1635 return (sys_acct(p, &ua, retval)); 1636 } 1637 1638 int 1639 netbsd32_revoke(p, v, retval) 1640 struct proc *p; 1641 void *v; 1642 register_t *retval; 1643 { 1644 struct netbsd32_revoke_args /* { 1645 syscallarg(const netbsd32_charp) path; 1646 } */ *uap = v; 1647 struct sys_revoke_args ua; 1648 caddr_t sg; 1649 1650 NETBSD32TOP_UAP(path, const char); 1651 sg = stackgap_init(p->p_emul); 1652 NETBSD32_CHECK_ALT_EXIST(p, &sg, SCARG(&ua, path)); 1653 1654 return (sys_revoke(p, &ua, retval)); 1655 } 1656 1657 int 1658 netbsd32_symlink(p, v, retval) 1659 struct proc *p; 1660 void *v; 1661 register_t *retval; 1662 { 1663 struct netbsd32_symlink_args /* { 1664 syscallarg(const netbsd32_charp) path; 1665 syscallarg(const netbsd32_charp) link; 1666 } */ *uap = v; 1667 struct sys_symlink_args ua; 1668 1669 NETBSD32TOP_UAP(path, const char); 1670 NETBSD32TOP_UAP(link, const char); 1671 1672 return (sys_symlink(p, &ua, retval)); 1673 } 1674 1675 int 1676 netbsd32_readlink(p, v, retval) 1677 struct proc *p; 1678 void *v; 1679 register_t *retval; 1680 { 1681 struct netbsd32_readlink_args /* { 1682 syscallarg(const netbsd32_charp) path; 1683 syscallarg(netbsd32_charp) buf; 1684 syscallarg(netbsd32_size_t) count; 1685 } */ *uap = v; 1686 struct sys_readlink_args ua; 1687 caddr_t sg; 1688 1689 NETBSD32TOP_UAP(path, const char); 1690 NETBSD32TOP_UAP(buf, char); 1691 NETBSD32TOX_UAP(count, size_t); 1692 sg = stackgap_init(p->p_emul); 1693 NETBSD32_CHECK_ALT_EXIST(p, &sg, SCARG(&ua, path)); 1694 1695 return (sys_readlink(p, &ua, retval)); 1696 } 1697 1698 int 1699 netbsd32_execve(p, v, retval) 1700 struct proc *p; 1701 void *v; 1702 register_t *retval; 1703 { 1704 struct netbsd32_execve_args /* { 1705 syscallarg(const netbsd32_charp) path; 1706 syscallarg(netbsd32_charpp) argp; 1707 syscallarg(netbsd32_charpp) envp; 1708 } */ *uap = v; 1709 struct sys_execve_args ua; 1710 caddr_t sg; 1711 1712 NETBSD32TOP_UAP(path, const char); 1713 NETBSD32TOP_UAP(argp, char *); 1714 NETBSD32TOP_UAP(envp, char *); 1715 sg = stackgap_init(p->p_emul); 1716 NETBSD32_CHECK_ALT_EXIST(p, &sg, SCARG(&ua, path)); 1717 1718 return (sys_execve(p, &ua, retval)); 1719 } 1720 1721 int 1722 netbsd32_umask(p, v, retval) 1723 struct proc *p; 1724 void *v; 1725 register_t *retval; 1726 { 1727 struct netbsd32_umask_args /* { 1728 syscallarg(mode_t) newmask; 1729 } */ *uap = v; 1730 struct sys_umask_args ua; 1731 1732 NETBSD32TO64_UAP(newmask); 1733 return (sys_umask(p, &ua, retval)); 1734 } 1735 1736 int 1737 netbsd32_chroot(p, v, retval) 1738 struct proc *p; 1739 void *v; 1740 register_t *retval; 1741 { 1742 struct netbsd32_chroot_args /* { 1743 syscallarg(const netbsd32_charp) path; 1744 } */ *uap = v; 1745 struct sys_chroot_args ua; 1746 1747 NETBSD32TOP_UAP(path, const char); 1748 return (sys_chroot(p, &ua, retval)); 1749 } 1750 1751 int 1752 netbsd32_sbrk(p, v, retval) 1753 struct proc *p; 1754 void *v; 1755 register_t *retval; 1756 { 1757 struct netbsd32_sbrk_args /* { 1758 syscallarg(int) incr; 1759 } */ *uap = v; 1760 struct sys_sbrk_args ua; 1761 1762 NETBSD32TO64_UAP(incr); 1763 return (sys_sbrk(p, &ua, retval)); 1764 } 1765 1766 int 1767 netbsd32_sstk(p, v, retval) 1768 struct proc *p; 1769 void *v; 1770 register_t *retval; 1771 { 1772 struct netbsd32_sstk_args /* { 1773 syscallarg(int) incr; 1774 } */ *uap = v; 1775 struct sys_sstk_args ua; 1776 1777 NETBSD32TO64_UAP(incr); 1778 return (sys_sstk(p, &ua, retval)); 1779 } 1780 1781 int 1782 netbsd32_munmap(p, v, retval) 1783 struct proc *p; 1784 void *v; 1785 register_t *retval; 1786 { 1787 struct netbsd32_munmap_args /* { 1788 syscallarg(netbsd32_voidp) addr; 1789 syscallarg(netbsd32_size_t) len; 1790 } */ *uap = v; 1791 struct sys_munmap_args ua; 1792 1793 NETBSD32TOP_UAP(addr, void); 1794 NETBSD32TOX_UAP(len, size_t); 1795 return (sys_munmap(p, &ua, retval)); 1796 } 1797 1798 int 1799 netbsd32_mprotect(p, v, retval) 1800 struct proc *p; 1801 void *v; 1802 register_t *retval; 1803 { 1804 struct netbsd32_mprotect_args /* { 1805 syscallarg(netbsd32_voidp) addr; 1806 syscallarg(netbsd32_size_t) len; 1807 syscallarg(int) prot; 1808 } */ *uap = v; 1809 struct sys_mprotect_args ua; 1810 1811 NETBSD32TOP_UAP(addr, void); 1812 NETBSD32TOX_UAP(len, size_t); 1813 NETBSD32TO64_UAP(prot); 1814 return (sys_mprotect(p, &ua, retval)); 1815 } 1816 1817 int 1818 netbsd32_madvise(p, v, retval) 1819 struct proc *p; 1820 void *v; 1821 register_t *retval; 1822 { 1823 struct netbsd32_madvise_args /* { 1824 syscallarg(netbsd32_voidp) addr; 1825 syscallarg(netbsd32_size_t) len; 1826 syscallarg(int) behav; 1827 } */ *uap = v; 1828 struct sys_madvise_args ua; 1829 1830 NETBSD32TOP_UAP(addr, void); 1831 NETBSD32TOX_UAP(len, size_t); 1832 NETBSD32TO64_UAP(behav); 1833 return (sys_madvise(p, &ua, retval)); 1834 } 1835 1836 int 1837 netbsd32_mincore(p, v, retval) 1838 struct proc *p; 1839 void *v; 1840 register_t *retval; 1841 { 1842 struct netbsd32_mincore_args /* { 1843 syscallarg(netbsd32_caddr_t) addr; 1844 syscallarg(netbsd32_size_t) len; 1845 syscallarg(netbsd32_charp) vec; 1846 } */ *uap = v; 1847 struct sys_mincore_args ua; 1848 1849 NETBSD32TOX64_UAP(addr, caddr_t); 1850 NETBSD32TOX_UAP(len, size_t); 1851 NETBSD32TOP_UAP(vec, char); 1852 return (sys_mincore(p, &ua, retval)); 1853 } 1854 1855 int 1856 netbsd32_getgroups(p, v, retval) 1857 struct proc *p; 1858 void *v; 1859 register_t *retval; 1860 { 1861 struct netbsd32_getgroups_args /* { 1862 syscallarg(int) gidsetsize; 1863 syscallarg(netbsd32_gid_tp) gidset; 1864 } */ *uap = v; 1865 register struct pcred *pc = p->p_cred; 1866 register int ngrp; 1867 int error; 1868 1869 ngrp = SCARG(uap, gidsetsize); 1870 if (ngrp == 0) { 1871 *retval = pc->pc_ucred->cr_ngroups; 1872 return (0); 1873 } 1874 if (ngrp < pc->pc_ucred->cr_ngroups) 1875 return (EINVAL); 1876 ngrp = pc->pc_ucred->cr_ngroups; 1877 /* Should convert gid_t to netbsd32_gid_t, but they're the same */ 1878 error = copyout((caddr_t)pc->pc_ucred->cr_groups, 1879 (caddr_t)(u_long)SCARG(uap, gidset), 1880 ngrp * sizeof(gid_t)); 1881 if (error) 1882 return (error); 1883 *retval = ngrp; 1884 return (0); 1885 } 1886 1887 int 1888 netbsd32_setgroups(p, v, retval) 1889 struct proc *p; 1890 void *v; 1891 register_t *retval; 1892 { 1893 struct netbsd32_setgroups_args /* { 1894 syscallarg(int) gidsetsize; 1895 syscallarg(const netbsd32_gid_tp) gidset; 1896 } */ *uap = v; 1897 struct sys_setgroups_args ua; 1898 1899 NETBSD32TO64_UAP(gidsetsize); 1900 NETBSD32TOP_UAP(gidset, gid_t); 1901 return (sys_setgroups(p, &ua, retval)); 1902 } 1903 1904 int 1905 netbsd32_setpgid(p, v, retval) 1906 struct proc *p; 1907 void *v; 1908 register_t *retval; 1909 { 1910 struct netbsd32_setpgid_args /* { 1911 syscallarg(int) pid; 1912 syscallarg(int) pgid; 1913 } */ *uap = v; 1914 struct sys_setpgid_args ua; 1915 1916 NETBSD32TO64_UAP(pid); 1917 NETBSD32TO64_UAP(pgid); 1918 return (sys_setpgid(p, &ua, retval)); 1919 } 1920 1921 int 1922 netbsd32_setitimer(p, v, retval) 1923 struct proc *p; 1924 void *v; 1925 register_t *retval; 1926 { 1927 struct netbsd32_setitimer_args /* { 1928 syscallarg(int) which; 1929 syscallarg(const netbsd32_itimervalp_t) itv; 1930 syscallarg(netbsd32_itimervalp_t) oitv; 1931 } */ *uap = v; 1932 struct netbsd32_itimerval s32it, *itvp; 1933 int which = SCARG(uap, which); 1934 struct netbsd32_getitimer_args getargs; 1935 struct itimerval aitv; 1936 int s, error; 1937 1938 if ((u_int)which > ITIMER_PROF) 1939 return (EINVAL); 1940 itvp = (struct netbsd32_itimerval *)(u_long)SCARG(uap, itv); 1941 if (itvp && (error = copyin(itvp, &s32it, sizeof(s32it)))) 1942 return (error); 1943 netbsd32_to_itimerval(&s32it, &aitv); 1944 if (SCARG(uap, oitv) != NULL) { 1945 SCARG(&getargs, which) = which; 1946 SCARG(&getargs, itv) = SCARG(uap, oitv); 1947 if ((error = netbsd32_getitimer(p, &getargs, retval)) != 0) 1948 return (error); 1949 } 1950 if (itvp == 0) 1951 return (0); 1952 if (itimerfix(&aitv.it_value) || itimerfix(&aitv.it_interval)) 1953 return (EINVAL); 1954 s = splclock(); 1955 if (which == ITIMER_REAL) { 1956 untimeout(realitexpire, p); 1957 if (timerisset(&aitv.it_value)) { 1958 timeradd(&aitv.it_value, &time, &aitv.it_value); 1959 timeout(realitexpire, p, hzto(&aitv.it_value)); 1960 } 1961 p->p_realtimer = aitv; 1962 } else 1963 p->p_stats->p_timer[which] = aitv; 1964 splx(s); 1965 return (0); 1966 } 1967 1968 int 1969 netbsd32_getitimer(p, v, retval) 1970 struct proc *p; 1971 void *v; 1972 register_t *retval; 1973 { 1974 struct netbsd32_getitimer_args /* { 1975 syscallarg(int) which; 1976 syscallarg(netbsd32_itimervalp_t) itv; 1977 } */ *uap = v; 1978 int which = SCARG(uap, which); 1979 struct netbsd32_itimerval s32it; 1980 struct itimerval aitv; 1981 int s; 1982 1983 if ((u_int)which > ITIMER_PROF) 1984 return (EINVAL); 1985 s = splclock(); 1986 if (which == ITIMER_REAL) { 1987 /* 1988 * Convert from absolute to relative time in .it_value 1989 * part of real time timer. If time for real time timer 1990 * has passed return 0, else return difference between 1991 * current time and time for the timer to go off. 1992 */ 1993 aitv = p->p_realtimer; 1994 if (timerisset(&aitv.it_value)) { 1995 if (timercmp(&aitv.it_value, &time, <)) 1996 timerclear(&aitv.it_value); 1997 else 1998 timersub(&aitv.it_value, &time, &aitv.it_value); 1999 } 2000 } else 2001 aitv = p->p_stats->p_timer[which]; 2002 splx(s); 2003 netbsd32_from_itimerval(&aitv, &s32it); 2004 return (copyout(&s32it, (caddr_t)(u_long)SCARG(uap, itv), sizeof(s32it))); 2005 } 2006 2007 int 2008 netbsd32_fcntl(p, v, retval) 2009 struct proc *p; 2010 void *v; 2011 register_t *retval; 2012 { 2013 struct netbsd32_fcntl_args /* { 2014 syscallarg(int) fd; 2015 syscallarg(int) cmd; 2016 syscallarg(netbsd32_voidp) arg; 2017 } */ *uap = v; 2018 struct sys_fcntl_args ua; 2019 2020 NETBSD32TO64_UAP(fd); 2021 NETBSD32TO64_UAP(cmd); 2022 NETBSD32TOP_UAP(arg, void); 2023 /* XXXX we can do this 'cause flock doesn't change */ 2024 return (sys_fcntl(p, &ua, retval)); 2025 } 2026 2027 int 2028 netbsd32_dup2(p, v, retval) 2029 struct proc *p; 2030 void *v; 2031 register_t *retval; 2032 { 2033 struct netbsd32_dup2_args /* { 2034 syscallarg(int) from; 2035 syscallarg(int) to; 2036 } */ *uap = v; 2037 struct sys_dup2_args ua; 2038 2039 NETBSD32TO64_UAP(from); 2040 NETBSD32TO64_UAP(to); 2041 return (sys_dup2(p, &ua, retval)); 2042 } 2043 2044 int 2045 netbsd32_select(p, v, retval) 2046 struct proc *p; 2047 void *v; 2048 register_t *retval; 2049 { 2050 struct netbsd32_select_args /* { 2051 syscallarg(int) nd; 2052 syscallarg(netbsd32_fd_setp_t) in; 2053 syscallarg(netbsd32_fd_setp_t) ou; 2054 syscallarg(netbsd32_fd_setp_t) ex; 2055 syscallarg(netbsd32_timevalp_t) tv; 2056 } */ *uap = v; 2057 /* This one must be done in-line 'cause of the timeval */ 2058 struct netbsd32_timeval tv32; 2059 caddr_t bits; 2060 char smallbits[howmany(FD_SETSIZE, NFDBITS) * sizeof(fd_mask) * 6]; 2061 struct timeval atv; 2062 int s, ncoll, error = 0, timo; 2063 size_t ni; 2064 extern int selwait, nselcoll; 2065 extern int selscan __P((struct proc *, fd_mask *, fd_mask *, int, register_t *)); 2066 2067 if (SCARG(uap, nd) < 0) 2068 return (EINVAL); 2069 if (SCARG(uap, nd) > p->p_fd->fd_nfiles) { 2070 /* forgiving; slightly wrong */ 2071 SCARG(uap, nd) = p->p_fd->fd_nfiles; 2072 } 2073 ni = howmany(SCARG(uap, nd), NFDBITS) * sizeof(fd_mask); 2074 if (ni * 6 > sizeof(smallbits)) 2075 bits = malloc(ni * 6, M_TEMP, M_WAITOK); 2076 else 2077 bits = smallbits; 2078 2079 #define getbits(name, x) \ 2080 if (SCARG(uap, name)) { \ 2081 error = copyin((caddr_t)(u_long)SCARG(uap, name), bits + ni * x, ni); \ 2082 if (error) \ 2083 goto done; \ 2084 } else \ 2085 memset(bits + ni * x, 0, ni); 2086 getbits(in, 0); 2087 getbits(ou, 1); 2088 getbits(ex, 2); 2089 #undef getbits 2090 2091 if (SCARG(uap, tv)) { 2092 error = copyin((caddr_t)(u_long)SCARG(uap, tv), (caddr_t)&tv32, 2093 sizeof(tv32)); 2094 if (error) 2095 goto done; 2096 netbsd32_to_timeval(&tv32, &atv); 2097 if (itimerfix(&atv)) { 2098 error = EINVAL; 2099 goto done; 2100 } 2101 s = splclock(); 2102 timeradd(&atv, &time, &atv); 2103 timo = hzto(&atv); 2104 /* 2105 * Avoid inadvertently sleeping forever. 2106 */ 2107 if (timo == 0) 2108 timo = 1; 2109 splx(s); 2110 } else 2111 timo = 0; 2112 retry: 2113 ncoll = nselcoll; 2114 p->p_flag |= P_SELECT; 2115 error = selscan(p, (fd_mask *)(bits + ni * 0), 2116 (fd_mask *)(bits + ni * 3), SCARG(uap, nd), retval); 2117 if (error || *retval) 2118 goto done; 2119 s = splhigh(); 2120 if (timo && timercmp(&time, &atv, >=)) { 2121 splx(s); 2122 goto done; 2123 } 2124 if ((p->p_flag & P_SELECT) == 0 || nselcoll != ncoll) { 2125 splx(s); 2126 goto retry; 2127 } 2128 p->p_flag &= ~P_SELECT; 2129 error = tsleep((caddr_t)&selwait, PSOCK | PCATCH, "select", timo); 2130 splx(s); 2131 if (error == 0) 2132 goto retry; 2133 done: 2134 p->p_flag &= ~P_SELECT; 2135 /* select is not restarted after signals... */ 2136 if (error == ERESTART) 2137 error = EINTR; 2138 if (error == EWOULDBLOCK) 2139 error = 0; 2140 if (error == 0) { 2141 #define putbits(name, x) \ 2142 if (SCARG(uap, name)) { \ 2143 error = copyout(bits + ni * x, (caddr_t)(u_long)SCARG(uap, name), ni); \ 2144 if (error) \ 2145 goto out; \ 2146 } 2147 putbits(in, 3); 2148 putbits(ou, 4); 2149 putbits(ex, 5); 2150 #undef putbits 2151 } 2152 out: 2153 if (ni * 6 > sizeof(smallbits)) 2154 free(bits, M_TEMP); 2155 return (error); 2156 } 2157 2158 int 2159 netbsd32_fsync(p, v, retval) 2160 struct proc *p; 2161 void *v; 2162 register_t *retval; 2163 { 2164 struct netbsd32_fsync_args /* { 2165 syscallarg(int) fd; 2166 } */ *uap = v; 2167 struct sys_fsync_args ua; 2168 2169 NETBSD32TO64_UAP(fd); 2170 return (sys_fsync(p, &ua, retval)); 2171 } 2172 2173 int 2174 netbsd32_setpriority(p, v, retval) 2175 struct proc *p; 2176 void *v; 2177 register_t *retval; 2178 { 2179 struct netbsd32_setpriority_args /* { 2180 syscallarg(int) which; 2181 syscallarg(int) who; 2182 syscallarg(int) prio; 2183 } */ *uap = v; 2184 struct sys_setpriority_args ua; 2185 2186 NETBSD32TO64_UAP(which); 2187 NETBSD32TO64_UAP(who); 2188 NETBSD32TO64_UAP(prio); 2189 return (sys_setpriority(p, &ua, retval)); 2190 } 2191 2192 int 2193 netbsd32_socket(p, v, retval) 2194 struct proc *p; 2195 void *v; 2196 register_t *retval; 2197 { 2198 struct netbsd32_socket_args /* { 2199 syscallarg(int) domain; 2200 syscallarg(int) type; 2201 syscallarg(int) protocol; 2202 } */ *uap = v; 2203 struct sys_socket_args ua; 2204 2205 NETBSD32TO64_UAP(domain); 2206 NETBSD32TO64_UAP(type); 2207 NETBSD32TO64_UAP(protocol); 2208 return (sys_socket(p, &ua, retval)); 2209 } 2210 2211 int 2212 netbsd32_connect(p, v, retval) 2213 struct proc *p; 2214 void *v; 2215 register_t *retval; 2216 { 2217 struct netbsd32_connect_args /* { 2218 syscallarg(int) s; 2219 syscallarg(const netbsd32_sockaddrp_t) name; 2220 syscallarg(int) namelen; 2221 } */ *uap = v; 2222 struct sys_connect_args ua; 2223 2224 NETBSD32TO64_UAP(s); 2225 NETBSD32TOP_UAP(name, struct sockaddr); 2226 NETBSD32TO64_UAP(namelen); 2227 return (sys_connect(p, &ua, retval)); 2228 } 2229 2230 int 2231 netbsd32_getpriority(p, v, retval) 2232 struct proc *p; 2233 void *v; 2234 register_t *retval; 2235 { 2236 struct netbsd32_getpriority_args /* { 2237 syscallarg(int) which; 2238 syscallarg(int) who; 2239 } */ *uap = v; 2240 struct sys_getpriority_args ua; 2241 2242 NETBSD32TO64_UAP(which); 2243 NETBSD32TO64_UAP(who); 2244 return (sys_getpriority(p, &ua, retval)); 2245 } 2246 2247 int 2248 netbsd32_bind(p, v, retval) 2249 struct proc *p; 2250 void *v; 2251 register_t *retval; 2252 { 2253 struct netbsd32_bind_args /* { 2254 syscallarg(int) s; 2255 syscallarg(const netbsd32_sockaddrp_t) name; 2256 syscallarg(int) namelen; 2257 } */ *uap = v; 2258 struct sys_bind_args ua; 2259 2260 NETBSD32TO64_UAP(s); 2261 NETBSD32TOP_UAP(name, struct sockaddr); 2262 NETBSD32TO64_UAP(namelen); 2263 return (sys_bind(p, &ua, retval)); 2264 } 2265 2266 int 2267 netbsd32_setsockopt(p, v, retval) 2268 struct proc *p; 2269 void *v; 2270 register_t *retval; 2271 { 2272 struct netbsd32_setsockopt_args /* { 2273 syscallarg(int) s; 2274 syscallarg(int) level; 2275 syscallarg(int) name; 2276 syscallarg(const netbsd32_voidp) val; 2277 syscallarg(int) valsize; 2278 } */ *uap = v; 2279 struct sys_setsockopt_args ua; 2280 2281 NETBSD32TO64_UAP(s); 2282 NETBSD32TO64_UAP(level); 2283 NETBSD32TO64_UAP(name); 2284 NETBSD32TOP_UAP(val, void); 2285 NETBSD32TO64_UAP(valsize); 2286 /* may be more efficient to do this inline. */ 2287 return (sys_setsockopt(p, &ua, retval)); 2288 } 2289 2290 int 2291 netbsd32_listen(p, v, retval) 2292 struct proc *p; 2293 void *v; 2294 register_t *retval; 2295 { 2296 struct netbsd32_listen_args /* { 2297 syscallarg(int) s; 2298 syscallarg(int) backlog; 2299 } */ *uap = v; 2300 struct sys_listen_args ua; 2301 2302 NETBSD32TO64_UAP(s); 2303 NETBSD32TO64_UAP(backlog); 2304 return (sys_listen(p, &ua, retval)); 2305 } 2306 2307 int 2308 netbsd32_gettimeofday(p, v, retval) 2309 struct proc *p; 2310 void *v; 2311 register_t *retval; 2312 { 2313 struct netbsd32_gettimeofday_args /* { 2314 syscallarg(netbsd32_timevalp_t) tp; 2315 syscallarg(netbsd32_timezonep_t) tzp; 2316 } */ *uap = v; 2317 struct timeval atv; 2318 struct netbsd32_timeval tv32; 2319 int error = 0; 2320 struct netbsd32_timezone tzfake; 2321 2322 if (SCARG(uap, tp)) { 2323 microtime(&atv); 2324 netbsd32_from_timeval(&atv, &tv32); 2325 error = copyout(&tv32, (caddr_t)(u_long)SCARG(uap, tp), sizeof(tv32)); 2326 if (error) 2327 return (error); 2328 } 2329 if (SCARG(uap, tzp)) { 2330 /* 2331 * NetBSD has no kernel notion of time zone, so we just 2332 * fake up a timezone struct and return it if demanded. 2333 */ 2334 tzfake.tz_minuteswest = 0; 2335 tzfake.tz_dsttime = 0; 2336 error = copyout(&tzfake, (caddr_t)(u_long)SCARG(uap, tzp), sizeof(tzfake)); 2337 } 2338 return (error); 2339 } 2340 2341 static int settime __P((struct timeval *)); 2342 /* This function is used by clock_settime and settimeofday */ 2343 static int 2344 settime(tv) 2345 struct timeval *tv; 2346 { 2347 struct timeval delta; 2348 int s; 2349 2350 /* WHAT DO WE DO ABOUT PENDING REAL-TIME TIMEOUTS??? */ 2351 s = splclock(); 2352 timersub(tv, &time, &delta); 2353 if ((delta.tv_sec < 0 || delta.tv_usec < 0) && securelevel > 1) 2354 return (EPERM); 2355 #ifdef notyet 2356 if ((delta.tv_sec < 86400) && securelevel > 0) 2357 return (EPERM); 2358 #endif 2359 time = *tv; 2360 (void) spllowersoftclock(); 2361 timeradd(&boottime, &delta, &boottime); 2362 timeradd(&runtime, &delta, &runtime); 2363 # if defined(NFS) || defined(NFSSERVER) 2364 nqnfs_lease_updatetime(delta.tv_sec); 2365 # endif 2366 splx(s); 2367 resettodr(); 2368 return (0); 2369 } 2370 2371 2372 int 2373 netbsd32_settimeofday(p, v, retval) 2374 struct proc *p; 2375 void *v; 2376 register_t *retval; 2377 { 2378 struct netbsd32_settimeofday_args /* { 2379 syscallarg(const netbsd32_timevalp_t) tv; 2380 syscallarg(const netbsd32_timezonep_t) tzp; 2381 } */ *uap = v; 2382 struct netbsd32_timeval atv32; 2383 struct timeval atv; 2384 struct netbsd32_timezone atz; 2385 int error; 2386 2387 if ((error = suser(p->p_ucred, &p->p_acflag)) != 0) 2388 return (error); 2389 /* Verify all parameters before changing time. */ 2390 if (SCARG(uap, tv) && (error = copyin((caddr_t)(u_long)SCARG(uap, tv), 2391 &atv32, sizeof(atv32)))) 2392 return (error); 2393 netbsd32_to_timeval(&atv32, &atv); 2394 /* XXX since we don't use tz, probably no point in doing copyin. */ 2395 if (SCARG(uap, tzp) && (error = copyin((caddr_t)(u_long)SCARG(uap, tzp), 2396 &atz, sizeof(atz)))) 2397 return (error); 2398 if (SCARG(uap, tv)) 2399 if ((error = settime(&atv))) 2400 return (error); 2401 /* 2402 * NetBSD has no kernel notion of time zone, and only an 2403 * obsolete program would try to set it, so we log a warning. 2404 */ 2405 if (SCARG(uap, tzp)) 2406 printf("pid %d attempted to set the " 2407 "(obsolete) kernel time zone\n", p->p_pid); 2408 return (0); 2409 } 2410 2411 int 2412 netbsd32_fchown(p, v, retval) 2413 struct proc *p; 2414 void *v; 2415 register_t *retval; 2416 { 2417 struct netbsd32_fchown_args /* { 2418 syscallarg(int) fd; 2419 syscallarg(uid_t) uid; 2420 syscallarg(gid_t) gid; 2421 } */ *uap = v; 2422 struct sys_fchown_args ua; 2423 2424 NETBSD32TO64_UAP(fd); 2425 NETBSD32TO64_UAP(uid); 2426 NETBSD32TO64_UAP(gid); 2427 return (sys_fchown(p, &ua, retval)); 2428 } 2429 2430 int 2431 netbsd32_fchmod(p, v, retval) 2432 struct proc *p; 2433 void *v; 2434 register_t *retval; 2435 { 2436 struct netbsd32_fchmod_args /* { 2437 syscallarg(int) fd; 2438 syscallarg(mode_t) mode; 2439 } */ *uap = v; 2440 struct sys_fchmod_args ua; 2441 2442 NETBSD32TO64_UAP(fd); 2443 NETBSD32TO64_UAP(mode); 2444 return (sys_fchmod(p, &ua, retval)); 2445 } 2446 2447 int 2448 netbsd32_setreuid(p, v, retval) 2449 struct proc *p; 2450 void *v; 2451 register_t *retval; 2452 { 2453 struct netbsd32_setreuid_args /* { 2454 syscallarg(uid_t) ruid; 2455 syscallarg(uid_t) euid; 2456 } */ *uap = v; 2457 struct sys_setreuid_args ua; 2458 2459 NETBSD32TO64_UAP(ruid); 2460 NETBSD32TO64_UAP(euid); 2461 return (sys_setreuid(p, &ua, retval)); 2462 } 2463 2464 int 2465 netbsd32_setregid(p, v, retval) 2466 struct proc *p; 2467 void *v; 2468 register_t *retval; 2469 { 2470 struct netbsd32_setregid_args /* { 2471 syscallarg(gid_t) rgid; 2472 syscallarg(gid_t) egid; 2473 } */ *uap = v; 2474 struct sys_setregid_args ua; 2475 2476 NETBSD32TO64_UAP(rgid); 2477 NETBSD32TO64_UAP(egid); 2478 return (sys_setregid(p, &ua, retval)); 2479 } 2480 2481 int 2482 netbsd32_getrusage(p, v, retval) 2483 struct proc *p; 2484 void *v; 2485 register_t *retval; 2486 { 2487 struct netbsd32_getrusage_args /* { 2488 syscallarg(int) who; 2489 syscallarg(netbsd32_rusagep_t) rusage; 2490 } */ *uap = v; 2491 struct rusage *rup; 2492 struct netbsd32_rusage ru; 2493 2494 switch (SCARG(uap, who)) { 2495 2496 case RUSAGE_SELF: 2497 rup = &p->p_stats->p_ru; 2498 calcru(p, &rup->ru_utime, &rup->ru_stime, NULL); 2499 break; 2500 2501 case RUSAGE_CHILDREN: 2502 rup = &p->p_stats->p_cru; 2503 break; 2504 2505 default: 2506 return (EINVAL); 2507 } 2508 netbsd32_from_rusage(rup, &ru); 2509 return (copyout(&ru, (caddr_t)(u_long)SCARG(uap, rusage), sizeof(ru))); 2510 } 2511 2512 int 2513 netbsd32_getsockopt(p, v, retval) 2514 struct proc *p; 2515 void *v; 2516 register_t *retval; 2517 { 2518 struct netbsd32_getsockopt_args /* { 2519 syscallarg(int) s; 2520 syscallarg(int) level; 2521 syscallarg(int) name; 2522 syscallarg(netbsd32_voidp) val; 2523 syscallarg(netbsd32_intp) avalsize; 2524 } */ *uap = v; 2525 struct sys_getsockopt_args ua; 2526 2527 NETBSD32TO64_UAP(s); 2528 NETBSD32TO64_UAP(level); 2529 NETBSD32TO64_UAP(name); 2530 NETBSD32TOP_UAP(val, void); 2531 NETBSD32TOP_UAP(avalsize, int); 2532 return (sys_getsockopt(p, &ua, retval)); 2533 } 2534 2535 int 2536 netbsd32_readv(p, v, retval) 2537 struct proc *p; 2538 void *v; 2539 register_t *retval; 2540 { 2541 struct netbsd32_readv_args /* { 2542 syscallarg(int) fd; 2543 syscallarg(const netbsd32_iovecp_t) iovp; 2544 syscallarg(int) iovcnt; 2545 } */ *uap = v; 2546 int fd = SCARG(uap, fd); 2547 register struct file *fp; 2548 register struct filedesc *fdp = p->p_fd; 2549 2550 if ((u_int)fd >= fdp->fd_nfiles || 2551 (fp = fdp->fd_ofiles[fd]) == NULL || 2552 (fp->f_flag & FREAD) == 0) 2553 return (EBADF); 2554 2555 return (dofilereadv32(p, fd, fp, (struct netbsd32_iovec *)(u_long)SCARG(uap, iovp), 2556 SCARG(uap, iovcnt), &fp->f_offset, FOF_UPDATE_OFFSET, retval)); 2557 } 2558 2559 /* Damn thing copies in the iovec! */ 2560 int 2561 dofilereadv32(p, fd, fp, iovp, iovcnt, offset, flags, retval) 2562 struct proc *p; 2563 int fd; 2564 struct file *fp; 2565 struct netbsd32_iovec *iovp; 2566 int iovcnt; 2567 off_t *offset; 2568 int flags; 2569 register_t *retval; 2570 { 2571 struct uio auio; 2572 register struct iovec *iov; 2573 struct iovec *needfree; 2574 struct iovec aiov[UIO_SMALLIOV]; 2575 long i, cnt, error = 0; 2576 u_int iovlen; 2577 #ifdef KTRACE 2578 struct iovec *ktriov = NULL; 2579 #endif 2580 2581 /* note: can't use iovlen until iovcnt is validated */ 2582 iovlen = iovcnt * sizeof(struct iovec); 2583 if ((u_int)iovcnt > UIO_SMALLIOV) { 2584 if ((u_int)iovcnt > IOV_MAX) 2585 return (EINVAL); 2586 MALLOC(iov, struct iovec *, iovlen, M_IOV, M_WAITOK); 2587 needfree = iov; 2588 } else if ((u_int)iovcnt > 0) { 2589 iov = aiov; 2590 needfree = NULL; 2591 } else 2592 return (EINVAL); 2593 2594 auio.uio_iov = iov; 2595 auio.uio_iovcnt = iovcnt; 2596 auio.uio_rw = UIO_READ; 2597 auio.uio_segflg = UIO_USERSPACE; 2598 auio.uio_procp = p; 2599 error = netbsd32_to_iovecin(iovp, iov, iovcnt); 2600 if (error) 2601 goto done; 2602 auio.uio_resid = 0; 2603 for (i = 0; i < iovcnt; i++) { 2604 auio.uio_resid += iov->iov_len; 2605 /* 2606 * Reads return ssize_t because -1 is returned on error. 2607 * Therefore we must restrict the length to SSIZE_MAX to 2608 * avoid garbage return values. 2609 */ 2610 if (iov->iov_len > SSIZE_MAX || auio.uio_resid > SSIZE_MAX) { 2611 error = EINVAL; 2612 goto done; 2613 } 2614 iov++; 2615 } 2616 #ifdef KTRACE 2617 /* 2618 * if tracing, save a copy of iovec 2619 */ 2620 if (KTRPOINT(p, KTR_GENIO)) { 2621 MALLOC(ktriov, struct iovec *, iovlen, M_TEMP, M_WAITOK); 2622 memcpy((caddr_t)ktriov, (caddr_t)auio.uio_iov, iovlen); 2623 } 2624 #endif 2625 cnt = auio.uio_resid; 2626 error = (*fp->f_ops->fo_read)(fp, offset, &auio, fp->f_cred, flags); 2627 if (error) 2628 if (auio.uio_resid != cnt && (error == ERESTART || 2629 error == EINTR || error == EWOULDBLOCK)) 2630 error = 0; 2631 cnt -= auio.uio_resid; 2632 #ifdef KTRACE 2633 if (KTRPOINT(p, KTR_GENIO)) 2634 if (error == 0) { 2635 ktrgenio(p->p_tracep, fd, UIO_READ, ktriov, cnt, 2636 error); 2637 FREE(ktriov, M_TEMP); 2638 } 2639 #endif 2640 *retval = cnt; 2641 done: 2642 if (needfree) 2643 FREE(needfree, M_IOV); 2644 return (error); 2645 } 2646 2647 2648 int 2649 netbsd32_writev(p, v, retval) 2650 struct proc *p; 2651 void *v; 2652 register_t *retval; 2653 { 2654 struct netbsd32_writev_args /* { 2655 syscallarg(int) fd; 2656 syscallarg(const netbsd32_iovecp_t) iovp; 2657 syscallarg(int) iovcnt; 2658 } */ *uap = v; 2659 int fd = SCARG(uap, fd); 2660 register struct file *fp; 2661 register struct filedesc *fdp = p->p_fd; 2662 2663 if ((u_int)fd >= fdp->fd_nfiles || 2664 (fp = fdp->fd_ofiles[fd]) == NULL || 2665 (fp->f_flag & FWRITE) == 0) 2666 return (EBADF); 2667 2668 return (dofilewritev32(p, fd, fp, (struct netbsd32_iovec *)(u_long)SCARG(uap, iovp), 2669 SCARG(uap, iovcnt), &fp->f_offset, FOF_UPDATE_OFFSET, retval)); 2670 } 2671 2672 int 2673 dofilewritev32(p, fd, fp, iovp, iovcnt, offset, flags, retval) 2674 struct proc *p; 2675 int fd; 2676 struct file *fp; 2677 struct netbsd32_iovec *iovp; 2678 int iovcnt; 2679 off_t *offset; 2680 int flags; 2681 register_t *retval; 2682 { 2683 struct uio auio; 2684 register struct iovec *iov; 2685 struct iovec *needfree; 2686 struct iovec aiov[UIO_SMALLIOV]; 2687 long i, cnt, error = 0; 2688 u_int iovlen; 2689 #ifdef KTRACE 2690 struct iovec *ktriov = NULL; 2691 #endif 2692 2693 /* note: can't use iovlen until iovcnt is validated */ 2694 iovlen = iovcnt * sizeof(struct iovec); 2695 if ((u_int)iovcnt > UIO_SMALLIOV) { 2696 if ((u_int)iovcnt > IOV_MAX) 2697 return (EINVAL); 2698 MALLOC(iov, struct iovec *, iovlen, M_IOV, M_WAITOK); 2699 needfree = iov; 2700 } else if ((u_int)iovcnt > 0) { 2701 iov = aiov; 2702 needfree = NULL; 2703 } else 2704 return (EINVAL); 2705 2706 auio.uio_iov = iov; 2707 auio.uio_iovcnt = iovcnt; 2708 auio.uio_rw = UIO_WRITE; 2709 auio.uio_segflg = UIO_USERSPACE; 2710 auio.uio_procp = p; 2711 error = netbsd32_to_iovecin(iovp, iov, iovcnt); 2712 if (error) 2713 goto done; 2714 auio.uio_resid = 0; 2715 for (i = 0; i < iovcnt; i++) { 2716 auio.uio_resid += iov->iov_len; 2717 /* 2718 * Writes return ssize_t because -1 is returned on error. 2719 * Therefore we must restrict the length to SSIZE_MAX to 2720 * avoid garbage return values. 2721 */ 2722 if (iov->iov_len > SSIZE_MAX || auio.uio_resid > SSIZE_MAX) { 2723 error = EINVAL; 2724 goto done; 2725 } 2726 iov++; 2727 } 2728 #ifdef KTRACE 2729 /* 2730 * if tracing, save a copy of iovec 2731 */ 2732 if (KTRPOINT(p, KTR_GENIO)) { 2733 MALLOC(ktriov, struct iovec *, iovlen, M_TEMP, M_WAITOK); 2734 memcpy((caddr_t)ktriov, (caddr_t)auio.uio_iov, iovlen); 2735 } 2736 #endif 2737 cnt = auio.uio_resid; 2738 error = (*fp->f_ops->fo_write)(fp, offset, &auio, fp->f_cred, flags); 2739 if (error) { 2740 if (auio.uio_resid != cnt && (error == ERESTART || 2741 error == EINTR || error == EWOULDBLOCK)) 2742 error = 0; 2743 if (error == EPIPE) 2744 psignal(p, SIGPIPE); 2745 } 2746 cnt -= auio.uio_resid; 2747 #ifdef KTRACE 2748 if (KTRPOINT(p, KTR_GENIO)) 2749 if (error == 0) { 2750 ktrgenio(p->p_tracep, fd, UIO_WRITE, ktriov, cnt, 2751 error); 2752 FREE(ktriov, M_TEMP); 2753 } 2754 #endif 2755 *retval = cnt; 2756 done: 2757 if (needfree) 2758 FREE(needfree, M_IOV); 2759 return (error); 2760 } 2761 2762 2763 int 2764 netbsd32_rename(p, v, retval) 2765 struct proc *p; 2766 void *v; 2767 register_t *retval; 2768 { 2769 struct netbsd32_rename_args /* { 2770 syscallarg(const netbsd32_charp) from; 2771 syscallarg(const netbsd32_charp) to; 2772 } */ *uap = v; 2773 struct sys_rename_args ua; 2774 2775 NETBSD32TOP_UAP(from, const char *); 2776 NETBSD32TOP_UAP(to, const char *) 2777 2778 return (sys_rename(p, &ua, retval)); 2779 } 2780 2781 int 2782 netbsd32_flock(p, v, retval) 2783 struct proc *p; 2784 void *v; 2785 register_t *retval; 2786 { 2787 struct netbsd32_flock_args /* { 2788 syscallarg(int) fd; 2789 syscallarg(int) how; 2790 } */ *uap = v; 2791 struct sys_flock_args ua; 2792 2793 NETBSD32TO64_UAP(fd); 2794 NETBSD32TO64_UAP(how) 2795 2796 return (sys_flock(p, &ua, retval)); 2797 } 2798 2799 int 2800 netbsd32_mkfifo(p, v, retval) 2801 struct proc *p; 2802 void *v; 2803 register_t *retval; 2804 { 2805 struct netbsd32_mkfifo_args /* { 2806 syscallarg(const netbsd32_charp) path; 2807 syscallarg(mode_t) mode; 2808 } */ *uap = v; 2809 struct sys_mkfifo_args ua; 2810 2811 NETBSD32TOP_UAP(path, const char) 2812 NETBSD32TO64_UAP(mode); 2813 return (sys_mkfifo(p, &ua, retval)); 2814 } 2815 2816 int 2817 netbsd32_shutdown(p, v, retval) 2818 struct proc *p; 2819 void *v; 2820 register_t *retval; 2821 { 2822 struct netbsd32_shutdown_args /* { 2823 syscallarg(int) s; 2824 syscallarg(int) how; 2825 } */ *uap = v; 2826 struct sys_shutdown_args ua; 2827 2828 NETBSD32TO64_UAP(s) 2829 NETBSD32TO64_UAP(how); 2830 return (sys_shutdown(p, &ua, retval)); 2831 } 2832 2833 int 2834 netbsd32_socketpair(p, v, retval) 2835 struct proc *p; 2836 void *v; 2837 register_t *retval; 2838 { 2839 struct netbsd32_socketpair_args /* { 2840 syscallarg(int) domain; 2841 syscallarg(int) type; 2842 syscallarg(int) protocol; 2843 syscallarg(netbsd32_intp) rsv; 2844 } */ *uap = v; 2845 struct sys_socketpair_args ua; 2846 2847 NETBSD32TO64_UAP(domain); 2848 NETBSD32TO64_UAP(type); 2849 NETBSD32TO64_UAP(protocol); 2850 NETBSD32TOP_UAP(rsv, int); 2851 /* Since we're just copying out two `int's we can do this */ 2852 return (sys_socketpair(p, &ua, retval)); 2853 } 2854 2855 int 2856 netbsd32_mkdir(p, v, retval) 2857 struct proc *p; 2858 void *v; 2859 register_t *retval; 2860 { 2861 struct netbsd32_mkdir_args /* { 2862 syscallarg(const netbsd32_charp) path; 2863 syscallarg(mode_t) mode; 2864 } */ *uap = v; 2865 struct sys_mkdir_args ua; 2866 2867 NETBSD32TOP_UAP(path, const char) 2868 NETBSD32TO64_UAP(mode); 2869 return (sys_mkdir(p, &ua, retval)); 2870 } 2871 2872 int 2873 netbsd32_rmdir(p, v, retval) 2874 struct proc *p; 2875 void *v; 2876 register_t *retval; 2877 { 2878 struct netbsd32_rmdir_args /* { 2879 syscallarg(const netbsd32_charp) path; 2880 } */ *uap = v; 2881 struct sys_rmdir_args ua; 2882 2883 NETBSD32TOP_UAP(path, const char); 2884 return (sys_rmdir(p, &ua, retval)); 2885 } 2886 2887 int 2888 netbsd32_utimes(p, v, retval) 2889 struct proc *p; 2890 void *v; 2891 register_t *retval; 2892 { 2893 struct netbsd32_utimes_args /* { 2894 syscallarg(const netbsd32_charp) path; 2895 syscallarg(const netbsd32_timevalp_t) tptr; 2896 } */ *uap = v; 2897 int error; 2898 struct nameidata nd; 2899 2900 NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, (char *)(u_long)SCARG(uap, path), p); 2901 if ((error = namei(&nd)) != 0) 2902 return (error); 2903 2904 error = change_utimes32(nd.ni_vp, (struct timeval *)(u_long)SCARG(uap, tptr), p); 2905 2906 vrele(nd.ni_vp); 2907 return (error); 2908 } 2909 2910 /* 2911 * Common routine to set access and modification times given a vnode. 2912 */ 2913 static int 2914 change_utimes32(vp, tptr, p) 2915 struct vnode *vp; 2916 struct timeval *tptr; 2917 struct proc *p; 2918 { 2919 struct netbsd32_timeval tv32[2]; 2920 struct timeval tv[2]; 2921 struct vattr vattr; 2922 int error; 2923 2924 VATTR_NULL(&vattr); 2925 if (tptr == NULL) { 2926 microtime(&tv[0]); 2927 tv[1] = tv[0]; 2928 vattr.va_vaflags |= VA_UTIMES_NULL; 2929 } else { 2930 error = copyin(tptr, tv, sizeof(tv)); 2931 if (error) 2932 return (error); 2933 } 2934 netbsd32_to_timeval(&tv32[0], &tv[0]); 2935 netbsd32_to_timeval(&tv32[1], &tv[1]); 2936 VOP_LEASE(vp, p, p->p_ucred, LEASE_WRITE); 2937 vn_lock(vp, LK_EXCLUSIVE | LK_RETRY); 2938 vattr.va_atime.tv_sec = tv[0].tv_sec; 2939 vattr.va_atime.tv_nsec = tv[0].tv_usec * 1000; 2940 vattr.va_mtime.tv_sec = tv[1].tv_sec; 2941 vattr.va_mtime.tv_nsec = tv[1].tv_usec * 1000; 2942 error = VOP_SETATTR(vp, &vattr, p->p_ucred, p); 2943 VOP_UNLOCK(vp, 0); 2944 return (error); 2945 } 2946 2947 int 2948 netbsd32_adjtime(p, v, retval) 2949 struct proc *p; 2950 void *v; 2951 register_t *retval; 2952 { 2953 struct netbsd32_adjtime_args /* { 2954 syscallarg(const netbsd32_timevalp_t) delta; 2955 syscallarg(netbsd32_timevalp_t) olddelta; 2956 } */ *uap = v; 2957 struct netbsd32_timeval atv; 2958 int32_t ndelta, ntickdelta, odelta; 2959 int s, error; 2960 extern long bigadj, timedelta; 2961 extern int tickdelta; 2962 2963 if ((error = suser(p->p_ucred, &p->p_acflag)) != 0) 2964 return (error); 2965 2966 error = copyin((caddr_t)(u_long)SCARG(uap, delta), &atv, sizeof(struct timeval)); 2967 if (error) 2968 return (error); 2969 /* 2970 * Compute the total correction and the rate at which to apply it. 2971 * Round the adjustment down to a whole multiple of the per-tick 2972 * delta, so that after some number of incremental changes in 2973 * hardclock(), tickdelta will become zero, lest the correction 2974 * overshoot and start taking us away from the desired final time. 2975 */ 2976 ndelta = atv.tv_sec * 1000000 + atv.tv_usec; 2977 if (ndelta > bigadj) 2978 ntickdelta = 10 * tickadj; 2979 else 2980 ntickdelta = tickadj; 2981 if (ndelta % ntickdelta) 2982 ndelta = ndelta / ntickdelta * ntickdelta; 2983 2984 /* 2985 * To make hardclock()'s job easier, make the per-tick delta negative 2986 * if we want time to run slower; then hardclock can simply compute 2987 * tick + tickdelta, and subtract tickdelta from timedelta. 2988 */ 2989 if (ndelta < 0) 2990 ntickdelta = -ntickdelta; 2991 s = splclock(); 2992 odelta = timedelta; 2993 timedelta = ndelta; 2994 tickdelta = ntickdelta; 2995 splx(s); 2996 2997 if (SCARG(uap, olddelta)) { 2998 atv.tv_sec = odelta / 1000000; 2999 atv.tv_usec = odelta % 1000000; 3000 (void) copyout(&atv, (caddr_t)(u_long)SCARG(uap, olddelta), 3001 sizeof(struct timeval)); 3002 } 3003 return (0); 3004 } 3005 3006 int 3007 netbsd32_quotactl(p, v, retval) 3008 struct proc *p; 3009 void *v; 3010 register_t *retval; 3011 { 3012 struct netbsd32_quotactl_args /* { 3013 syscallarg(const netbsd32_charp) path; 3014 syscallarg(int) cmd; 3015 syscallarg(int) uid; 3016 syscallarg(netbsd32_caddr_t) arg; 3017 } */ *uap = v; 3018 struct sys_quotactl_args ua; 3019 3020 NETBSD32TOP_UAP(path, const char); 3021 NETBSD32TO64_UAP(cmd); 3022 NETBSD32TO64_UAP(uid); 3023 NETBSD32TOX64_UAP(arg, caddr_t); 3024 return (sys_quotactl(p, &ua, retval)); 3025 } 3026 3027 #if defined(NFS) || defined(NFSSERVER) 3028 int 3029 netbsd32_nfssvc(p, v, retval) 3030 struct proc *p; 3031 void *v; 3032 register_t *retval; 3033 { 3034 #if 0 3035 struct netbsd32_nfssvc_args /* { 3036 syscallarg(int) flag; 3037 syscallarg(netbsd32_voidp) argp; 3038 } */ *uap = v; 3039 struct sys_nfssvc_args ua; 3040 3041 NETBSD32TO64_UAP(flag); 3042 NETBSD32TOP_UAP(argp, void); 3043 return (sys_nfssvc(p, &ua, retval)); 3044 #else 3045 /* Why would we want to support a 32-bit nfsd? */ 3046 return (ENOSYS); 3047 #endif 3048 } 3049 #endif 3050 3051 int 3052 netbsd32_statfs(p, v, retval) 3053 struct proc *p; 3054 void *v; 3055 register_t *retval; 3056 { 3057 struct netbsd32_statfs_args /* { 3058 syscallarg(const netbsd32_charp) path; 3059 syscallarg(netbsd32_statfsp_t) buf; 3060 } */ *uap = v; 3061 register struct mount *mp; 3062 register struct statfs *sp; 3063 struct netbsd32_statfs s32; 3064 int error; 3065 struct nameidata nd; 3066 3067 NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, (char *)(u_long)SCARG(uap, path), p); 3068 if ((error = namei(&nd)) != 0) 3069 return (error); 3070 mp = nd.ni_vp->v_mount; 3071 sp = &mp->mnt_stat; 3072 vrele(nd.ni_vp); 3073 if ((error = VFS_STATFS(mp, sp, p)) != 0) 3074 return (error); 3075 sp->f_flags = mp->mnt_flag & MNT_VISFLAGMASK; 3076 netbsd32_from_statfs(sp, &s32); 3077 return (copyout(&s32, (caddr_t)(u_long)SCARG(uap, buf), sizeof(s32))); 3078 } 3079 3080 int 3081 netbsd32_fstatfs(p, v, retval) 3082 struct proc *p; 3083 void *v; 3084 register_t *retval; 3085 { 3086 struct netbsd32_fstatfs_args /* { 3087 syscallarg(int) fd; 3088 syscallarg(netbsd32_statfsp_t) buf; 3089 } */ *uap = v; 3090 struct file *fp; 3091 register struct mount *mp; 3092 register struct statfs *sp; 3093 struct netbsd32_statfs s32; 3094 int error; 3095 3096 /* getvnode() will use the descriptor for us */ 3097 if ((error = getvnode(p->p_fd, SCARG(uap, fd), &fp)) != 0) 3098 return (error); 3099 mp = ((struct vnode *)fp->f_data)->v_mount; 3100 sp = &mp->mnt_stat; 3101 if ((error = VFS_STATFS(mp, sp, p)) != 0) 3102 goto out; 3103 sp->f_flags = mp->mnt_flag & MNT_VISFLAGMASK; 3104 netbsd32_from_statfs(sp, &s32); 3105 error = copyout(&s32, (caddr_t)(u_long)SCARG(uap, buf), sizeof(s32)); 3106 out: 3107 FILE_UNUSE(fp, p); 3108 return (error); 3109 } 3110 3111 #if defined(NFS) || defined(NFSSERVER) 3112 int 3113 netbsd32_getfh(p, v, retval) 3114 struct proc *p; 3115 void *v; 3116 register_t *retval; 3117 { 3118 struct netbsd32_getfh_args /* { 3119 syscallarg(const netbsd32_charp) fname; 3120 syscallarg(netbsd32_fhandlep_t) fhp; 3121 } */ *uap = v; 3122 struct sys_getfh_args ua; 3123 3124 NETBSD32TOP_UAP(fname, const char); 3125 NETBSD32TOP_UAP(fhp, struct fhandle); 3126 /* Lucky for us a fhandlep_t doesn't change sizes */ 3127 return (sys_getfh(p, &ua, retval)); 3128 } 3129 #endif 3130 3131 int 3132 netbsd32_sysarch(p, v, retval) 3133 struct proc *p; 3134 void *v; 3135 register_t *retval; 3136 { 3137 struct netbsd32_sysarch_args /* { 3138 syscallarg(int) op; 3139 syscallarg(netbsd32_voidp) parms; 3140 } */ *uap = v; 3141 3142 switch (SCARG(uap, op)) { 3143 default: 3144 printf("(sparc64) netbsd32_sysarch(%d)\n", SCARG(uap, op)); 3145 return EINVAL; 3146 } 3147 } 3148 3149 int 3150 netbsd32_pread(p, v, retval) 3151 struct proc *p; 3152 void *v; 3153 register_t *retval; 3154 { 3155 struct netbsd32_pread_args /* { 3156 syscallarg(int) fd; 3157 syscallarg(netbsd32_voidp) buf; 3158 syscallarg(netbsd32_size_t) nbyte; 3159 syscallarg(int) pad; 3160 syscallarg(off_t) offset; 3161 } */ *uap = v; 3162 struct sys_pread_args ua; 3163 ssize_t rt; 3164 int error; 3165 3166 NETBSD32TO64_UAP(fd); 3167 NETBSD32TOP_UAP(buf, void); 3168 NETBSD32TOX_UAP(nbyte, size_t); 3169 NETBSD32TO64_UAP(pad); 3170 NETBSD32TO64_UAP(offset); 3171 error = sys_pread(p, &ua, (register_t *)&rt); 3172 *(netbsd32_ssize_t *)retval = rt; 3173 return (error); 3174 } 3175 3176 int 3177 netbsd32_pwrite(p, v, retval) 3178 struct proc *p; 3179 void *v; 3180 register_t *retval; 3181 { 3182 struct netbsd32_pwrite_args /* { 3183 syscallarg(int) fd; 3184 syscallarg(const netbsd32_voidp) buf; 3185 syscallarg(netbsd32_size_t) nbyte; 3186 syscallarg(int) pad; 3187 syscallarg(off_t) offset; 3188 } */ *uap = v; 3189 struct sys_pwrite_args ua; 3190 ssize_t rt; 3191 int error; 3192 3193 NETBSD32TO64_UAP(fd); 3194 NETBSD32TOP_UAP(buf, void); 3195 NETBSD32TOX_UAP(nbyte, size_t); 3196 NETBSD32TO64_UAP(pad); 3197 NETBSD32TO64_UAP(offset); 3198 error = sys_pwrite(p, &ua, (register_t *)&rt); 3199 *(netbsd32_ssize_t *)retval = rt; 3200 return (error); 3201 } 3202 3203 #ifdef NTP 3204 int 3205 netbsd32_ntp_gettime(p, v, retval) 3206 struct proc *p; 3207 void *v; 3208 register_t *retval; 3209 { 3210 struct netbsd32_ntp_gettime_args /* { 3211 syscallarg(netbsd32_ntptimevalp_t) ntvp; 3212 } */ *uap = v; 3213 struct netbsd32_ntptimeval ntv32; 3214 struct timeval atv; 3215 struct ntptimeval ntv; 3216 int error = 0; 3217 int s; 3218 3219 /* The following are NTP variables */ 3220 extern long time_maxerror; 3221 extern long time_esterror; 3222 extern int time_status; 3223 extern int time_state; /* clock state */ 3224 extern int time_status; /* clock status bits */ 3225 3226 if (SCARG(uap, ntvp)) { 3227 s = splclock(); 3228 #ifdef EXT_CLOCK 3229 /* 3230 * The microtime() external clock routine returns a 3231 * status code. If less than zero, we declare an error 3232 * in the clock status word and return the kernel 3233 * (software) time variable. While there are other 3234 * places that call microtime(), this is the only place 3235 * that matters from an application point of view. 3236 */ 3237 if (microtime(&atv) < 0) { 3238 time_status |= STA_CLOCKERR; 3239 ntv.time = time; 3240 } else 3241 time_status &= ~STA_CLOCKERR; 3242 #else /* EXT_CLOCK */ 3243 microtime(&atv); 3244 #endif /* EXT_CLOCK */ 3245 ntv.time = atv; 3246 ntv.maxerror = time_maxerror; 3247 ntv.esterror = time_esterror; 3248 (void) splx(s); 3249 3250 netbsd32_from_timeval(&ntv.time, &ntv32.time); 3251 ntv32.maxerror = (netbsd32_long)ntv.maxerror; 3252 ntv32.esterror = (netbsd32_long)ntv.esterror; 3253 error = copyout((caddr_t)&ntv32, (caddr_t)(u_long)SCARG(uap, ntvp), 3254 sizeof(ntv32)); 3255 } 3256 if (!error) { 3257 3258 /* 3259 * Status word error decode. If any of these conditions 3260 * occur, an error is returned, instead of the status 3261 * word. Most applications will care only about the fact 3262 * the system clock may not be trusted, not about the 3263 * details. 3264 * 3265 * Hardware or software error 3266 */ 3267 if ((time_status & (STA_UNSYNC | STA_CLOCKERR)) || 3268 3269 /* 3270 * PPS signal lost when either time or frequency 3271 * synchronization requested 3272 */ 3273 (time_status & (STA_PPSFREQ | STA_PPSTIME) && 3274 !(time_status & STA_PPSSIGNAL)) || 3275 3276 /* 3277 * PPS jitter exceeded when time synchronization 3278 * requested 3279 */ 3280 (time_status & STA_PPSTIME && 3281 time_status & STA_PPSJITTER) || 3282 3283 /* 3284 * PPS wander exceeded or calibration error when 3285 * frequency synchronization requested 3286 */ 3287 (time_status & STA_PPSFREQ && 3288 time_status & (STA_PPSWANDER | STA_PPSERROR))) 3289 *retval = TIME_ERROR; 3290 else 3291 *retval = (register_t)time_state; 3292 } 3293 return(error); 3294 } 3295 3296 int 3297 netbsd32_ntp_adjtime(p, v, retval) 3298 struct proc *p; 3299 void *v; 3300 register_t *retval; 3301 { 3302 struct netbsd32_ntp_adjtime_args /* { 3303 syscallarg(netbsd32_timexp_t) tp; 3304 } */ *uap = v; 3305 struct netbsd32_timex ntv32; 3306 struct timex ntv; 3307 int error = 0; 3308 int modes; 3309 int s; 3310 extern long time_freq; /* frequency offset (scaled ppm) */ 3311 extern long time_maxerror; 3312 extern long time_esterror; 3313 extern int time_state; /* clock state */ 3314 extern int time_status; /* clock status bits */ 3315 extern long time_constant; /* pll time constant */ 3316 extern long time_offset; /* time offset (us) */ 3317 extern long time_tolerance; /* frequency tolerance (scaled ppm) */ 3318 extern long time_precision; /* clock precision (us) */ 3319 3320 if ((error = copyin((caddr_t)(u_long)SCARG(uap, tp), (caddr_t)&ntv32, 3321 sizeof(ntv32)))) 3322 return (error); 3323 netbsd32_to_timex(&ntv32, &ntv); 3324 3325 /* 3326 * Update selected clock variables - only the superuser can 3327 * change anything. Note that there is no error checking here on 3328 * the assumption the superuser should know what it is doing. 3329 */ 3330 modes = ntv.modes; 3331 if (modes != 0 && (error = suser(p->p_ucred, &p->p_acflag))) 3332 return (error); 3333 3334 s = splclock(); 3335 if (modes & MOD_FREQUENCY) 3336 #ifdef PPS_SYNC 3337 time_freq = ntv.freq - pps_freq; 3338 #else /* PPS_SYNC */ 3339 time_freq = ntv.freq; 3340 #endif /* PPS_SYNC */ 3341 if (modes & MOD_MAXERROR) 3342 time_maxerror = ntv.maxerror; 3343 if (modes & MOD_ESTERROR) 3344 time_esterror = ntv.esterror; 3345 if (modes & MOD_STATUS) { 3346 time_status &= STA_RONLY; 3347 time_status |= ntv.status & ~STA_RONLY; 3348 } 3349 if (modes & MOD_TIMECONST) 3350 time_constant = ntv.constant; 3351 if (modes & MOD_OFFSET) 3352 hardupdate(ntv.offset); 3353 3354 /* 3355 * Retrieve all clock variables 3356 */ 3357 if (time_offset < 0) 3358 ntv.offset = -(-time_offset >> SHIFT_UPDATE); 3359 else 3360 ntv.offset = time_offset >> SHIFT_UPDATE; 3361 #ifdef PPS_SYNC 3362 ntv.freq = time_freq + pps_freq; 3363 #else /* PPS_SYNC */ 3364 ntv.freq = time_freq; 3365 #endif /* PPS_SYNC */ 3366 ntv.maxerror = time_maxerror; 3367 ntv.esterror = time_esterror; 3368 ntv.status = time_status; 3369 ntv.constant = time_constant; 3370 ntv.precision = time_precision; 3371 ntv.tolerance = time_tolerance; 3372 #ifdef PPS_SYNC 3373 ntv.shift = pps_shift; 3374 ntv.ppsfreq = pps_freq; 3375 ntv.jitter = pps_jitter >> PPS_AVG; 3376 ntv.stabil = pps_stabil; 3377 ntv.calcnt = pps_calcnt; 3378 ntv.errcnt = pps_errcnt; 3379 ntv.jitcnt = pps_jitcnt; 3380 ntv.stbcnt = pps_stbcnt; 3381 #endif /* PPS_SYNC */ 3382 (void)splx(s); 3383 3384 netbsd32_from_timeval(&ntv, &ntv32); 3385 error = copyout((caddr_t)&ntv32, (caddr_t)SCARG(uap, tp), sizeof(ntv32)); 3386 if (!error) { 3387 3388 /* 3389 * Status word error decode. See comments in 3390 * ntp_gettime() routine. 3391 */ 3392 if ((time_status & (STA_UNSYNC | STA_CLOCKERR)) || 3393 (time_status & (STA_PPSFREQ | STA_PPSTIME) && 3394 !(time_status & STA_PPSSIGNAL)) || 3395 (time_status & STA_PPSTIME && 3396 time_status & STA_PPSJITTER) || 3397 (time_status & STA_PPSFREQ && 3398 time_status & (STA_PPSWANDER | STA_PPSERROR))) 3399 *retval = TIME_ERROR; 3400 else 3401 *retval = (register_t)time_state; 3402 } 3403 return error; 3404 } 3405 #endif 3406 3407 int 3408 netbsd32_setgid(p, v, retval) 3409 struct proc *p; 3410 void *v; 3411 register_t *retval; 3412 { 3413 struct netbsd32_setgid_args /* { 3414 syscallarg(gid_t) gid; 3415 } */ *uap = v; 3416 struct sys_setgid_args ua; 3417 3418 NETBSD32TO64_UAP(gid); 3419 return (sys_setgid(p, v, retval)); 3420 } 3421 3422 int 3423 netbsd32_setegid(p, v, retval) 3424 struct proc *p; 3425 void *v; 3426 register_t *retval; 3427 { 3428 struct netbsd32_setegid_args /* { 3429 syscallarg(gid_t) egid; 3430 } */ *uap = v; 3431 struct sys_setegid_args ua; 3432 3433 NETBSD32TO64_UAP(egid); 3434 return (sys_setegid(p, v, retval)); 3435 } 3436 3437 int 3438 netbsd32_seteuid(p, v, retval) 3439 struct proc *p; 3440 void *v; 3441 register_t *retval; 3442 { 3443 struct netbsd32_seteuid_args /* { 3444 syscallarg(gid_t) euid; 3445 } */ *uap = v; 3446 struct sys_seteuid_args ua; 3447 3448 NETBSD32TO64_UAP(euid); 3449 return (sys_seteuid(p, v, retval)); 3450 } 3451 3452 #ifdef LFS 3453 int 3454 netbsd32_lfs_bmapv(p, v, retval) 3455 struct proc *p; 3456 void *v; 3457 register_t *retval; 3458 { 3459 #if 0 3460 struct netbsd32_lfs_bmapv_args /* { 3461 syscallarg(netbsd32_fsid_tp_t) fsidp; 3462 syscallarg(netbsd32_block_infop_t) blkiov; 3463 syscallarg(int) blkcnt; 3464 } */ *uap = v; 3465 struct sys_lfs_bmapv_args ua; 3466 3467 NETBSD32TOP_UAP(fdidp, struct fsid); 3468 NETBSD32TO64_UAP(blkcnt); 3469 /* XXX finish me */ 3470 #else 3471 3472 return (ENOSYS); /* XXX */ 3473 #endif 3474 } 3475 3476 int 3477 netbsd32_lfs_markv(p, v, retval) 3478 struct proc *p; 3479 void *v; 3480 register_t *retval; 3481 { 3482 struct netbsd32_lfs_markv_args /* { 3483 syscallarg(netbsd32_fsid_tp_t) fsidp; 3484 syscallarg(netbsd32_block_infop_t) blkiov; 3485 syscallarg(int) blkcnt; 3486 } */ *uap = v; 3487 3488 return (ENOSYS); /* XXX */ 3489 } 3490 3491 int 3492 netbsd32_lfs_segclean(p, v, retval) 3493 struct proc *p; 3494 void *v; 3495 register_t *retval; 3496 { 3497 struct netbsd32_lfs_segclean_args /* { 3498 syscallarg(netbsd32_fsid_tp_t) fsidp; 3499 syscallarg(netbsd32_u_long) segment; 3500 } */ *uap = v; 3501 return (ENOSYS); /* XXX */ 3502 } 3503 3504 int 3505 netbsd32_lfs_segwait(p, v, retval) 3506 struct proc *p; 3507 void *v; 3508 register_t *retval; 3509 { 3510 struct netbsd32_lfs_segwait_args /* { 3511 syscallarg(netbsd32_fsid_tp_t) fsidp; 3512 syscallarg(netbsd32_timevalp_t) tv; 3513 } */ *uap = v; 3514 return (ENOSYS); /* XXX */ 3515 } 3516 #endif 3517 3518 int 3519 netbsd32_pathconf(p, v, retval) 3520 struct proc *p; 3521 void *v; 3522 register_t *retval; 3523 { 3524 struct netbsd32_pathconf_args /* { 3525 syscallarg(int) fd; 3526 syscallarg(int) name; 3527 } */ *uap = v; 3528 struct sys_pathconf_args ua; 3529 long rt; 3530 int error; 3531 3532 NETBSD32TOP_UAP(path, const char); 3533 NETBSD32TO64_UAP(name); 3534 error = sys_pathconf(p, &ua, (register_t *)&rt); 3535 *(netbsd32_long *)retval = (netbsd32_long)rt; 3536 return (error); 3537 } 3538 3539 int 3540 netbsd32_fpathconf(p, v, retval) 3541 struct proc *p; 3542 void *v; 3543 register_t *retval; 3544 { 3545 struct netbsd32_fpathconf_args /* { 3546 syscallarg(int) fd; 3547 syscallarg(int) name; 3548 } */ *uap = v; 3549 struct sys_fpathconf_args ua; 3550 long rt; 3551 int error; 3552 3553 NETBSD32TO64_UAP(fd); 3554 NETBSD32TO64_UAP(name); 3555 error = sys_fpathconf(p, &ua, (register_t *)&rt); 3556 *(netbsd32_long *)retval = (netbsd32_long)rt; 3557 return (error); 3558 } 3559 3560 int 3561 netbsd32_getrlimit(p, v, retval) 3562 struct proc *p; 3563 void *v; 3564 register_t *retval; 3565 { 3566 struct netbsd32_getrlimit_args /* { 3567 syscallarg(int) which; 3568 syscallarg(netbsd32_rlimitp_t) rlp; 3569 } */ *uap = v; 3570 int which = SCARG(uap, which); 3571 3572 if ((u_int)which >= RLIM_NLIMITS) 3573 return (EINVAL); 3574 return (copyout(&p->p_rlimit[which], (caddr_t)(u_long)SCARG(uap, rlp), 3575 sizeof(struct rlimit))); 3576 } 3577 3578 int 3579 netbsd32_setrlimit(p, v, retval) 3580 struct proc *p; 3581 void *v; 3582 register_t *retval; 3583 { 3584 struct netbsd32_setrlimit_args /* { 3585 syscallarg(int) which; 3586 syscallarg(const netbsd32_rlimitp_t) rlp; 3587 } */ *uap = v; 3588 int which = SCARG(uap, which); 3589 struct rlimit alim; 3590 int error; 3591 3592 error = copyin((caddr_t)(u_long)SCARG(uap, rlp), &alim, sizeof(struct rlimit)); 3593 if (error) 3594 return (error); 3595 return (dosetrlimit(p, p->p_cred, which, &alim)); 3596 } 3597 3598 int 3599 netbsd32_mmap(p, v, retval) 3600 struct proc *p; 3601 void *v; 3602 register_t *retval; 3603 { 3604 struct netbsd32_mmap_args /* { 3605 syscallarg(netbsd32_voidp) addr; 3606 syscallarg(netbsd32_size_t) len; 3607 syscallarg(int) prot; 3608 syscallarg(int) flags; 3609 syscallarg(int) fd; 3610 syscallarg(netbsd32_long) pad; 3611 syscallarg(off_t) pos; 3612 } */ *uap = v; 3613 struct sys_mmap_args ua; 3614 void *rt; 3615 int error; 3616 3617 NETBSD32TOP_UAP(addr, void); 3618 NETBSD32TOX_UAP(len, size_t); 3619 NETBSD32TO64_UAP(prot); 3620 NETBSD32TO64_UAP(flags); 3621 NETBSD32TO64_UAP(fd); 3622 NETBSD32TOX_UAP(pad, long); 3623 NETBSD32TOX_UAP(pos, off_t); 3624 error = sys_mmap(p, &ua, (register_t *)&rt); 3625 if ((long)rt > (long)UINT_MAX) 3626 printf("netbsd32_mmap: retval out of range: 0x%qx", 3627 rt); 3628 *retval = (netbsd32_voidp)(u_long)rt; 3629 return (error); 3630 } 3631 3632 int 3633 netbsd32_lseek(p, v, retval) 3634 struct proc *p; 3635 void *v; 3636 register_t *retval; 3637 { 3638 struct netbsd32_lseek_args /* { 3639 syscallarg(int) fd; 3640 syscallarg(int) pad; 3641 syscallarg(off_t) offset; 3642 syscallarg(int) whence; 3643 } */ *uap = v; 3644 struct sys_lseek_args ua; 3645 3646 NETBSD32TO64_UAP(fd); 3647 NETBSD32TO64_UAP(pad); 3648 NETBSD32TO64_UAP(offset); 3649 NETBSD32TO64_UAP(whence); 3650 return (sys_lseek(p, &ua, retval)); 3651 } 3652 3653 int 3654 netbsd32_truncate(p, v, retval) 3655 struct proc *p; 3656 void *v; 3657 register_t *retval; 3658 { 3659 struct netbsd32_truncate_args /* { 3660 syscallarg(const netbsd32_charp) path; 3661 syscallarg(int) pad; 3662 syscallarg(off_t) length; 3663 } */ *uap = v; 3664 struct sys_truncate_args ua; 3665 3666 NETBSD32TOP_UAP(path, const char); 3667 NETBSD32TO64_UAP(pad); 3668 NETBSD32TO64_UAP(length); 3669 return (sys_truncate(p, &ua, retval)); 3670 } 3671 3672 int 3673 netbsd32_ftruncate(p, v, retval) 3674 struct proc *p; 3675 void *v; 3676 register_t *retval; 3677 { 3678 struct netbsd32_ftruncate_args /* { 3679 syscallarg(int) fd; 3680 syscallarg(int) pad; 3681 syscallarg(off_t) length; 3682 } */ *uap = v; 3683 struct sys_ftruncate_args ua; 3684 3685 NETBSD32TO64_UAP(fd); 3686 NETBSD32TO64_UAP(pad); 3687 NETBSD32TO64_UAP(length); 3688 return (sys_ftruncate(p, &ua, retval)); 3689 } 3690 3691 int 3692 netbsd32___sysctl(p, v, retval) 3693 struct proc *p; 3694 void *v; 3695 register_t *retval; 3696 { 3697 struct netbsd32___sysctl_args /* { 3698 syscallarg(netbsd32_intp) name; 3699 syscallarg(u_int) namelen; 3700 syscallarg(netbsd32_voidp) old; 3701 syscallarg(netbsd32_size_tp) oldlenp; 3702 syscallarg(netbsd32_voidp) new; 3703 syscallarg(netbsd32_size_t) newlen; 3704 } */ *uap = v; 3705 int error, dolock = 1; 3706 netbsd32_size_t savelen = 0; 3707 size_t oldlen = 0; 3708 sysctlfn *fn; 3709 int name[CTL_MAXNAME]; 3710 3711 /* 3712 * Some of these sysctl functions do their own copyin/copyout. 3713 * We need to disable or emulate the ones that need their 3714 * arguments converted. 3715 */ 3716 3717 if (SCARG(uap, new) != NULL && 3718 (error = suser(p->p_ucred, &p->p_acflag))) 3719 return (error); 3720 /* 3721 * all top-level sysctl names are non-terminal 3722 */ 3723 if (SCARG(uap, namelen) > CTL_MAXNAME || SCARG(uap, namelen) < 2) 3724 return (EINVAL); 3725 error = copyin((caddr_t)(u_long)SCARG(uap, name), &name, 3726 SCARG(uap, namelen) * sizeof(int)); 3727 if (error) 3728 return (error); 3729 3730 switch (name[0]) { 3731 case CTL_KERN: 3732 fn = kern_sysctl; 3733 if (name[2] != KERN_VNODE) /* XXX */ 3734 dolock = 0; 3735 break; 3736 case CTL_HW: 3737 fn = hw_sysctl; 3738 break; 3739 case CTL_VM: 3740 fn = uvm_sysctl; 3741 break; 3742 case CTL_NET: 3743 fn = net_sysctl; 3744 break; 3745 case CTL_VFS: 3746 fn = vfs_sysctl; 3747 break; 3748 case CTL_MACHDEP: 3749 fn = cpu_sysctl; 3750 break; 3751 #ifdef DEBUG 3752 case CTL_DEBUG: 3753 fn = debug_sysctl; 3754 break; 3755 #endif 3756 #ifdef DDB 3757 case CTL_DDB: 3758 fn = ddb_sysctl; 3759 break; 3760 #endif 3761 default: 3762 return (EOPNOTSUPP); 3763 } 3764 3765 if (SCARG(uap, oldlenp) && 3766 (error = copyin((caddr_t)(u_long)SCARG(uap, oldlenp), &savelen, sizeof(savelen)))) 3767 return (error); 3768 if (SCARG(uap, old) != NULL) { 3769 if (!uvm_useracc((caddr_t)(u_long)SCARG(uap, old), savelen, B_WRITE)) 3770 return (EFAULT); 3771 #if 0 /* XXXXXXXX */ 3772 while (memlock.sl_lock) { 3773 memlock.sl_want = 1; 3774 sleep((caddr_t)&memlock, PRIBIO+1); 3775 memlock.sl_locked++; 3776 } 3777 memlock.sl_lock = 1; 3778 #endif /* XXXXXXXX */ 3779 if (dolock) { 3780 /* 3781 * XXX Um, this is kind of evil. What should 3782 * XXX we be passing here? 3783 */ 3784 if (uvm_vslock(p, SCARG(uap, old), savelen, 3785 VM_PROT_NONE) != KERN_SUCCESS) { 3786 #if 0 /* XXXXXXXX */ 3787 memlock.sl_lock = 0; 3788 if (memlock.sl_want) { 3789 memlock.sl_want = 0; 3790 wakeup((caddr_t)&memlock); 3791 } 3792 #endif /* XXXXXXXX */ 3793 return (EFAULT); 3794 } 3795 } 3796 oldlen = savelen; 3797 } 3798 error = (*fn)(name + 1, SCARG(uap, namelen) - 1, SCARG(uap, old), 3799 &oldlen, SCARG(uap, new), SCARG(uap, newlen), p); 3800 if (SCARG(uap, old) != NULL) { 3801 if (dolock) 3802 uvm_vsunlock(p, SCARG(uap, old), savelen); 3803 #if 0 /* XXXXXXXXXXX */ 3804 memlock.sl_lock = 0; 3805 if (memlock.sl_want) { 3806 memlock.sl_want = 0; 3807 wakeup((caddr_t)&memlock); 3808 } 3809 #endif /* XXXXXXXXX */ 3810 } 3811 savelen = oldlen; 3812 if (error) 3813 return (error); 3814 if (SCARG(uap, oldlenp)) 3815 error = copyout(&savelen, (caddr_t)(u_long)SCARG(uap, oldlenp), sizeof(savelen)); 3816 return (error); 3817 } 3818 3819 int 3820 netbsd32_mlock(p, v, retval) 3821 struct proc *p; 3822 void *v; 3823 register_t *retval; 3824 { 3825 struct netbsd32_mlock_args /* { 3826 syscallarg(const netbsd32_voidp) addr; 3827 syscallarg(netbsd32_size_t) len; 3828 } */ *uap = v; 3829 struct sys_mlock_args ua; 3830 3831 NETBSD32TOP_UAP(addr, const void); 3832 NETBSD32TO64_UAP(len); 3833 return (sys_mlock(p, &ua, retval)); 3834 } 3835 3836 int 3837 netbsd32_munlock(p, v, retval) 3838 struct proc *p; 3839 void *v; 3840 register_t *retval; 3841 { 3842 struct netbsd32_munlock_args /* { 3843 syscallarg(const netbsd32_voidp) addr; 3844 syscallarg(netbsd32_size_t) len; 3845 } */ *uap = v; 3846 struct sys_munlock_args ua; 3847 3848 NETBSD32TOP_UAP(addr, const void); 3849 NETBSD32TO64_UAP(len); 3850 return (sys_munlock(p, &ua, retval)); 3851 } 3852 3853 int 3854 netbsd32_undelete(p, v, retval) 3855 struct proc *p; 3856 void *v; 3857 register_t *retval; 3858 { 3859 struct netbsd32_undelete_args /* { 3860 syscallarg(const netbsd32_charp) path; 3861 } */ *uap = v; 3862 struct sys_undelete_args ua; 3863 3864 NETBSD32TOP_UAP(path, const char); 3865 return (sys_undelete(p, &ua, retval)); 3866 } 3867 3868 int 3869 netbsd32_futimes(p, v, retval) 3870 struct proc *p; 3871 void *v; 3872 register_t *retval; 3873 { 3874 struct netbsd32_futimes_args /* { 3875 syscallarg(int) fd; 3876 syscallarg(const netbsd32_timevalp_t) tptr; 3877 } */ *uap = v; 3878 int error; 3879 struct file *fp; 3880 3881 /* getvnode() will use the descriptor for us */ 3882 if ((error = getvnode(p->p_fd, SCARG(uap, fd), &fp)) != 0) 3883 return (error); 3884 3885 error = change_utimes32((struct vnode *)fp->f_data, 3886 (struct timeval *)(u_long)SCARG(uap, tptr), p); 3887 FILE_UNUSE(fp, p); 3888 return (error); 3889 } 3890 3891 int 3892 netbsd32_getpgid(p, v, retval) 3893 struct proc *p; 3894 void *v; 3895 register_t *retval; 3896 { 3897 struct netbsd32_getpgid_args /* { 3898 syscallarg(pid_t) pid; 3899 } */ *uap = v; 3900 struct sys_getpgid_args ua; 3901 3902 NETBSD32TO64_UAP(pid); 3903 return (sys_getpgid(p, &ua, retval)); 3904 } 3905 3906 int 3907 netbsd32_reboot(p, v, retval) 3908 struct proc *p; 3909 void *v; 3910 register_t *retval; 3911 { 3912 struct netbsd32_reboot_args /* { 3913 syscallarg(int) opt; 3914 syscallarg(netbsd32_charp) bootstr; 3915 } */ *uap = v; 3916 struct sys_reboot_args ua; 3917 3918 NETBSD32TO64_UAP(opt); 3919 NETBSD32TOP_UAP(bootstr, char); 3920 return (sys_reboot(p, &ua, retval)); 3921 } 3922 3923 int 3924 netbsd32_poll(p, v, retval) 3925 struct proc *p; 3926 void *v; 3927 register_t *retval; 3928 { 3929 struct netbsd32_poll_args /* { 3930 syscallarg(netbsd32_pollfdp_t) fds; 3931 syscallarg(u_int) nfds; 3932 syscallarg(int) timeout; 3933 } */ *uap = v; 3934 struct sys_poll_args ua; 3935 3936 NETBSD32TOP_UAP(fds, struct pollfd); 3937 NETBSD32TO64_UAP(nfds); 3938 NETBSD32TO64_UAP(timeout); 3939 return (sys_poll(p, &ua, retval)); 3940 } 3941 3942 /* 3943 * XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX 3944 * 3945 * This is BSD. We won't support System V IPC. 3946 * Too much work. 3947 * 3948 * XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX 3949 */ 3950 int 3951 netbsd32___semctl(p, v, retval) 3952 struct proc *p; 3953 void *v; 3954 register_t *retval; 3955 { 3956 #if 0 3957 struct netbsd32___semctl_args /* { 3958 syscallarg(int) semid; 3959 syscallarg(int) semnum; 3960 syscallarg(int) cmd; 3961 syscallarg(netbsd32_semunu_t) arg; 3962 } */ *uap = v; 3963 union netbsd32_semun sem32; 3964 int semid = SCARG(uap, semid); 3965 int semnum = SCARG(uap, semnum); 3966 int cmd = SCARG(uap, cmd); 3967 union netbsd32_semun *arg = (void*)(u_long)SCARG(uap, arg); 3968 union netbsd32_semun real_arg; 3969 struct ucred *cred = p->p_ucred; 3970 int i, rval, eval; 3971 struct netbsd32_semid_ds sbuf; 3972 register struct semid_ds *semaptr; 3973 3974 semlock(p); 3975 3976 semid = IPCID_TO_IX(semid); 3977 if (semid < 0 || semid >= seminfo.semmsl) 3978 return(EINVAL); 3979 3980 semaptr = &sema[semid]; 3981 if ((semaptr->sem_perm.mode & SEM_ALLOC) == 0 || 3982 semaptr->sem_perm.seq != IPCID_TO_SEQ(SCARG(uap, semid))) 3983 return(EINVAL); 3984 3985 eval = 0; 3986 rval = 0; 3987 3988 switch (cmd) { 3989 case IPC_RMID: 3990 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_M)) != 0) 3991 return(eval); 3992 semaptr->sem_perm.cuid = cred->cr_uid; 3993 semaptr->sem_perm.uid = cred->cr_uid; 3994 semtot -= semaptr->sem_nsems; 3995 for (i = semaptr->_sem_base - sem; i < semtot; i++) 3996 sem[i] = sem[i + semaptr->sem_nsems]; 3997 for (i = 0; i < seminfo.semmni; i++) { 3998 if ((sema[i].sem_perm.mode & SEM_ALLOC) && 3999 sema[i]._sem_base > semaptr->_sem_base) 4000 sema[i]._sem_base -= semaptr->sem_nsems; 4001 } 4002 semaptr->sem_perm.mode = 0; 4003 semundo_clear(semid, -1); 4004 wakeup((caddr_t)semaptr); 4005 break; 4006 4007 case IPC_SET: 4008 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_M))) 4009 return(eval); 4010 if ((eval = copyin(arg, &real_arg, sizeof(real_arg))) != 0) 4011 return(eval); 4012 if ((eval = copyin((caddr_t)(u_long)real_arg.buf, (caddr_t)&sbuf, 4013 sizeof(sbuf))) != 0) 4014 return(eval); 4015 semaptr->sem_perm.uid = sbuf.sem_perm.uid; 4016 semaptr->sem_perm.gid = sbuf.sem_perm.gid; 4017 semaptr->sem_perm.mode = (semaptr->sem_perm.mode & ~0777) | 4018 (sbuf.sem_perm.mode & 0777); 4019 semaptr->sem_ctime = time.tv_sec; 4020 break; 4021 4022 case IPC_STAT: 4023 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4024 return(eval); 4025 if ((eval = copyin(arg, &real_arg, sizeof(real_arg))) != 0) 4026 return(eval); 4027 eval = copyout((caddr_t)semaptr, (caddr_t)(u_long)real_arg.buf, 4028 sizeof(struct semid_ds)); 4029 break; 4030 4031 case GETNCNT: 4032 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4033 return(eval); 4034 if (semnum < 0 || semnum >= semaptr->sem_nsems) 4035 return(EINVAL); 4036 rval = semaptr->_sem_base[semnum].semncnt; 4037 break; 4038 4039 case GETPID: 4040 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4041 return(eval); 4042 if (semnum < 0 || semnum >= semaptr->sem_nsems) 4043 return(EINVAL); 4044 rval = semaptr->_sem_base[semnum].sempid; 4045 break; 4046 4047 case GETVAL: 4048 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4049 return(eval); 4050 if (semnum < 0 || semnum >= semaptr->sem_nsems) 4051 return(EINVAL); 4052 rval = semaptr->_sem_base[semnum].semval; 4053 break; 4054 4055 case GETALL: 4056 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4057 return(eval); 4058 if ((eval = copyin(arg, &real_arg, sizeof(real_arg))) != 0) 4059 return(eval); 4060 for (i = 0; i < semaptr->sem_nsems; i++) { 4061 eval = copyout((caddr_t)&semaptr->_sem_base[i].semval, 4062 &real_arg.array[i], sizeof(real_arg.array[0])); 4063 if (eval != 0) 4064 break; 4065 } 4066 break; 4067 4068 case GETZCNT: 4069 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_R))) 4070 return(eval); 4071 if (semnum < 0 || semnum >= semaptr->sem_nsems) 4072 return(EINVAL); 4073 rval = semaptr->_sem_base[semnum].semzcnt; 4074 break; 4075 4076 case SETVAL: 4077 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_W))) 4078 return(eval); 4079 if (semnum < 0 || semnum >= semaptr->sem_nsems) 4080 return(EINVAL); 4081 if ((eval = copyin(arg, &real_arg, sizeof(real_arg))) != 0) 4082 return(eval); 4083 semaptr->_sem_base[semnum].semval = real_arg.val; 4084 semundo_clear(semid, semnum); 4085 wakeup((caddr_t)semaptr); 4086 break; 4087 4088 case SETALL: 4089 if ((eval = ipcperm(cred, &semaptr->sem_perm, IPC_W))) 4090 return(eval); 4091 if ((eval = copyin(arg, &real_arg, sizeof(real_arg))) != 0) 4092 return(eval); 4093 for (i = 0; i < semaptr->sem_nsems; i++) { 4094 eval = copyin(&real_arg.array[i], 4095 (caddr_t)&semaptr->_sem_base[i].semval, 4096 sizeof(real_arg.array[0])); 4097 if (eval != 0) 4098 break; 4099 } 4100 semundo_clear(semid, -1); 4101 wakeup((caddr_t)semaptr); 4102 break; 4103 4104 default: 4105 return(EINVAL); 4106 } 4107 4108 if (eval == 0) 4109 *retval = rval; 4110 return(eval); 4111 #else 4112 return (ENOSYS); 4113 #endif 4114 } 4115 4116 int 4117 netbsd32_semget(p, v, retval) 4118 struct proc *p; 4119 void *v; 4120 register_t *retval; 4121 { 4122 struct netbsd32_semget_args /* { 4123 syscallarg(netbsd32_key_t) key; 4124 syscallarg(int) nsems; 4125 syscallarg(int) semflg; 4126 } */ *uap = v; 4127 struct sys_semget_args ua; 4128 4129 NETBSD32TOX_UAP(key, key_t); 4130 NETBSD32TO64_UAP(nsems); 4131 NETBSD32TO64_UAP(semflg); 4132 return (sys_semget(p, &ua, retval)); 4133 } 4134 4135 int 4136 netbsd32_semop(p, v, retval) 4137 struct proc *p; 4138 void *v; 4139 register_t *retval; 4140 { 4141 struct netbsd32_semop_args /* { 4142 syscallarg(int) semid; 4143 syscallarg(netbsd32_sembufp_t) sops; 4144 syscallarg(netbsd32_size_t) nsops; 4145 } */ *uap = v; 4146 struct sys_semop_args ua; 4147 4148 NETBSD32TO64_UAP(semid); 4149 NETBSD32TOP_UAP(sops, struct sembuf); 4150 NETBSD32TOX_UAP(nsops, size_t); 4151 return (sys_semop(p, &ua, retval)); 4152 } 4153 4154 int 4155 netbsd32_semconfig(p, v, retval) 4156 struct proc *p; 4157 void *v; 4158 register_t *retval; 4159 { 4160 struct netbsd32_semconfig_args /* { 4161 syscallarg(int) flag; 4162 } */ *uap = v; 4163 struct sys_semconfig_args ua; 4164 4165 NETBSD32TO64_UAP(flag); 4166 return (sys_semconfig(p, &ua, retval)); 4167 } 4168 4169 int 4170 netbsd32_msgctl(p, v, retval) 4171 struct proc *p; 4172 void *v; 4173 register_t *retval; 4174 { 4175 #if 0 4176 struct netbsd32_msgctl_args /* { 4177 syscallarg(int) msqid; 4178 syscallarg(int) cmd; 4179 syscallarg(netbsd32_msqid_dsp_t) buf; 4180 } */ *uap = v; 4181 struct sys_msgctl_args ua; 4182 struct msqid_ds ds; 4183 struct netbsd32_msqid_ds *ds32p; 4184 int error; 4185 4186 NETBSD32TO64_UAP(msqid); 4187 NETBSD32TO64_UAP(cmd); 4188 ds32p = (struct netbsd32_msqid_ds *)(u_long)SCARG(uap, buf); 4189 if (ds32p) { 4190 SCARG(&ua, buf) = NULL; 4191 netbsd32_to_msqid_ds(ds32p, &ds); 4192 } else 4193 SCARG(&ua, buf) = NULL; 4194 error = sys_msgctl(p, &ua, retval); 4195 if (error) 4196 return (error); 4197 4198 if (ds32p) 4199 netbsd32_from_msqid_ds(&ds, ds32p); 4200 return (0); 4201 #else 4202 return (ENOSYS); 4203 #endif 4204 } 4205 4206 int 4207 netbsd32_msgget(p, v, retval) 4208 struct proc *p; 4209 void *v; 4210 register_t *retval; 4211 { 4212 #if 0 4213 struct netbsd32_msgget_args /* { 4214 syscallarg(netbsd32_key_t) key; 4215 syscallarg(int) msgflg; 4216 } */ *uap = v; 4217 struct sys_msgget_args ua; 4218 4219 NETBSD32TOX_UAP(key, key_t); 4220 NETBSD32TO64_UAP(msgflg); 4221 return (sys_msgget(p, &ua, retval)); 4222 #else 4223 return (ENOSYS); 4224 #endif 4225 } 4226 4227 int 4228 netbsd32_msgsnd(p, v, retval) 4229 struct proc *p; 4230 void *v; 4231 register_t *retval; 4232 { 4233 #if 0 4234 struct netbsd32_msgsnd_args /* { 4235 syscallarg(int) msqid; 4236 syscallarg(const netbsd32_voidp) msgp; 4237 syscallarg(netbsd32_size_t) msgsz; 4238 syscallarg(int) msgflg; 4239 } */ *uap = v; 4240 struct sys_msgsnd_args ua; 4241 4242 NETBSD32TO64_UAP(msqid); 4243 NETBSD32TOP_UAP(msgp, void); 4244 NETBSD32TOX_UAP(msgsz, size_t); 4245 NETBSD32TO64_UAP(msgflg); 4246 return (sys_msgsnd(p, &ua, retval)); 4247 #else 4248 return (ENOSYS); 4249 #endif 4250 } 4251 4252 int 4253 netbsd32_msgrcv(p, v, retval) 4254 struct proc *p; 4255 void *v; 4256 register_t *retval; 4257 { 4258 #if 0 4259 struct netbsd32_msgrcv_args /* { 4260 syscallarg(int) msqid; 4261 syscallarg(netbsd32_voidp) msgp; 4262 syscallarg(netbsd32_size_t) msgsz; 4263 syscallarg(netbsd32_long) msgtyp; 4264 syscallarg(int) msgflg; 4265 } */ *uap = v; 4266 struct sys_msgrcv_args ua; 4267 ssize_t rt; 4268 int error; 4269 4270 NETBSD32TO64_UAP(msqid); 4271 NETBSD32TOP_UAP(msgp, void); 4272 NETBSD32TOX_UAP(msgsz, size_t); 4273 NETBSD32TOX_UAP(msgtyp, long); 4274 NETBSD32TO64_UAP(msgflg); 4275 error = sys_msgrcv(p, &ua, (register_t *)&rt); 4276 *(netbsd32_ssize_t *)retval = rt; 4277 return (error); 4278 #else 4279 return (ENOSYS); 4280 #endif 4281 } 4282 4283 int 4284 netbsd32_shmat(p, v, retval) 4285 struct proc *p; 4286 void *v; 4287 register_t *retval; 4288 { 4289 #if 0 4290 struct netbsd32_shmat_args /* { 4291 syscallarg(int) shmid; 4292 syscallarg(const netbsd32_voidp) shmaddr; 4293 syscallarg(int) shmflg; 4294 } */ *uap = v; 4295 struct sys_shmat_args ua; 4296 void *rt; 4297 int error; 4298 4299 NETBSD32TO64_UAP(shmid); 4300 NETBSD32TOP_UAP(shmaddr, void); 4301 NETBSD32TO64_UAP(shmflg); 4302 error = sys_shmat(p, &ua, (register_t *)&rt); 4303 *retval = (netbsd32_voidp)(u_long)rt; 4304 return (error); 4305 #else 4306 return (ENOSYS); 4307 #endif 4308 } 4309 4310 int 4311 netbsd32_shmctl(p, v, retval) 4312 struct proc *p; 4313 void *v; 4314 register_t *retval; 4315 { 4316 #if 0 4317 struct netbsd32_shmctl_args /* { 4318 syscallarg(int) shmid; 4319 syscallarg(int) cmd; 4320 syscallarg(netbsd32_shmid_dsp_t) buf; 4321 } */ *uap = v; 4322 struct sys_shmctl_args ua; 4323 struct shmid_ds ds; 4324 struct netbsd32_shmid_ds *ds32p; 4325 int error; 4326 4327 NETBSD32TO64_UAP(shmid); 4328 NETBSD32TO64_UAP(cmd); 4329 ds32p = (struct netbsd32_shmid_ds *)(u_long)SCARG(uap, buf); 4330 if (ds32p) { 4331 SCARG(&ua, buf) = NULL; 4332 netbsd32_to_shmid_ds(ds32p, &ds); 4333 } else 4334 SCARG(&ua, buf) = NULL; 4335 error = sys_shmctl(p, &ua, retval); 4336 if (error) 4337 return (error); 4338 4339 if (ds32p) 4340 netbsd32_from_shmid_ds(&ds, ds32p); 4341 return (0); 4342 #else 4343 return (ENOSYS); 4344 #endif 4345 } 4346 4347 int 4348 netbsd32_shmdt(p, v, retval) 4349 struct proc *p; 4350 void *v; 4351 register_t *retval; 4352 { 4353 #if 0 4354 struct netbsd32_shmdt_args /* { 4355 syscallarg(const netbsd32_voidp) shmaddr; 4356 } */ *uap = v; 4357 struct sys_shmdt_args ua; 4358 4359 NETBSD32TOP_UAP(shmaddr, const char); 4360 return (sys_shmdt(p, &ua, retval)); 4361 #else 4362 return (ENOSYS); 4363 #endif 4364 } 4365 4366 int 4367 netbsd32_shmget(p, v, retval) 4368 struct proc *p; 4369 void *v; 4370 register_t *retval; 4371 { 4372 #if 0 4373 struct netbsd32_shmget_args /* { 4374 syscallarg(netbsd32_key_t) key; 4375 syscallarg(netbsd32_size_t) size; 4376 syscallarg(int) shmflg; 4377 } */ *uap = v; 4378 struct sys_shmget_args ua; 4379 4380 NETBSD32TOX_UAP(key, key_t) 4381 NETBSD32TOX_UAP(size, size_t) 4382 NETBSD32TO64_UAP(shmflg); 4383 return (sys_shmget(p, &ua, retval)); 4384 #else 4385 return (ENOSYS); 4386 #endif 4387 } 4388 4389 int 4390 netbsd32_clock_gettime(p, v, retval) 4391 struct proc *p; 4392 void *v; 4393 register_t *retval; 4394 { 4395 struct netbsd32_clock_gettime_args /* { 4396 syscallarg(netbsd32_clockid_t) clock_id; 4397 syscallarg(netbsd32_timespecp_t) tp; 4398 } */ *uap = v; 4399 clockid_t clock_id; 4400 struct timeval atv; 4401 struct timespec ats; 4402 struct netbsd32_timespec ts32; 4403 4404 clock_id = SCARG(uap, clock_id); 4405 if (clock_id != CLOCK_REALTIME) 4406 return (EINVAL); 4407 4408 microtime(&atv); 4409 TIMEVAL_TO_TIMESPEC(&atv,&ats); 4410 netbsd32_from_timespec(&ats, &ts32); 4411 4412 return copyout(&ts32, (caddr_t)(u_long)SCARG(uap, tp), sizeof(ts32)); 4413 } 4414 4415 int 4416 netbsd32_clock_settime(p, v, retval) 4417 struct proc *p; 4418 void *v; 4419 register_t *retval; 4420 { 4421 struct netbsd32_clock_settime_args /* { 4422 syscallarg(netbsd32_clockid_t) clock_id; 4423 syscallarg(const netbsd32_timespecp_t) tp; 4424 } */ *uap = v; 4425 struct netbsd32_timespec ts32; 4426 clockid_t clock_id; 4427 struct timeval atv; 4428 struct timespec ats; 4429 int error; 4430 4431 if ((error = suser(p->p_ucred, &p->p_acflag)) != 0) 4432 return (error); 4433 4434 clock_id = SCARG(uap, clock_id); 4435 if (clock_id != CLOCK_REALTIME) 4436 return (EINVAL); 4437 4438 if ((error = copyin((caddr_t)(u_long)SCARG(uap, tp), &ts32, sizeof(ts32))) != 0) 4439 return (error); 4440 4441 netbsd32_to_timespec(&ts32, &ats); 4442 TIMESPEC_TO_TIMEVAL(&atv,&ats); 4443 if ((error = settime(&atv))) 4444 return (error); 4445 4446 return 0; 4447 } 4448 4449 int 4450 netbsd32_clock_getres(p, v, retval) 4451 struct proc *p; 4452 void *v; 4453 register_t *retval; 4454 { 4455 struct netbsd32_clock_getres_args /* { 4456 syscallarg(netbsd32_clockid_t) clock_id; 4457 syscallarg(netbsd32_timespecp_t) tp; 4458 } */ *uap = v; 4459 struct netbsd32_timespec ts32; 4460 clockid_t clock_id; 4461 struct timespec ts; 4462 int error = 0; 4463 4464 clock_id = SCARG(uap, clock_id); 4465 if (clock_id != CLOCK_REALTIME) 4466 return (EINVAL); 4467 4468 if (SCARG(uap, tp)) { 4469 ts.tv_sec = 0; 4470 ts.tv_nsec = 1000000000 / hz; 4471 4472 netbsd32_from_timespec(&ts, &ts32); 4473 error = copyout(&ts, (caddr_t)(u_long)SCARG(uap, tp), sizeof(ts)); 4474 } 4475 4476 return error; 4477 } 4478 4479 int 4480 netbsd32_nanosleep(p, v, retval) 4481 struct proc *p; 4482 void *v; 4483 register_t *retval; 4484 { 4485 struct netbsd32_nanosleep_args /* { 4486 syscallarg(const netbsd32_timespecp_t) rqtp; 4487 syscallarg(netbsd32_timespecp_t) rmtp; 4488 } */ *uap = v; 4489 static int nanowait; 4490 struct netbsd32_timespec ts32; 4491 struct timespec rqt; 4492 struct timespec rmt; 4493 struct timeval atv, utv; 4494 int error, s, timo; 4495 4496 error = copyin((caddr_t)(u_long)SCARG(uap, rqtp), (caddr_t)&ts32, 4497 sizeof(ts32)); 4498 if (error) 4499 return (error); 4500 4501 netbsd32_to_timespec(&ts32, &rqt); 4502 TIMESPEC_TO_TIMEVAL(&atv,&rqt) 4503 if (itimerfix(&atv)) 4504 return (EINVAL); 4505 4506 s = splclock(); 4507 timeradd(&atv,&time,&atv); 4508 timo = hzto(&atv); 4509 /* 4510 * Avoid inadvertantly sleeping forever 4511 */ 4512 if (timo == 0) 4513 timo = 1; 4514 splx(s); 4515 4516 error = tsleep(&nanowait, PWAIT | PCATCH, "nanosleep", timo); 4517 if (error == ERESTART) 4518 error = EINTR; 4519 if (error == EWOULDBLOCK) 4520 error = 0; 4521 4522 if (SCARG(uap, rmtp)) { 4523 int error; 4524 4525 s = splclock(); 4526 utv = time; 4527 splx(s); 4528 4529 timersub(&atv, &utv, &utv); 4530 if (utv.tv_sec < 0) 4531 timerclear(&utv); 4532 4533 TIMEVAL_TO_TIMESPEC(&utv,&rmt); 4534 netbsd32_from_timespec(&rmt, &ts32); 4535 error = copyout((caddr_t)&ts32, (caddr_t)(u_long)SCARG(uap,rmtp), 4536 sizeof(ts32)); 4537 if (error) 4538 return (error); 4539 } 4540 4541 return error; 4542 } 4543 4544 int 4545 netbsd32_fdatasync(p, v, retval) 4546 struct proc *p; 4547 void *v; 4548 register_t *retval; 4549 { 4550 struct netbsd32_fdatasync_args /* { 4551 syscallarg(int) fd; 4552 } */ *uap = v; 4553 struct sys_fdatasync_args ua; 4554 4555 NETBSD32TO64_UAP(fd); 4556 4557 return (sys_fdatasync(p, &ua, retval)); 4558 } 4559 4560 int 4561 netbsd32___posix_rename(p, v, retval) 4562 struct proc *p; 4563 void *v; 4564 register_t *retval; 4565 { 4566 struct netbsd32___posix_rename_args /* { 4567 syscallarg(const netbsd32_charp) from; 4568 syscallarg(const netbsd32_charp) to; 4569 } */ *uap = v; 4570 struct sys___posix_rename_args ua; 4571 4572 NETBSD32TOP_UAP(from, const char *); 4573 NETBSD32TOP_UAP(to, const char *); 4574 4575 return (sys___posix_rename(p, &ua, retval)); 4576 } 4577 4578 int 4579 netbsd32_swapctl(p, v, retval) 4580 struct proc *p; 4581 void *v; 4582 register_t *retval; 4583 { 4584 struct netbsd32_swapctl_args /* { 4585 syscallarg(int) cmd; 4586 syscallarg(const netbsd32_voidp) arg; 4587 syscallarg(int) misc; 4588 } */ *uap = v; 4589 struct sys_swapctl_args ua; 4590 4591 NETBSD32TO64_UAP(cmd); 4592 NETBSD32TOP_UAP(arg, const void); 4593 NETBSD32TO64_UAP(misc); 4594 return (sys_swapctl(p, &ua, retval)); 4595 } 4596 4597 int 4598 netbsd32_getdents(p, v, retval) 4599 struct proc *p; 4600 void *v; 4601 register_t *retval; 4602 { 4603 struct netbsd32_getdents_args /* { 4604 syscallarg(int) fd; 4605 syscallarg(netbsd32_charp) buf; 4606 syscallarg(netbsd32_size_t) count; 4607 } */ *uap = v; 4608 struct file *fp; 4609 int error, done; 4610 4611 /* getvnode() will use the descriptor for us */ 4612 if ((error = getvnode(p->p_fd, SCARG(uap, fd), &fp)) != 0) 4613 return (error); 4614 if ((fp->f_flag & FREAD) == 0) { 4615 error = EBADF; 4616 goto out; 4617 } 4618 error = vn_readdir(fp, (caddr_t)(u_long)SCARG(uap, buf), UIO_USERSPACE, 4619 SCARG(uap, count), &done, p, 0, 0); 4620 *retval = done; 4621 out: 4622 FILE_UNUSE(fp, p); 4623 return (error); 4624 } 4625 4626 4627 int 4628 netbsd32_minherit(p, v, retval) 4629 struct proc *p; 4630 void *v; 4631 register_t *retval; 4632 { 4633 struct netbsd32_minherit_args /* { 4634 syscallarg(netbsd32_voidp) addr; 4635 syscallarg(netbsd32_size_t) len; 4636 syscallarg(int) inherit; 4637 } */ *uap = v; 4638 struct sys_minherit_args ua; 4639 4640 NETBSD32TOP_UAP(addr, void); 4641 NETBSD32TOX_UAP(len, size_t); 4642 NETBSD32TO64_UAP(inherit); 4643 return (sys_minherit(p, &ua, retval)); 4644 } 4645 4646 int 4647 netbsd32_lchmod(p, v, retval) 4648 struct proc *p; 4649 void *v; 4650 register_t *retval; 4651 { 4652 struct netbsd32_lchmod_args /* { 4653 syscallarg(const netbsd32_charp) path; 4654 syscallarg(mode_t) mode; 4655 } */ *uap = v; 4656 struct sys_lchmod_args ua; 4657 4658 NETBSD32TOP_UAP(path, const char); 4659 NETBSD32TO64_UAP(mode); 4660 return (sys_lchmod(p, &ua, retval)); 4661 } 4662 4663 int 4664 netbsd32_lchown(p, v, retval) 4665 struct proc *p; 4666 void *v; 4667 register_t *retval; 4668 { 4669 struct netbsd32_lchown_args /* { 4670 syscallarg(const netbsd32_charp) path; 4671 syscallarg(uid_t) uid; 4672 syscallarg(gid_t) gid; 4673 } */ *uap = v; 4674 struct sys_lchown_args ua; 4675 4676 NETBSD32TOP_UAP(path, const char); 4677 NETBSD32TO64_UAP(uid); 4678 NETBSD32TO64_UAP(gid); 4679 return (sys_lchown(p, &ua, retval)); 4680 } 4681 4682 int 4683 netbsd32_lutimes(p, v, retval) 4684 struct proc *p; 4685 void *v; 4686 register_t *retval; 4687 { 4688 struct netbsd32_lutimes_args /* { 4689 syscallarg(const netbsd32_charp) path; 4690 syscallarg(const netbsd32_timevalp_t) tptr; 4691 } */ *uap = v; 4692 int error; 4693 struct nameidata nd; 4694 4695 NDINIT(&nd, LOOKUP, NOFOLLOW, UIO_USERSPACE, (caddr_t)(u_long)SCARG(uap, path), p); 4696 if ((error = namei(&nd)) != 0) 4697 return (error); 4698 4699 error = change_utimes32(nd.ni_vp, (struct timeval *)(u_long)SCARG(uap, tptr), p); 4700 4701 vrele(nd.ni_vp); 4702 return (error); 4703 } 4704 4705 4706 int 4707 netbsd32___msync13(p, v, retval) 4708 struct proc *p; 4709 void *v; 4710 register_t *retval; 4711 { 4712 struct netbsd32___msync13_args /* { 4713 syscallarg(netbsd32_voidp) addr; 4714 syscallarg(netbsd32_size_t) len; 4715 syscallarg(int) flags; 4716 } */ *uap = v; 4717 struct sys___msync13_args ua; 4718 4719 NETBSD32TOP_UAP(addr, void); 4720 NETBSD32TOX_UAP(len, size_t); 4721 NETBSD32TO64_UAP(flags); 4722 return (sys___msync13(p, &ua, retval)); 4723 } 4724 4725 int 4726 netbsd32___stat13(p, v, retval) 4727 struct proc *p; 4728 void *v; 4729 register_t *retval; 4730 { 4731 struct netbsd32___stat13_args /* { 4732 syscallarg(const netbsd32_charp) path; 4733 syscallarg(netbsd32_statp_t) ub; 4734 } */ *uap = v; 4735 struct netbsd32_stat sb32; 4736 struct stat sb; 4737 int error; 4738 struct nameidata nd; 4739 4740 NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, UIO_USERSPACE, 4741 (caddr_t)(u_long)SCARG(uap, path), p); 4742 if ((error = namei(&nd)) != 0) 4743 return (error); 4744 error = vn_stat(nd.ni_vp, &sb, p); 4745 vput(nd.ni_vp); 4746 if (error) 4747 return (error); 4748 netbsd32_from___stat13(&sb, &sb32); 4749 error = copyout(&sb32, (caddr_t)(u_long)SCARG(uap, ub), sizeof(sb32)); 4750 return (error); 4751 } 4752 4753 int 4754 netbsd32___fstat13(p, v, retval) 4755 struct proc *p; 4756 void *v; 4757 register_t *retval; 4758 { 4759 struct netbsd32___fstat13_args /* { 4760 syscallarg(int) fd; 4761 syscallarg(netbsd32_statp_t) sb; 4762 } */ *uap = v; 4763 int fd = SCARG(uap, fd); 4764 register struct filedesc *fdp = p->p_fd; 4765 register struct file *fp; 4766 struct netbsd32_stat sb32; 4767 struct stat ub; 4768 int error = 0; 4769 4770 if ((u_int)fd >= fdp->fd_nfiles || 4771 (fp = fdp->fd_ofiles[fd]) == NULL) 4772 return (EBADF); 4773 switch (fp->f_type) { 4774 4775 case DTYPE_VNODE: 4776 error = vn_stat((struct vnode *)fp->f_data, &ub, p); 4777 break; 4778 4779 case DTYPE_SOCKET: 4780 error = soo_stat((struct socket *)fp->f_data, &ub); 4781 break; 4782 4783 default: 4784 panic("fstat"); 4785 /*NOTREACHED*/ 4786 } 4787 if (error == 0) { 4788 netbsd32_from___stat13(&ub, &sb32); 4789 error = copyout(&sb32, (caddr_t)(u_long)SCARG(uap, sb), sizeof(sb32)); 4790 } 4791 return (error); 4792 } 4793 4794 int 4795 netbsd32___lstat13(p, v, retval) 4796 struct proc *p; 4797 void *v; 4798 register_t *retval; 4799 { 4800 struct netbsd32___lstat13_args /* { 4801 syscallarg(const netbsd32_charp) path; 4802 syscallarg(netbsd32_statp_t) ub; 4803 } */ *uap = v; 4804 struct netbsd32_stat sb32; 4805 struct stat sb; 4806 int error; 4807 struct nameidata nd; 4808 4809 NDINIT(&nd, LOOKUP, NOFOLLOW | LOCKLEAF, UIO_USERSPACE, 4810 (caddr_t)(u_long)SCARG(uap, path), p); 4811 if ((error = namei(&nd)) != 0) 4812 return (error); 4813 error = vn_stat(nd.ni_vp, &sb, p); 4814 vput(nd.ni_vp); 4815 if (error) 4816 return (error); 4817 netbsd32_from___stat13(&sb, &sb32); 4818 error = copyout(&sb32, (caddr_t)(u_long)SCARG(uap, ub), sizeof(sb32)); 4819 return (error); 4820 } 4821 4822 int 4823 netbsd32___sigaltstack14(p, v, retval) 4824 struct proc *p; 4825 void *v; 4826 register_t *retval; 4827 { 4828 struct netbsd32___sigaltstack14_args /* { 4829 syscallarg(const netbsd32_sigaltstackp_t) nss; 4830 syscallarg(netbsd32_sigaltstackp_t) oss; 4831 } */ *uap = v; 4832 struct netbsd32_sigaltstack s32; 4833 struct sigaltstack nss, oss; 4834 int error; 4835 4836 if (SCARG(uap, nss)) { 4837 error = copyin((caddr_t)(u_long)SCARG(uap, nss), &s32, sizeof(s32)); 4838 if (error) 4839 return (error); 4840 nss.ss_sp = (void *)(u_long)s32.ss_sp; 4841 nss.ss_size = (size_t)s32.ss_size; 4842 nss.ss_flags = s32.ss_flags; 4843 } 4844 error = sigaltstack1(p, 4845 SCARG(uap, nss) ? &nss : 0, SCARG(uap, oss) ? &oss : 0); 4846 if (error) 4847 return (error); 4848 if (SCARG(uap, oss)) { 4849 s32.ss_sp = (netbsd32_voidp)(u_long)oss.ss_sp; 4850 s32.ss_size = (netbsd32_size_t)oss.ss_size; 4851 s32.ss_flags = oss.ss_flags; 4852 error = copyout(&s32, (caddr_t)(u_long)SCARG(uap, oss), sizeof(s32)); 4853 if (error) 4854 return (error); 4855 } 4856 return (0); 4857 } 4858 4859 int 4860 netbsd32___posix_chown(p, v, retval) 4861 struct proc *p; 4862 void *v; 4863 register_t *retval; 4864 { 4865 struct netbsd32___posix_chown_args /* { 4866 syscallarg(const netbsd32_charp) path; 4867 syscallarg(uid_t) uid; 4868 syscallarg(gid_t) gid; 4869 } */ *uap = v; 4870 struct sys___posix_chown_args ua; 4871 4872 NETBSD32TOP_UAP(path, const char); 4873 NETBSD32TO64_UAP(uid); 4874 NETBSD32TO64_UAP(gid); 4875 return (sys___posix_chown(p, &ua, retval)); 4876 } 4877 4878 int 4879 netbsd32___posix_fchown(p, v, retval) 4880 struct proc *p; 4881 void *v; 4882 register_t *retval; 4883 { 4884 struct netbsd32___posix_fchown_args /* { 4885 syscallarg(int) fd; 4886 syscallarg(uid_t) uid; 4887 syscallarg(gid_t) gid; 4888 } */ *uap = v; 4889 struct sys___posix_fchown_args ua; 4890 4891 NETBSD32TO64_UAP(fd); 4892 NETBSD32TO64_UAP(uid); 4893 NETBSD32TO64_UAP(gid); 4894 return (sys___posix_fchown(p, &ua, retval)); 4895 } 4896 4897 int 4898 netbsd32___posix_lchown(p, v, retval) 4899 struct proc *p; 4900 void *v; 4901 register_t *retval; 4902 { 4903 struct netbsd32___posix_lchown_args /* { 4904 syscallarg(const netbsd32_charp) path; 4905 syscallarg(uid_t) uid; 4906 syscallarg(gid_t) gid; 4907 } */ *uap = v; 4908 struct sys___posix_lchown_args ua; 4909 4910 NETBSD32TOP_UAP(path, const char); 4911 NETBSD32TO64_UAP(uid); 4912 NETBSD32TO64_UAP(gid); 4913 return (sys___posix_lchown(p, &ua, retval)); 4914 } 4915 4916 int 4917 netbsd32_getsid(p, v, retval) 4918 struct proc *p; 4919 void *v; 4920 register_t *retval; 4921 { 4922 struct netbsd32_getsid_args /* { 4923 syscallarg(pid_t) pid; 4924 } */ *uap = v; 4925 struct sys_getsid_args ua; 4926 4927 NETBSD32TO64_UAP(pid); 4928 return (sys_getsid(p, &ua, retval)); 4929 } 4930 4931 int 4932 netbsd32_fktrace(p, v, retval) 4933 struct proc *p; 4934 void *v; 4935 register_t *retval; 4936 { 4937 struct netbsd32_fktrace_args /* { 4938 syscallarg(const int) fd; 4939 syscallarg(int) ops; 4940 syscallarg(int) facs; 4941 syscallarg(int) pid; 4942 } */ *uap = v; 4943 struct sys_fktrace_args ua; 4944 4945 NETBSD32TO64_UAP(fd); 4946 NETBSD32TO64_UAP(ops); 4947 NETBSD32TO64_UAP(facs); 4948 NETBSD32TO64_UAP(pid); 4949 return (sys_fktrace(p, &ua, retval)); 4950 } 4951 4952 int 4953 netbsd32_preadv(p, v, retval) 4954 struct proc *p; 4955 void *v; 4956 register_t *retval; 4957 { 4958 struct netbsd32_preadv_args /* { 4959 syscallarg(int) fd; 4960 syscallarg(const netbsd32_iovecp_t) iovp; 4961 syscallarg(int) iovcnt; 4962 syscallarg(int) pad; 4963 syscallarg(off_t) offset; 4964 } */ *uap = v; 4965 struct filedesc *fdp = p->p_fd; 4966 struct file *fp; 4967 struct vnode *vp; 4968 off_t offset; 4969 int error, fd = SCARG(uap, fd); 4970 4971 if ((u_int)fd >= fdp->fd_nfiles || 4972 (fp = fdp->fd_ofiles[fd]) == NULL || 4973 (fp->f_flag & FREAD) == 0) 4974 return (EBADF); 4975 4976 vp = (struct vnode *)fp->f_data; 4977 if (fp->f_type != DTYPE_VNODE 4978 || vp->v_type == VFIFO) 4979 return (ESPIPE); 4980 4981 offset = SCARG(uap, offset); 4982 4983 /* 4984 * XXX This works because no file systems actually 4985 * XXX take any action on the seek operation. 4986 */ 4987 if ((error = VOP_SEEK(vp, fp->f_offset, offset, fp->f_cred)) != 0) 4988 return (error); 4989 4990 return (dofilereadv32(p, fd, fp, (struct netbsd32_iovec *)(u_long)SCARG(uap, iovp), SCARG(uap, iovcnt), 4991 &offset, 0, retval)); 4992 } 4993 4994 int 4995 netbsd32_pwritev(p, v, retval) 4996 struct proc *p; 4997 void *v; 4998 register_t *retval; 4999 { 5000 struct netbsd32_pwritev_args /* { 5001 syscallarg(int) fd; 5002 syscallarg(const netbsd32_iovecp_t) iovp; 5003 syscallarg(int) iovcnt; 5004 syscallarg(int) pad; 5005 syscallarg(off_t) offset; 5006 } */ *uap = v; 5007 struct filedesc *fdp = p->p_fd; 5008 struct file *fp; 5009 struct vnode *vp; 5010 off_t offset; 5011 int error, fd = SCARG(uap, fd); 5012 5013 if ((u_int)fd >= fdp->fd_nfiles || 5014 (fp = fdp->fd_ofiles[fd]) == NULL || 5015 (fp->f_flag & FWRITE) == 0) 5016 return (EBADF); 5017 5018 vp = (struct vnode *)fp->f_data; 5019 if (fp->f_type != DTYPE_VNODE 5020 || vp->v_type == VFIFO) 5021 return (ESPIPE); 5022 5023 offset = SCARG(uap, offset); 5024 5025 /* 5026 * XXX This works because no file systems actually 5027 * XXX take any action on the seek operation. 5028 */ 5029 if ((error = VOP_SEEK(vp, fp->f_offset, offset, fp->f_cred)) != 0) 5030 return (error); 5031 5032 return (dofilewritev32(p, fd, fp, (struct netbsd32_iovec *)(u_long)SCARG(uap, iovp), SCARG(uap, iovcnt), 5033 &offset, 0, retval)); 5034 } 5035 5036 int 5037 compat_13_netbsd32_sigprocmask(p, v, retval) 5038 register struct proc *p; 5039 void *v; 5040 register_t *retval; 5041 { 5042 struct compat_13_netbsd32_sigprocmask_args /* { 5043 syscallarg(int) how; 5044 syscallarg(int) mask; 5045 } */ *uap = v; 5046 sigset13_t ness, oess; 5047 sigset_t nbss, obss; 5048 int error; 5049 5050 ness = SCARG(uap, mask); 5051 native_sigset13_to_sigset(&ness, &nbss); 5052 error = sigprocmask1(p, SCARG(uap, how), &nbss, &obss); 5053 if (error) 5054 return (error); 5055 native_sigset_to_sigset13(&obss, &oess); 5056 *retval = oess; 5057 return (0); 5058 } 5059 5060 int 5061 compat_13_netbsd32_sigsuspend(p, v, retval) 5062 register struct proc *p; 5063 void *v; 5064 register_t *retval; 5065 { 5066 struct compat_13_netbsd32_sigsuspend_args /* { 5067 syscallarg(sigset13_t) mask; 5068 } */ *uap = v; 5069 sigset13_t ess; 5070 sigset_t bss; 5071 5072 ess = SCARG(uap, mask); 5073 native_sigset13_to_sigset(&ess, &bss); 5074 return (sigsuspend1(p, &bss)); 5075 } 5076