1 /*- 2 * Copyright (c) 1982, 1986, 1991 The Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.proprietary.c% 6 * 7 * @(#)kern_exec.c 7.68 (Berkeley) 12/26/92 8 */ 9 10 #include <sys/param.h> 11 #include <sys/systm.h> 12 #include <sys/filedesc.h> 13 #include <sys/kernel.h> 14 #include <sys/proc.h> 15 #include <sys/mount.h> 16 #include <sys/malloc.h> 17 #include <sys/namei.h> 18 #include <sys/vnode.h> 19 #include <sys/file.h> 20 #include <sys/acct.h> 21 #include <sys/exec.h> 22 #include <sys/ktrace.h> 23 #include <sys/resourcevar.h> 24 25 #include <machine/cpu.h> 26 #include <machine/reg.h> 27 28 #include <sys/mman.h> 29 #include <vm/vm.h> 30 #include <vm/vm_param.h> 31 #include <vm/vm_map.h> 32 #include <vm/vm_kern.h> 33 #include <vm/vm_pager.h> 34 35 #include <sys/signalvar.h> 36 #include <sys/kinfo_proc.h> 37 38 #ifdef HPUXCOMPAT 39 #include <sys/user.h> /* for pcb */ 40 #include <hp/hpux/hpux_exec.h> 41 #endif 42 43 #ifdef COPY_SIGCODE 44 extern char sigcode[], esigcode[]; 45 #define szsigcode (esigcode - sigcode) 46 #else 47 #define szsigcode 0 48 #endif 49 50 /* 51 * exec system call 52 */ 53 struct execve_args { 54 char *fname; 55 char **argp; 56 char **envp; 57 }; 58 /* ARGSUSED */ 59 execve(p, uap, retval) 60 register struct proc *p; 61 register struct execve_args *uap; 62 int *retval; 63 { 64 register struct ucred *cred = p->p_ucred; 65 register struct filedesc *fdp = p->p_fd; 66 int na, ne, ucp, ap, cc, ssize; 67 register char *cp; 68 register int nc; 69 unsigned len; 70 int indir, uid, gid; 71 char *sharg; 72 struct vnode *vp; 73 int resid, error, paged = 0; 74 vm_offset_t execargs = 0; 75 struct vattr vattr; 76 char cfarg[MAXINTERP]; 77 union { 78 char ex_shell[MAXINTERP]; /* #! and interpreter name */ 79 struct exec ex_exec; 80 #ifdef HPUXCOMPAT 81 struct hpux_exec ex_hexec; 82 #endif 83 } exdata; 84 #ifdef HPUXCOMPAT 85 struct hpux_exec hhead; 86 #endif 87 struct nameidata nd; 88 struct ps_strings ps; 89 90 NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF | SAVENAME, UIO_USERSPACE, 91 uap->fname, p); 92 if (error = namei(&nd)) 93 return (error); 94 vp = nd.ni_vp; 95 indir = 0; 96 uid = cred->cr_uid; 97 gid = cred->cr_gid; 98 if (error = VOP_GETATTR(vp, &vattr, cred, p)) 99 goto bad; 100 if (vp->v_mount->mnt_flag & MNT_NOEXEC) { 101 error = EACCES; 102 goto bad; 103 } 104 if ((vp->v_mount->mnt_flag & MNT_NOSUID) == 0) { 105 if (vattr.va_mode & VSUID) 106 uid = vattr.va_uid; 107 if (vattr.va_mode & VSGID) 108 gid = vattr.va_gid; 109 } 110 111 again: 112 if (error = VOP_ACCESS(vp, VEXEC, cred, p)) 113 goto bad; 114 if ((p->p_flag & STRC) && (error = VOP_ACCESS(vp, VREAD, cred, p))) 115 goto bad; 116 if (vp->v_type != VREG || 117 (vattr.va_mode & (VEXEC|(VEXEC>>3)|(VEXEC>>6))) == 0) { 118 error = EACCES; 119 goto bad; 120 } 121 122 /* 123 * Read in first few bytes of file for segment sizes, magic number: 124 * OMAGIC = plain executable 125 * NMAGIC = RO text 126 * ZMAGIC = demand paged RO text 127 * Also an ASCII line beginning with #! is 128 * the file name of a ``shell'' and arguments may be prepended 129 * to the argument list if given here. 130 * 131 * SHELL NAMES ARE LIMITED IN LENGTH. 132 * 133 * ONLY ONE ARGUMENT MAY BE PASSED TO THE SHELL FROM 134 * THE ASCII LINE. 135 */ 136 exdata.ex_shell[0] = '\0'; /* for zero length files */ 137 error = vn_rdwr(UIO_READ, vp, (caddr_t)&exdata, sizeof (exdata), 138 (off_t)0, UIO_SYSSPACE, (IO_UNIT|IO_NODELOCKED), cred, &resid, 139 (struct proc *)0); 140 if (error) 141 goto bad; 142 #ifndef lint 143 if (resid > sizeof(exdata) - sizeof(exdata.ex_exec) && 144 exdata.ex_shell[0] != '#') { 145 error = ENOEXEC; 146 goto bad; 147 } 148 #endif 149 #if defined(hp300) || defined(luna68k) 150 switch ((int)exdata.ex_exec.a_mid) { 151 152 /* 153 * An ancient hp200 or hp300 binary, shouldn't happen anymore. 154 * Mark as invalid. 155 */ 156 case MID_ZERO: 157 exdata.ex_exec.a_magic = 0; 158 break; 159 160 /* 161 * HP200 series has a smaller page size so we cannot 162 * demand-load or even write protect text, so we just 163 * treat as OMAGIC. 164 */ 165 case MID_HP200: 166 exdata.ex_exec.a_magic = OMAGIC; 167 break; 168 169 case MID_HP300: 170 break; 171 172 #ifdef HPUXCOMPAT 173 case MID_HPUX: 174 /* 175 * Save a.out header. This is eventually saved in the pcb, 176 * but we cannot do that yet in case the exec fails before 177 * the image is overlayed. 178 */ 179 bcopy((caddr_t)&exdata.ex_hexec, 180 (caddr_t)&hhead, sizeof hhead); 181 /* 182 * If version number is 0x2bad this is a native BSD 183 * binary created via the HPUX SGS. Should not be 184 * treated as an HPUX binary. 185 */ 186 if (exdata.ex_hexec.ha_version != BSDVNUM) 187 paged |= SHPUX; /* XXX */ 188 /* 189 * Shuffle important fields to their BSD locations. 190 * Note that the order in which this is done is important. 191 */ 192 exdata.ex_exec.a_text = exdata.ex_hexec.ha_text; 193 exdata.ex_exec.a_data = exdata.ex_hexec.ha_data; 194 exdata.ex_exec.a_bss = exdata.ex_hexec.ha_bss; 195 exdata.ex_exec.a_entry = exdata.ex_hexec.ha_entry; 196 /* 197 * For ZMAGIC files, make sizes consistant with those 198 * generated by BSD ld. 199 */ 200 if (exdata.ex_exec.a_magic == ZMAGIC) { 201 exdata.ex_exec.a_text = 202 ctob(btoc(exdata.ex_exec.a_text)); 203 nc = exdata.ex_exec.a_data + exdata.ex_exec.a_bss; 204 exdata.ex_exec.a_data = 205 ctob(btoc(exdata.ex_exec.a_data)); 206 nc -= (int)exdata.ex_exec.a_data; 207 exdata.ex_exec.a_bss = (nc < 0) ? 0 : nc; 208 } 209 break; 210 #endif 211 } 212 #endif 213 switch ((int)exdata.ex_exec.a_magic) { 214 215 case OMAGIC: 216 #ifdef COFF 217 if (exdata.ex_exec.ex_fhdr.magic != COFF_MAGIC) { 218 error = ENOEXEC; 219 goto bad; 220 } 221 #endif 222 #ifdef sparc 223 if (exdata.ex_exec.a_mid != MID_SUN_SPARC) { 224 error = ENOEXEC; 225 goto bad; 226 } 227 #endif 228 exdata.ex_exec.a_data += exdata.ex_exec.a_text; 229 exdata.ex_exec.a_text = 0; 230 break; 231 232 case ZMAGIC: 233 #ifdef HPUXCOMPAT 234 paged |= 1; /* XXX fix me */ 235 #else 236 paged = 1; 237 #endif 238 /* FALLTHROUGH */ 239 240 case NMAGIC: 241 #ifdef COFF 242 if (exdata.ex_exec.ex_fhdr.magic != COFF_MAGIC) { 243 error = ENOEXEC; 244 goto bad; 245 } 246 #endif 247 #ifdef sparc 248 if (exdata.ex_exec.a_mid != MID_SUN_SPARC) { 249 error = ENOEXEC; 250 goto bad; 251 } 252 #endif 253 if (exdata.ex_exec.a_text == 0) { 254 error = ENOEXEC; 255 goto bad; 256 } 257 break; 258 259 default: 260 if (exdata.ex_shell[0] != '#' || 261 exdata.ex_shell[1] != '!' || 262 indir) { 263 error = ENOEXEC; 264 goto bad; 265 } 266 for (cp = &exdata.ex_shell[2];; ++cp) { 267 if (cp >= &exdata.ex_shell[MAXINTERP]) { 268 error = ENOEXEC; 269 goto bad; 270 } 271 if (*cp == '\n') { 272 *cp = '\0'; 273 break; 274 } 275 if (*cp == '\t') 276 *cp = ' '; 277 } 278 cp = &exdata.ex_shell[2]; 279 while (*cp == ' ') 280 cp++; 281 nd.ni_dirp = cp; 282 while (*cp && *cp != ' ') 283 cp++; 284 cfarg[0] = '\0'; 285 if (*cp) { 286 *cp++ = '\0'; 287 while (*cp == ' ') 288 cp++; 289 if (*cp) 290 bcopy((caddr_t)cp, (caddr_t)cfarg, MAXINTERP); 291 } 292 indir = 1; 293 vput(vp); 294 nd.ni_segflg = UIO_SYSSPACE; 295 if (error = namei(&nd)) 296 return (error); 297 vp = nd.ni_vp; 298 if (error = VOP_GETATTR(vp, &vattr, cred, p)) 299 goto bad; 300 uid = cred->cr_uid; /* shell scripts can't be setuid */ 301 gid = cred->cr_gid; 302 goto again; 303 } 304 305 /* 306 * Collect arguments on "file" in swap space. 307 */ 308 na = 0; 309 ne = 0; 310 nc = 0; 311 cc = NCARGS; 312 execargs = kmem_alloc_wait(exec_map, NCARGS); 313 #ifdef DIAGNOSTIC 314 if (execargs == (vm_offset_t)0) 315 panic("execve: kmem_alloc_wait"); 316 #endif 317 cp = (char *) execargs; 318 /* 319 * Copy arguments into file in argdev area. 320 */ 321 if (uap->argp) for (;;) { 322 ap = NULL; 323 sharg = NULL; 324 if (indir && na == 0) { 325 sharg = nd.ni_cnd.cn_nameptr; 326 ap = (int)sharg; 327 uap->argp++; /* ignore argv[0] */ 328 } else if (indir && (na == 1 && cfarg[0])) { 329 sharg = cfarg; 330 ap = (int)sharg; 331 } else if (indir && (na == 1 || na == 2 && cfarg[0])) 332 ap = (int)uap->fname; 333 else if (uap->argp) { 334 ap = fuword((caddr_t)uap->argp); 335 uap->argp++; 336 } 337 if (ap == NULL && uap->envp) { 338 uap->argp = NULL; 339 if ((ap = fuword((caddr_t)uap->envp)) != NULL) 340 uap->envp++, ne++; 341 } 342 if (ap == NULL) 343 break; 344 na++; 345 if (ap == -1) { 346 error = EFAULT; 347 goto bad; 348 } 349 do { 350 if (nc >= NCARGS-1) { 351 error = E2BIG; 352 break; 353 } 354 if (sharg) { 355 error = copystr(sharg, cp, (unsigned)cc, &len); 356 sharg += len; 357 } else { 358 error = copyinstr((caddr_t)ap, cp, (unsigned)cc, 359 &len); 360 ap += len; 361 } 362 cp += len; 363 nc += len; 364 cc -= len; 365 } while (error == ENAMETOOLONG); 366 if (error) 367 goto bad; 368 } 369 370 /* 371 * XXX the following is excessively bogus 372 * 373 * Compute initial process stack size and location of argc 374 * and character strings. `nc' is currently just the number 375 * of characters of arg and env strings. 376 * 377 * nc = size of ps_strings structure + 378 * size of signal code + 379 * 4 bytes of NULL pointer + 380 * nc, 381 * rounded to nearest integer; 382 * ucp = USRSTACK - nc; [user characters pointer] 383 * apsize = padding (if any) + 384 * 4 bytes of NULL pointer + 385 * ne 4-byte pointers to env strings + 386 * 4 bytes of NULL pointer + 387 * (na-ne) 4-byte pointers to arg strings + 388 * 4 bytes of argc; 389 * (this is the same as nc + (na+3)*4) 390 * ap = ucp - apsize; [user address of argc] 391 * ssize = ssize + nc + machine-dependent space; 392 */ 393 nc = (sizeof(ps) + szsigcode + 4 + nc + NBPW-1) & ~(NBPW - 1); 394 #if defined(sparc) || defined(mips) 395 ucp = USRSTACK; 396 ssize = ALIGN(nc + (na + 3) * NBPW); 397 ap = ucp - ssize; 398 ucp -= nc; 399 #ifdef sparc 400 ssize += sizeof(struct rwindow); 401 #endif 402 #else 403 ssize = (na + 3) * NBPW; 404 ucp = USRSTACK - nc; 405 ap = ucp - ssize; 406 ssize += nc; 407 #endif 408 error = getxfile(p, vp, &exdata.ex_exec, paged, ssize, uid, gid); 409 if (error) 410 goto bad; 411 vput(vp); 412 vp = NULL; 413 414 #ifdef HPUXCOMPAT 415 /* 416 * We are now committed to the exec so we can save the exec 417 * header in the pcb where we can dump it if necessary in core() 418 */ 419 if (p->p_addr->u_pcb.pcb_flags & PCB_HPUXBIN) 420 bcopy((caddr_t)&hhead, 421 (caddr_t)p->p_addr->u_pcb.pcb_exec, sizeof hhead); 422 #endif 423 424 /* 425 * Copy back arglist. 426 */ 427 cpu_setstack(p, ap); 428 (void) suword((caddr_t)ap, na-ne); 429 nc = 0; 430 cp = (char *) execargs; 431 cc = NCARGS; 432 ps.ps_argvstr = (char *)ucp; /* first argv string */ 433 ps.ps_nargvstr = na - ne; /* argc */ 434 for (;;) { 435 ap += NBPW; 436 if (na == ne) { 437 (void) suword((caddr_t)ap, 0); 438 ap += NBPW; 439 ps.ps_envstr = (char *)ucp; 440 ps.ps_nenvstr = ne; 441 } 442 if (--na < 0) 443 break; 444 (void) suword((caddr_t)ap, ucp); 445 do { 446 error = copyoutstr(cp, (caddr_t)ucp, (unsigned)cc, 447 &len); 448 ucp += len; 449 cp += len; 450 nc += len; 451 cc -= len; 452 } while (error == ENAMETOOLONG); 453 if (error == EFAULT) 454 panic("exec: EFAULT"); 455 } 456 (void) suword((caddr_t)ap, 0); 457 (void) copyout((caddr_t)&ps, (caddr_t)PS_STRINGS, sizeof(ps)); 458 459 execsigs(p); 460 461 for (nc = fdp->fd_lastfile; nc >= 0; --nc) { 462 if (fdp->fd_ofileflags[nc] & UF_EXCLOSE) { 463 (void) closef(fdp->fd_ofiles[nc], p); 464 fdp->fd_ofiles[nc] = NULL; 465 fdp->fd_ofileflags[nc] = 0; 466 if (nc < fdp->fd_freefile) 467 fdp->fd_freefile = nc; 468 } 469 fdp->fd_ofileflags[nc] &= ~UF_MAPPED; 470 } 471 /* 472 * Adjust fd_lastfile to account for descriptors closed above. 473 * Don't decrement fd_lastfile past 0, as it's unsigned. 474 */ 475 while (fdp->fd_lastfile > 0 && fdp->fd_ofiles[fdp->fd_lastfile] == NULL) 476 fdp->fd_lastfile--; 477 setregs(p, exdata.ex_exec.a_entry, retval); 478 #ifdef COPY_SIGCODE 479 /* 480 * Install sigcode at top of user stack. 481 */ 482 copyout((caddr_t)sigcode, (caddr_t)PS_STRINGS - szsigcode, szsigcode); 483 #endif 484 /* 485 * Remember file name for accounting. 486 */ 487 p->p_acflag &= ~AFORK; 488 if (nd.ni_cnd.cn_namelen > MAXCOMLEN) 489 nd.ni_cnd.cn_namelen = MAXCOMLEN; 490 bcopy((caddr_t)nd.ni_cnd.cn_nameptr, (caddr_t)p->p_comm, 491 (unsigned)nd.ni_cnd.cn_namelen); 492 p->p_comm[nd.ni_cnd.cn_namelen] = '\0'; 493 cpu_exec(p); 494 bad: 495 FREE(nd.ni_cnd.cn_pnbuf, M_NAMEI); 496 if (execargs) 497 kmem_free_wakeup(exec_map, execargs, NCARGS); 498 if (vp) 499 vput(vp); 500 return (error); 501 } 502 503 /* 504 * Read in and set up memory for executed file. 505 */ 506 getxfile(p, vp, ep, paged, ssize, uid, gid) 507 register struct proc *p; 508 register struct vnode *vp; 509 register struct exec *ep; 510 int paged, ssize, uid, gid; 511 { 512 register struct ucred *cred = p->p_ucred; 513 register struct vmspace *vm = p->p_vmspace; 514 vm_offset_t addr; 515 vm_size_t xts, size; 516 segsz_t ds; 517 off_t toff; 518 int error = 0; 519 520 #ifdef HPUXCOMPAT 521 int hpux = (paged & SHPUX); 522 paged &= ~SHPUX; 523 if (ep->a_mid == MID_HPUX) 524 toff = paged ? CLBYTES : sizeof(struct hpux_exec); 525 else 526 #endif 527 #ifdef COFF 528 toff = N_TXTOFF(*ep); 529 #else 530 #ifdef sparc 531 if (ep->a_mid == MID_SUN_SPARC) 532 toff = paged ? 0 : sizeof(struct exec); 533 else 534 #endif 535 if (paged) 536 toff = CLBYTES; 537 else 538 toff = sizeof (struct exec); 539 #endif 540 if (ep->a_text != 0 && (vp->v_flag & VTEXT) == 0 && 541 vp->v_writecount != 0) 542 return (ETXTBSY); 543 544 /* 545 * Compute text and data sizes and make sure not too large. 546 * Text size is rounded to an ``ld page''; data+bss is left 547 * in machine pages. Check data and bss separately as they 548 * may overflow when summed together. (XXX not done yet) 549 */ 550 xts = roundup(ep->a_text, __LDPGSZ); 551 ds = clrnd(btoc(ep->a_data + ep->a_bss)); 552 553 /* 554 * If we're sharing the address space, allocate a new space 555 * and release our reference to the old one. Otherwise, 556 * empty out the existing vmspace. 557 */ 558 #ifdef sparc 559 kill_user_windows(p); /* before addrs go away */ 560 #endif 561 if (vm->vm_refcnt > 1) { 562 p->p_vmspace = vmspace_alloc(VM_MIN_ADDRESS, 563 VM_MAXUSER_ADDRESS, 1); 564 vmspace_free(vm); 565 vm = p->p_vmspace; 566 } else { 567 #ifdef SYSVSHM 568 if (vm->vm_shm) 569 shmexit(p); 570 #endif 571 (void) vm_map_remove(&vm->vm_map, VM_MIN_ADDRESS, 572 VM_MAXUSER_ADDRESS); 573 } 574 /* 575 * If parent is waiting for us to exec or exit, 576 * SPPWAIT will be set; clear it and wakeup parent. 577 */ 578 if (p->p_flag & SPPWAIT) { 579 p->p_flag &= ~SPPWAIT; 580 wakeup((caddr_t) p->p_pptr); 581 } 582 #ifdef HPUXCOMPAT 583 p->p_addr->u_pcb.pcb_flags &= ~(PCB_HPUXMMAP|PCB_HPUXBIN); 584 /* remember that we were loaded from an HPUX format file */ 585 if (ep->a_mid == MID_HPUX) 586 p->p_addr->u_pcb.pcb_flags |= PCB_HPUXBIN; 587 if (hpux) 588 p->p_flag |= SHPUX; 589 else 590 p->p_flag &= ~SHPUX; 591 #endif 592 #ifdef ULTRIXCOMPAT 593 /* 594 * Always start out as an ULTRIX process. 595 * A system call in crt0.o will change us to BSD system calls later. 596 */ 597 p->p_md.md_flags |= MDP_ULTRIX; 598 #endif 599 p->p_flag |= SEXEC; 600 #ifndef COFF 601 addr = VM_MIN_ADDRESS; 602 if (vm_allocate(&vm->vm_map, &addr, xts + ctob(ds), FALSE)) { 603 uprintf("Cannot allocate text+data space\n"); 604 error = ENOMEM; /* XXX */ 605 goto badmap; 606 } 607 vm->vm_taddr = (caddr_t)VM_MIN_ADDRESS; 608 vm->vm_daddr = (caddr_t)(VM_MIN_ADDRESS + xts); 609 #else /* COFF */ 610 addr = (vm_offset_t)ep->ex_aout.codeStart; 611 vm->vm_taddr = (caddr_t)addr; 612 if (vm_allocate(&vm->vm_map, &addr, xts, FALSE)) { 613 uprintf("Cannot allocate text space\n"); 614 error = ENOMEM; /* XXX */ 615 goto badmap; 616 } 617 addr = (vm_offset_t)ep->ex_aout.heapStart; 618 vm->vm_daddr = (caddr_t)addr; 619 if (vm_allocate(&vm->vm_map, &addr, round_page(ctob(ds)), FALSE)) { 620 uprintf("Cannot allocate data space\n"); 621 error = ENOMEM; /* XXX */ 622 goto badmap; 623 } 624 #endif /* COFF */ 625 size = round_page(MAXSSIZ); /* XXX */ 626 #ifdef i386 627 addr = trunc_page(USRSTACK - size) - NBPG; /* XXX */ 628 #else 629 addr = trunc_page(USRSTACK - size); 630 #endif 631 if (vm_allocate(&vm->vm_map, &addr, size, FALSE)) { 632 uprintf("Cannot allocate stack space\n"); 633 error = ENOMEM; /* XXX */ 634 goto badmap; 635 } 636 size -= round_page(p->p_rlimit[RLIMIT_STACK].rlim_cur); 637 if (vm_map_protect(&vm->vm_map, addr, addr+size, VM_PROT_NONE, FALSE)) { 638 uprintf("Cannot protect stack space\n"); 639 error = ENOMEM; 640 goto badmap; 641 } 642 vm->vm_maxsaddr = (caddr_t)addr; 643 644 if (paged == 0) { 645 /* 646 * Read in data segment. 647 */ 648 (void) vn_rdwr(UIO_READ, vp, vm->vm_daddr, (int) ep->a_data, 649 (off_t)(toff + ep->a_text), UIO_USERSPACE, 650 (IO_UNIT|IO_NODELOCKED), cred, (int *)0, p); 651 /* 652 * Read in text segment if necessary (0410), 653 * and read-protect it. 654 */ 655 if (ep->a_text > 0) { 656 error = vn_rdwr(UIO_READ, vp, vm->vm_taddr, 657 (int)ep->a_text, toff, UIO_USERSPACE, 658 (IO_UNIT|IO_NODELOCKED), cred, (int *)0, p); 659 (void) vm_map_protect(&vm->vm_map, 660 (vm_offset_t)vm->vm_taddr, 661 (vm_offset_t)vm->vm_taddr + trunc_page(ep->a_text), 662 VM_PROT_READ|VM_PROT_EXECUTE, FALSE); 663 } 664 } else { 665 /* 666 * Allocate a region backed by the exec'ed vnode. 667 */ 668 #ifndef COFF 669 addr = VM_MIN_ADDRESS; 670 size = round_page(xts + ep->a_data); 671 error = vm_mmap(&vm->vm_map, &addr, size, VM_PROT_ALL, 672 MAP_COPY|MAP_FIXED, 673 (caddr_t)vp, (vm_offset_t)toff); 674 (void) vm_map_protect(&vm->vm_map, addr, addr + xts, 675 VM_PROT_READ|VM_PROT_EXECUTE, FALSE); 676 #else /* COFF */ 677 addr = (vm_offset_t)vm->vm_taddr; 678 size = xts; 679 error = vm_mmap(&vm->vm_map, &addr, size, 680 VM_PROT_READ|VM_PROT_EXECUTE, 681 MAP_COPY|MAP_FIXED, 682 (caddr_t)vp, (vm_offset_t)toff); 683 toff += size; 684 addr = (vm_offset_t)vm->vm_daddr; 685 size = round_page(ep->a_data); 686 error = vm_mmap(&vm->vm_map, &addr, size, VM_PROT_ALL, 687 MAP_COPY|MAP_FIXED, 688 (caddr_t)vp, (vm_offset_t)toff); 689 #endif /* COFF */ 690 vp->v_flag |= VTEXT; 691 } 692 if (error) { 693 badmap: 694 printf("pid %d: VM allocation failure\n", p->p_pid); 695 uprintf("sorry, pid %d was killed in exec: VM allocation\n", 696 p->p_pid); 697 psignal(p, SIGKILL); 698 p->p_flag |= SKEEP; 699 return(error); 700 } 701 702 /* 703 * set SUID/SGID protections, if no tracing 704 */ 705 p->p_flag &= ~SUGID; 706 if ((p->p_flag & STRC) == 0) { 707 if (uid != cred->cr_uid || gid != cred->cr_gid) { 708 p->p_ucred = cred = crcopy(cred); 709 /* 710 * If process is being ktraced, turn off - unless 711 * root set it. 712 */ 713 if (p->p_tracep && !(p->p_traceflag & KTRFAC_ROOT)) { 714 vrele(p->p_tracep); 715 p->p_tracep = NULL; 716 p->p_traceflag = 0; 717 } 718 cred->cr_uid = uid; 719 cred->cr_gid = gid; 720 p->p_flag |= SUGID; 721 } 722 } else 723 psignal(p, SIGTRAP); 724 p->p_cred->p_svuid = cred->cr_uid; 725 p->p_cred->p_svgid = cred->cr_gid; 726 vm->vm_tsize = btoc(xts); 727 vm->vm_dsize = ds; 728 vm->vm_ssize = btoc(ssize); 729 if (p->p_flag & SPROFIL) 730 stopprofclock(p); 731 #if defined(tahoe) 732 /* move this when tahoe cpu_exec is created */ 733 p->p_addr->u_pcb.pcb_savacc.faddr = (float *)NULL; 734 #endif 735 return (0); 736 } 737