1 /* 2 * Copyright (c) 1988 University of Utah. 3 * Copyright (c) 1992 OMRON Corporation. 4 * Copyright (c) 1982, 1986, 1990, 1992 The Regents of the University of California. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to Berkeley by 8 * the Systems Programming Group of the University of Utah Computer 9 * Science Department. 10 * 11 * %sccs.include.redist.c% 12 * 13 * from: Utah $Hdr: machdep.c 1.63 91/04/24$ 14 * from: hp300/hp300/machdep.c 7.36 (Berkeley) 2/10/93 15 * 16 * @(#)machdep.c 7.10 (Berkeley) 05/12/93 17 */ 18 19 #include <sys/param.h> 20 #include <sys/systm.h> 21 #include <sys/signalvar.h> 22 #include <sys/kernel.h> 23 #include <sys/map.h> 24 #include <sys/proc.h> 25 #include <sys/buf.h> 26 #include <sys/reboot.h> 27 #include <sys/conf.h> 28 #include <sys/file.h> 29 #include <sys/clist.h> 30 #include <sys/callout.h> 31 #include <sys/malloc.h> 32 #include <sys/mbuf.h> 33 #include <sys/msgbuf.h> 34 #include <sys/mount.h> 35 #include <sys/user.h> 36 #include <sys/exec.h> 37 #ifdef SYSVSHM 38 #include <sys/shm.h> 39 #endif 40 41 #include <machine/cpu.h> 42 #include <machine/reg.h> 43 #include <machine/psl.h> 44 #include <luna68k/luna68k/pte.h> 45 #include <net/netisr.h> 46 47 #define MAXMEM 64*1024*CLSIZE /* XXX - from cmap.h */ 48 #include <vm/vm_kern.h> 49 50 /* the following is used externally (sysctl_hw) */ 51 char machine[] = "luna68k"; /* cpu "architecture" */ 52 53 vm_map_t buffer_map; 54 extern vm_offset_t avail_end; 55 56 /* 57 * Declare these as initialized data so we can patch them. 58 */ 59 int nswbuf = 0; 60 #ifdef NBUF 61 int nbuf = NBUF; 62 #else 63 int nbuf = 0; 64 #endif 65 #ifdef BUFPAGES 66 int bufpages = BUFPAGES; 67 #else 68 int bufpages = 0; 69 #endif 70 int msgbufmapped; /* set when safe to use msgbuf */ 71 int maxmem; /* max memory per process */ 72 int physmem = MAXMEM; /* max supported memory, changes to actual */ 73 /* 74 * safepri is a safe priority for sleep to set for a spin-wait 75 * during autoconfiguration or after a panic. 76 */ 77 int safepri = PSL_LOWIPL; 78 79 extern u_int lowram; 80 extern short exframesize[]; 81 82 #ifdef FPCOPROC 83 int fpptype = -1; 84 #endif 85 86 /* 87 * Console initialization: called early on from main, 88 * before vm init or startup. Do enough configuration 89 * to choose and initialize a console. 90 */ 91 consinit() 92 { 93 94 /* 95 * Set cpuspeed immediately since cninit() called routines 96 * might use delay. 97 */ 98 99 cpuspeed = MHZ_25; 100 101 /* 102 * Find what hardware is attached to this machine. 103 */ 104 find_devs(); 105 106 /* 107 * Initialize the console before we print anything out. 108 */ 109 cninit(); 110 } 111 112 /* 113 * cpu_startup: allocate memory for variable-sized tables, 114 * initialize cpu, and do autoconfiguration. 115 */ 116 cpu_startup() 117 { 118 register unsigned i; 119 register caddr_t v, firstaddr; 120 int base, residual; 121 vm_offset_t minaddr, maxaddr; 122 vm_size_t size; 123 #ifdef DEBUG 124 extern int pmapdebug; 125 int opmapdebug = pmapdebug; 126 127 pmapdebug = 0; 128 #endif 129 /* 130 * Initialize error message buffer (at end of core). 131 */ 132 for (i = 0; i < btoc(sizeof (struct msgbuf)); i++) 133 pmap_enter(kernel_pmap, (vm_offset_t)msgbufp, 134 avail_end + i * NBPG, VM_PROT_ALL, TRUE); 135 msgbufmapped = 1; 136 137 /* 138 * Good {morning,afternoon,evening,night}. 139 */ 140 printf(version); 141 identifyfpu(); 142 printf("real mem = %d\n", ctob(physmem)); 143 144 /* 145 * Allocate space for system data structures. 146 * The first available real memory address is in "firstaddr". 147 * The first available kernel virtual address is in "v". 148 * As pages of kernel virtual memory are allocated, "v" is incremented. 149 * As pages of memory are allocated and cleared, 150 * "firstaddr" is incremented. 151 * An index into the kernel page table corresponding to the 152 * virtual memory address maintained in "v" is kept in "mapaddr". 153 */ 154 /* 155 * Make two passes. The first pass calculates how much memory is 156 * needed and allocates it. The second pass assigns virtual 157 * addresses to the various data structures. 158 */ 159 firstaddr = 0; 160 again: 161 v = (caddr_t)firstaddr; 162 163 #define valloc(name, type, num) \ 164 (name) = (type *)v; v = (caddr_t)((name)+(num)) 165 #define valloclim(name, type, num, lim) \ 166 (name) = (type *)v; v = (caddr_t)((lim) = ((name)+(num))) 167 valloc(cfree, struct cblock, nclist); 168 valloc(callout, struct callout, ncallout); 169 valloc(swapmap, struct map, nswapmap = maxproc * 2); 170 #ifdef SYSVSHM 171 valloc(shmsegs, struct shmid_ds, shminfo.shmmni); 172 #endif 173 174 /* 175 * Determine how many buffers to allocate. 176 * Since HPs tend to be long on memory and short on disk speed, 177 * we allocate more buffer space than the BSD standard of 178 * use 10% of memory for the first 2 Meg, 5% of remaining. 179 * We just allocate a flat 10%. Insure a minimum of 16 buffers. 180 * We allocate 1/2 as many swap buffer headers as file i/o buffers. 181 */ 182 if (bufpages == 0) 183 bufpages = physmem / 10 / CLSIZE; 184 if (nbuf == 0) { 185 nbuf = bufpages; 186 if (nbuf < 16) 187 nbuf = 16; 188 } 189 if (nswbuf == 0) { 190 nswbuf = (nbuf / 2) &~ 1; /* force even */ 191 if (nswbuf > 256) 192 nswbuf = 256; /* sanity */ 193 } 194 valloc(swbuf, struct buf, nswbuf); 195 valloc(buf, struct buf, nbuf); 196 /* 197 * End of first pass, size has been calculated so allocate memory 198 */ 199 if (firstaddr == 0) { 200 size = (vm_size_t)(v - firstaddr); 201 firstaddr = (caddr_t) kmem_alloc(kernel_map, round_page(size)); 202 if (firstaddr == 0) 203 panic("startup: no room for tables"); 204 goto again; 205 } 206 /* 207 * End of second pass, addresses have been assigned 208 */ 209 if ((vm_size_t)(v - firstaddr) != size) 210 panic("startup: table size inconsistency"); 211 /* 212 * Now allocate buffers proper. They are different than the above 213 * in that they usually occupy more virtual memory than physical. 214 */ 215 size = MAXBSIZE * nbuf; 216 buffer_map = kmem_suballoc(kernel_map, (vm_offset_t *)&buffers, 217 &maxaddr, size, FALSE); 218 minaddr = (vm_offset_t)buffers; 219 if (vm_map_find(buffer_map, vm_object_allocate(size), (vm_offset_t)0, 220 &minaddr, size, FALSE) != KERN_SUCCESS) 221 panic("startup: cannot allocate buffers"); 222 base = bufpages / nbuf; 223 residual = bufpages % nbuf; 224 for (i = 0; i < nbuf; i++) { 225 vm_size_t curbufsize; 226 vm_offset_t curbuf; 227 228 /* 229 * First <residual> buffers get (base+1) physical pages 230 * allocated for them. The rest get (base) physical pages. 231 * 232 * The rest of each buffer occupies virtual space, 233 * but has no physical memory allocated for it. 234 */ 235 curbuf = (vm_offset_t)buffers + i * MAXBSIZE; 236 curbufsize = CLBYTES * (i < residual ? base+1 : base); 237 vm_map_pageable(buffer_map, curbuf, curbuf+curbufsize, FALSE); 238 vm_map_simplify(buffer_map, curbuf); 239 } 240 /* 241 * Allocate a submap for exec arguments. This map effectively 242 * limits the number of processes exec'ing at any time. 243 */ 244 exec_map = kmem_suballoc(kernel_map, &minaddr, &maxaddr, 245 16*NCARGS, TRUE); 246 /* 247 * Allocate a submap for physio 248 */ 249 phys_map = kmem_suballoc(kernel_map, &minaddr, &maxaddr, 250 VM_PHYS_SIZE, TRUE); 251 252 /* 253 * Finally, allocate mbuf pool. Since mclrefcnt is an off-size 254 * we use the more space efficient malloc in place of kmem_alloc. 255 */ 256 mclrefcnt = (char *)malloc(NMBCLUSTERS+CLBYTES/MCLBYTES, 257 M_MBUF, M_NOWAIT); 258 bzero(mclrefcnt, NMBCLUSTERS+CLBYTES/MCLBYTES); 259 mb_map = kmem_suballoc(kernel_map, (vm_offset_t *)&mbutl, &maxaddr, 260 VM_MBUF_SIZE, FALSE); 261 /* 262 * Initialize callouts 263 */ 264 callfree = callout; 265 for (i = 1; i < ncallout; i++) 266 callout[i-1].c_next = &callout[i]; 267 callout[i-1].c_next = NULL; 268 269 #ifdef DEBUG 270 pmapdebug = opmapdebug; 271 #endif 272 printf("avail mem = %d\n", ptoa(cnt.v_free_count)); 273 printf("using %d buffers containing %d bytes of memory\n", 274 nbuf, bufpages * CLBYTES); 275 /* 276 * Set up CPU-specific registers, cache, etc. 277 */ 278 initcpu(); 279 280 /* 281 * Set up buffers, so they can be used to read disk labels. 282 */ 283 bufinit(); 284 285 /* 286 * Configure the system. 287 */ 288 configure(); 289 } 290 291 /* 292 * Set registers on exec. 293 * XXX Should clear registers except sp, pc, 294 * but would break init; should be fixed soon. 295 */ 296 setregs(p, entry, retval) 297 register struct proc *p; 298 u_long entry; 299 int retval[2]; 300 { 301 struct frame *frame = (struct frame *)p->p_md.md_regs; 302 303 frame->f_pc = entry & ~1; 304 #ifdef FPCOPROC 305 /* restore a null state frame */ 306 p->p_addr->u_pcb.pcb_fpregs.fpf_null = 0; 307 m68881_restore(&p->p_addr->u_pcb.pcb_fpregs); 308 #endif 309 } 310 311 extern char machine[]; 312 char cpu_model[120]; 313 extern char ostype[], osrelease[], version[]; 314 315 identifyfpu() 316 { 317 #ifdef LUNA2 318 if (machineid == LUNA_II) { 319 sprintf(cpu_model, "LUNA-II (25MHz MC68040 CPU+MMU+FPU)"); 320 printf("%s\n", cpu_model); 321 return; 322 } 323 #endif 324 if ( fpptype == -1 ) { 325 printf("unknow FPU type \n"); 326 panic("startup"); 327 } 328 sprintf(cpu_model, "LUNA-I (20MHz MC68030 CPU+MMU, 20MHz MC6888%d FPU)", fpptype); 329 printf("%s\n", cpu_model); 330 331 /* 332 printf("LUNA(20Mhz MC68030 CPU, 20Mhz MC6888%d FPU)\n",fpptype); 333 */ 334 } 335 336 #define SS_RTEFRAME 1 337 #define SS_FPSTATE 2 338 #define SS_USERREGS 4 339 340 struct sigstate { 341 int ss_flags; /* which of the following are valid */ 342 struct frame ss_frame; /* original exception frame */ 343 struct fpframe ss_fpstate; /* 68881/68882 state info */ 344 }; 345 346 /* 347 * WARNING: code in locore.s assumes the layout shown for sf_signum 348 * thru sf_handler so... don't screw with them! 349 */ 350 struct sigframe { 351 int sf_signum; /* signo for handler */ 352 int sf_code; /* additional info for handler */ 353 struct sigcontext *sf_scp; /* context ptr for handler */ 354 sig_t sf_handler; /* handler addr for u_sigc */ 355 struct sigstate sf_state; /* state of the hardware */ 356 struct sigcontext sf_sc; /* actual context */ 357 }; 358 359 #ifdef DEBUG 360 int sigdebug = 0; 361 int sigpid = 0; 362 #define SDB_FOLLOW 0x01 363 #define SDB_KSTACK 0x02 364 #define SDB_FPSTATE 0x04 365 #endif 366 367 /* 368 * Send an interrupt to process. 369 */ 370 void 371 sendsig(catcher, sig, mask, code) 372 sig_t catcher; 373 int sig, mask; 374 unsigned code; 375 { 376 register struct proc *p = curproc; 377 register struct sigframe *fp, *kfp; 378 register struct frame *frame; 379 register struct sigacts *psp = p->p_sigacts; 380 register short ft; 381 int oonstack, fsize; 382 extern char sigcode[], esigcode[]; 383 384 frame = (struct frame *)p->p_md.md_regs; 385 ft = frame->f_format; 386 oonstack = psp->ps_sigstk.ss_flags & SA_ONSTACK; 387 /* 388 * Allocate and validate space for the signal handler 389 * context. Note that if the stack is in P0 space, the 390 * call to grow() is a nop, and the useracc() check 391 * will fail if the process has not already allocated 392 * the space with a `brk'. 393 */ 394 fsize = sizeof(struct sigframe); 395 if ((psp->ps_flags & SAS_ALTSTACK) && 396 (psp->ps_sigstk.ss_flags & SA_ONSTACK) == 0 && 397 (psp->ps_sigonstack & sigmask(sig))) { 398 fp = (struct sigframe *)(psp->ps_sigstk.ss_base + 399 psp->ps_sigstk.ss_size - fsize); 400 psp->ps_sigstk.ss_flags |= SA_ONSTACK; 401 } else 402 fp = (struct sigframe *)(frame->f_regs[SP] - fsize); 403 if ((unsigned)fp <= USRSTACK - ctob(p->p_vmspace->vm_ssize)) 404 (void)grow(p, (unsigned)fp); 405 #ifdef DEBUG 406 if ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid) 407 printf("sendsig(%d): sig %d ssp %x usp %x scp %x ft %d\n", 408 p->p_pid, sig, &oonstack, fp, &fp->sf_sc, ft); 409 #endif 410 if (useracc((caddr_t)fp, fsize, B_WRITE) == 0) { 411 #ifdef DEBUG 412 if ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid) 413 printf("sendsig(%d): useracc failed on sig %d\n", 414 p->p_pid, sig); 415 #endif 416 /* 417 * Process has trashed its stack; give it an illegal 418 * instruction to halt it in its tracks. 419 */ 420 SIGACTION(p, SIGILL) = SIG_DFL; 421 sig = sigmask(SIGILL); 422 p->p_sigignore &= ~sig; 423 p->p_sigcatch &= ~sig; 424 p->p_sigmask &= ~sig; 425 psignal(p, SIGILL); 426 return; 427 } 428 kfp = (struct sigframe *)malloc((u_long)fsize, M_TEMP, M_WAITOK); 429 /* 430 * Build the argument list for the signal handler. 431 */ 432 kfp->sf_signum = sig; 433 kfp->sf_code = code; 434 kfp->sf_scp = &fp->sf_sc; 435 kfp->sf_handler = catcher; 436 /* 437 * Save necessary hardware state. Currently this includes: 438 * - general registers 439 * - original exception frame (if not a "normal" frame) 440 * - FP coprocessor state 441 */ 442 kfp->sf_state.ss_flags = SS_USERREGS; 443 bcopy((caddr_t)frame->f_regs, 444 (caddr_t)kfp->sf_state.ss_frame.f_regs, sizeof frame->f_regs); 445 if (ft >= FMT7) { 446 #ifdef DEBUG 447 if (ft != FMT9 && ft != FMTA && ft != FMTB) 448 panic("sendsig: bogus frame type"); 449 #endif 450 kfp->sf_state.ss_flags |= SS_RTEFRAME; 451 kfp->sf_state.ss_frame.f_format = frame->f_format; 452 kfp->sf_state.ss_frame.f_vector = frame->f_vector; 453 bcopy((caddr_t)&frame->F_u, 454 (caddr_t)&kfp->sf_state.ss_frame.F_u, exframesize[ft]); 455 /* 456 * Leave an indicator that we need to clean up the kernel 457 * stack. We do this by setting the "pad word" above the 458 * hardware stack frame to the amount the stack must be 459 * adjusted by. 460 * 461 * N.B. we increment rather than just set f_stackadj in 462 * case we are called from syscall when processing a 463 * sigreturn. In that case, f_stackadj may be non-zero. 464 */ 465 frame->f_stackadj += exframesize[ft]; 466 frame->f_format = frame->f_vector = 0; 467 #ifdef DEBUG 468 if (sigdebug & SDB_FOLLOW) 469 printf("sendsig(%d): copy out %d of frame %d\n", 470 p->p_pid, exframesize[ft], ft); 471 #endif 472 } 473 #ifdef FPCOPROC 474 kfp->sf_state.ss_flags |= SS_FPSTATE; 475 m68881_save(&kfp->sf_state.ss_fpstate); 476 #ifdef DEBUG 477 if ((sigdebug & SDB_FPSTATE) && *(char *)&kfp->sf_state.ss_fpstate) 478 printf("sendsig(%d): copy out FP state (%x) to %x\n", 479 p->p_pid, *(u_int *)&kfp->sf_state.ss_fpstate, 480 &kfp->sf_state.ss_fpstate); 481 #endif 482 #endif 483 /* 484 * Build the signal context to be used by sigreturn. 485 */ 486 kfp->sf_sc.sc_onstack = oonstack; 487 kfp->sf_sc.sc_mask = mask; 488 kfp->sf_sc.sc_sp = frame->f_regs[SP]; 489 kfp->sf_sc.sc_fp = frame->f_regs[A6]; 490 kfp->sf_sc.sc_ap = (int)&fp->sf_state; 491 kfp->sf_sc.sc_pc = frame->f_pc; 492 kfp->sf_sc.sc_ps = frame->f_sr; 493 (void) copyout((caddr_t)kfp, (caddr_t)fp, fsize); 494 frame->f_regs[SP] = (int)fp; 495 #ifdef DEBUG 496 if (sigdebug & SDB_FOLLOW) 497 printf("sendsig(%d): sig %d scp %x fp %x sc_sp %x sc_ap %x\n", 498 p->p_pid, sig, kfp->sf_scp, fp, 499 kfp->sf_sc.sc_sp, kfp->sf_sc.sc_ap); 500 #endif 501 /* 502 * Signal trampoline code is at base of user stack. 503 */ 504 frame->f_pc = (int)PS_STRINGS - (esigcode - sigcode); 505 #ifdef DEBUG 506 if ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid) 507 printf("sendsig(%d): sig %d returns\n", 508 p->p_pid, sig); 509 #endif 510 free((caddr_t)kfp, M_TEMP); 511 } 512 513 /* 514 * System call to cleanup state after a signal 515 * has been taken. Reset signal mask and 516 * stack state from context left by sendsig (above). 517 * Return to previous pc and psl as specified by 518 * context left by sendsig. Check carefully to 519 * make sure that the user has not modified the 520 * psl to gain improper priviledges or to cause 521 * a machine fault. 522 */ 523 struct sigreturn_args { 524 struct sigcontext *sigcntxp; 525 }; 526 /* ARGSUSED */ 527 sigreturn(p, uap, retval) 528 struct proc *p; 529 struct sigreturn_args *uap; 530 int *retval; 531 { 532 register struct sigcontext *scp; 533 register struct frame *frame; 534 register int rf; 535 struct sigcontext tsigc; 536 struct sigstate tstate; 537 int flags; 538 539 scp = uap->sigcntxp; 540 #ifdef DEBUG 541 if (sigdebug & SDB_FOLLOW) 542 printf("sigreturn: pid %d, scp %x\n", p->p_pid, scp); 543 #endif 544 if ((int)scp & 1) 545 return (EINVAL); 546 /* 547 * Test and fetch the context structure. 548 * We grab it all at once for speed. 549 */ 550 if (useracc((caddr_t)scp, sizeof (*scp), B_WRITE) == 0 || 551 copyin((caddr_t)scp, (caddr_t)&tsigc, sizeof tsigc)) 552 return (EINVAL); 553 scp = &tsigc; 554 if ((scp->sc_ps & (PSL_MBZ|PSL_IPL|PSL_S)) != 0) 555 return (EINVAL); 556 /* 557 * Restore the user supplied information 558 */ 559 if (scp->sc_onstack & 01) 560 p->p_sigacts->ps_sigstk.ss_flags |= SA_ONSTACK; 561 else 562 p->p_sigacts->ps_sigstk.ss_flags &= ~SA_ONSTACK; 563 p->p_sigmask = scp->sc_mask &~ sigcantmask; 564 frame = (struct frame *) p->p_md.md_regs; 565 frame->f_regs[SP] = scp->sc_sp; 566 frame->f_regs[A6] = scp->sc_fp; 567 frame->f_pc = scp->sc_pc; 568 frame->f_sr = scp->sc_ps; 569 /* 570 * Grab pointer to hardware state information. 571 * If zero, the user is probably doing a longjmp. 572 */ 573 if ((rf = scp->sc_ap) == 0) 574 return (EJUSTRETURN); 575 /* 576 * See if there is anything to do before we go to the 577 * expense of copying in close to 1/2K of data 578 */ 579 flags = fuword((caddr_t)rf); 580 #ifdef DEBUG 581 if (sigdebug & SDB_FOLLOW) 582 printf("sigreturn(%d): sc_ap %x flags %x\n", 583 p->p_pid, rf, flags); 584 #endif 585 /* 586 * fuword failed (bogus sc_ap value). 587 */ 588 if (flags == -1) 589 return (EINVAL); 590 if (flags == 0 || copyin((caddr_t)rf, (caddr_t)&tstate, sizeof tstate)) 591 return (EJUSTRETURN); 592 #ifdef DEBUG 593 if ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid) 594 printf("sigreturn(%d): ssp %x usp %x scp %x ft %d\n", 595 p->p_pid, &flags, scp->sc_sp, uap->sigcntxp, 596 (flags&SS_RTEFRAME) ? tstate.ss_frame.f_format : -1); 597 #endif 598 /* 599 * Restore most of the users registers except for A6 and SP 600 * which were handled above. 601 */ 602 if (flags & SS_USERREGS) 603 bcopy((caddr_t)tstate.ss_frame.f_regs, 604 (caddr_t)frame->f_regs, sizeof(frame->f_regs)-2*NBPW); 605 /* 606 * Restore long stack frames. Note that we do not copy 607 * back the saved SR or PC, they were picked up above from 608 * the sigcontext structure. 609 */ 610 if (flags & SS_RTEFRAME) { 611 register int sz; 612 613 /* grab frame type and validate */ 614 sz = tstate.ss_frame.f_format; 615 if (sz > 15 || (sz = exframesize[sz]) < 0) 616 return (EINVAL); 617 frame->f_stackadj -= sz; 618 frame->f_format = tstate.ss_frame.f_format; 619 frame->f_vector = tstate.ss_frame.f_vector; 620 bcopy((caddr_t)&tstate.ss_frame.F_u, (caddr_t)&frame->F_u, sz); 621 #ifdef DEBUG 622 if (sigdebug & SDB_FOLLOW) 623 printf("sigreturn(%d): copy in %d of frame type %d\n", 624 p->p_pid, sz, tstate.ss_frame.f_format); 625 #endif 626 } 627 #ifdef FPCOPROC 628 /* 629 * Finally we restore the original FP context 630 */ 631 if (flags & SS_FPSTATE) 632 m68881_restore(&tstate.ss_fpstate); 633 #ifdef DEBUG 634 if ((sigdebug & SDB_FPSTATE) && *(char *)&tstate.ss_fpstate) 635 printf("sigreturn(%d): copied in FP state (%x) at %x\n", 636 p->p_pid, *(u_int *)&tstate.ss_fpstate, 637 &tstate.ss_fpstate); 638 #endif 639 #endif 640 #ifdef DEBUG 641 if ((sigdebug & SDB_FOLLOW) || 642 ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid)) 643 printf("sigreturn(%d): returns\n", p->p_pid); 644 #endif 645 return (EJUSTRETURN); 646 } 647 648 int waittime = -1; 649 650 boot(howto) 651 register int howto; 652 { 653 /* take a snap shot before clobbering any registers */ 654 if (curproc) 655 savectx(curproc->p_addr, 0); 656 657 boothowto = howto; 658 if ((howto&RB_NOSYNC) == 0 && waittime < 0) { 659 register struct buf *bp; 660 int iter, nbusy; 661 662 waittime = 0; 663 (void) spl0(); 664 printf("syncing disks... "); 665 /* 666 * Release vnodes held by texts before sync. 667 */ 668 if (panicstr == 0) 669 vnode_pager_umount(NULL); 670 #ifdef notdef 671 #include "fd.h" 672 #if NFD > 0 673 fdshutdown(); 674 #endif 675 #endif 676 sync(&proc0, (void *)NULL, (int *)NULL); 677 678 for (iter = 0; iter < 20; iter++) { 679 nbusy = 0; 680 for (bp = &buf[nbuf]; --bp >= buf; ) 681 if ((bp->b_flags & (B_BUSY|B_INVAL)) == B_BUSY) 682 nbusy++; 683 if (nbusy == 0) 684 break; 685 printf("%d ", nbusy); 686 DELAY(40000 * iter); 687 } 688 if (nbusy) 689 printf("giving up\n"); 690 else 691 printf("done\n"); 692 693 /* 694 * If we've been adjusting the clock, the todr 695 * will be out of synch; adjust it now. 696 */ 697 resettodr(); 698 } 699 splhigh(); /* extreme priority */ 700 if (howto&RB_HALT) { 701 printf("halted\n\n"); 702 asm(" stop #0x2700"); 703 } else { 704 printf("\r\n\n"); 705 if (howto & RB_DUMP) 706 dumpsys(); 707 doboot(); 708 /*NOTREACHED*/ 709 } 710 /*NOTREACHED*/ 711 } 712 713 int dumpmag = 0x8fca0101; /* magic number for savecore */ 714 int dumpsize = 0; /* also for savecore */ 715 long dumplo = 0; 716 717 dumpconf() 718 { 719 int nblks; 720 721 dumpsize = physmem; 722 if (dumpdev != NODEV && bdevsw[major(dumpdev)].d_psize) { 723 nblks = (*bdevsw[major(dumpdev)].d_psize)(dumpdev); 724 if (dumpsize > btoc(dbtob(nblks - dumplo))) 725 dumpsize = btoc(dbtob(nblks - dumplo)); 726 else if (dumplo == 0) 727 dumplo = nblks - btodb(ctob(physmem)); 728 } 729 /* 730 * Don't dump on the first CLBYTES (why CLBYTES?) 731 * in case the dump device includes a disk label. 732 */ 733 if (dumplo < btodb(CLBYTES)) 734 dumplo = btodb(CLBYTES); 735 } 736 737 /* 738 * Doadump comes here after turning off memory management and 739 * getting on the dump stack, either when called above, or by 740 * the auto-restart code. 741 */ 742 dumpsys() 743 { 744 745 msgbufmapped = 0; 746 if (dumpdev == NODEV) 747 return; 748 /* 749 * For dumps during autoconfiguration, 750 * if dump device has already configured... 751 */ 752 if (dumpsize == 0) 753 dumpconf(); 754 if (dumplo < 0) 755 return; 756 printf("\ndumping to dev %x, offset %d\n", dumpdev, dumplo); 757 printf("dump "); 758 switch ((*bdevsw[major(dumpdev)].d_dump)(dumpdev)) { 759 760 case ENXIO: 761 printf("device bad\n"); 762 break; 763 764 case EFAULT: 765 printf("device not ready\n"); 766 break; 767 768 case EINVAL: 769 printf("area improper\n"); 770 break; 771 772 case EIO: 773 printf("i/o error\n"); 774 break; 775 776 default: 777 printf("succeeded\n"); 778 break; 779 } 780 } 781 782 initcpu() 783 { 784 parityenable(); 785 } 786 787 straytrap(pc, evec) 788 int pc; 789 u_short evec; 790 { 791 printf("unexpected trap (vector offset %x) from %x\n", 792 evec & 0xFFF, pc); 793 } 794 795 int *nofault; 796 797 badaddr(addr) 798 register caddr_t addr; 799 { 800 register int i; 801 label_t faultbuf; 802 803 #ifdef lint 804 i = *addr; if (i) return(0); 805 #endif 806 nofault = (int *) &faultbuf; 807 if (setjmp((label_t *)nofault)) { 808 nofault = (int *) 0; 809 return(1); 810 } 811 i = *(volatile short *)addr; 812 nofault = (int *) 0; 813 return(0); 814 } 815 816 badbaddr(addr) 817 register caddr_t addr; 818 { 819 register int i; 820 label_t faultbuf; 821 822 #ifdef lint 823 i = *addr; if (i) return(0); 824 #endif 825 nofault = (int *) &faultbuf; 826 if (setjmp((label_t *)nofault)) { 827 nofault = (int *) 0; 828 return(1); 829 } 830 i = *(volatile char *)addr; 831 nofault = (int *) 0; 832 return(0); 833 } 834 835 netintr() 836 { 837 #ifdef INET 838 if (netisr & (1 << NETISR_ARP)) { 839 netisr &= ~(1 << NETISR_ARP); 840 arpintr(); 841 } 842 if (netisr & (1 << NETISR_IP)) { 843 netisr &= ~(1 << NETISR_IP); 844 ipintr(); 845 } 846 #endif 847 #ifdef NS 848 if (netisr & (1 << NETISR_NS)) { 849 netisr &= ~(1 << NETISR_NS); 850 nsintr(); 851 } 852 #endif 853 #ifdef ISO 854 if (netisr & (1 << NETISR_ISO)) { 855 netisr &= ~(1 << NETISR_ISO); 856 clnlintr(); 857 } 858 #endif 859 #ifdef CCITT 860 if (netisr & (1 << NETISR_CCITT)) { 861 netisr &= ~(1 << NETISR_CCITT); 862 ccittintr(); 863 } 864 #endif 865 } 866 867 #ifdef notfdef 868 intrhand(sr) 869 int sr; 870 { 871 register struct isr *isr; 872 register int found = 0; 873 register int ipl; 874 extern struct isr isrqueue[]; 875 876 ipl = (sr >> 8) & 7; 877 switch (ipl) { 878 879 case 3: 880 case 4: 881 case 5: 882 ipl = ISRIPL(ipl); 883 isr = isrqueue[ipl].isr_forw; 884 for (; isr != &isrqueue[ipl]; isr = isr->isr_forw) { 885 if ((isr->isr_intr)(isr->isr_arg)) { 886 found++; 887 break; 888 } 889 } 890 if (found == 0) 891 printf("stray interrupt, sr 0x%x\n", sr); 892 break; 893 894 case 0: 895 case 1: 896 case 2: 897 case 6: 898 case 7: 899 printf("intrhand: unexpected sr 0x%x\n", sr); 900 break; 901 } 902 } 903 #endif 904 905 #if defined(DEBUG) && !defined(PANICBUTTON) 906 #define PANICBUTTON 907 #endif 908 909 #ifdef PANICBUTTON 910 int panicbutton = 1; /* non-zero if panic buttons are enabled */ 911 int crashandburn = 0; 912 int candbdelay = 50; /* give em half a second */ 913 914 void 915 candbtimer(arg) 916 void *arg; 917 { 918 919 crashandburn = 0; 920 } 921 #endif 922 923 /* 924 * Level 7 interrupts can be caused by the keyboard or parity errors. 925 */ 926 nmihand(frame) 927 struct frame frame; 928 { 929 #ifdef PANICBUTTON 930 static int innmihand = 0; 931 932 /* 933 * Attempt to reduce the window of vulnerability for recursive 934 * NMIs (e.g. someone holding down the keyboard reset button). 935 */ 936 if (innmihand == 0) { 937 innmihand = 1; 938 printf("Got a keyboard NMI\n"); 939 innmihand = 0; 940 } 941 if (panicbutton) { 942 if (crashandburn) { 943 crashandburn = 0; 944 panic(panicstr ? 945 "forced crash, nosync" : "forced crash"); 946 } 947 crashandburn++; 948 timeout(candbtimer, (void *)0, candbdelay); 949 } 950 #endif 951 return; 952 } 953 954 regdump(fp, sbytes) 955 struct frame *fp; /* must not be register */ 956 int sbytes; 957 { 958 static int doingdump = 0; 959 register int i; 960 int s; 961 extern char *hexstr(); 962 963 if (doingdump) 964 return; 965 s = splhigh(); 966 doingdump = 1; 967 printf("pid = %d, pc = %s, ", 968 curproc ? curproc->p_pid : -1, hexstr(fp->f_pc, 8)); 969 printf("ps = %s, ", hexstr(fp->f_sr, 4)); 970 printf("sfc = %s, ", hexstr(getsfc(), 4)); 971 printf("dfc = %s\n", hexstr(getdfc(), 4)); 972 printf("Registers:\n "); 973 for (i = 0; i < 8; i++) 974 printf(" %d", i); 975 printf("\ndreg:"); 976 for (i = 0; i < 8; i++) 977 printf(" %s", hexstr(fp->f_regs[i], 8)); 978 printf("\nareg:"); 979 for (i = 0; i < 8; i++) 980 printf(" %s", hexstr(fp->f_regs[i+8], 8)); 981 if (sbytes > 0) { 982 if (fp->f_sr & PSL_S) { 983 printf("\n\nKernel stack (%s):", 984 hexstr((int)(((int *)&fp)-1), 8)); 985 dumpmem(((int *)&fp)-1, sbytes, 0); 986 } else { 987 printf("\n\nUser stack (%s):", hexstr(fp->f_regs[SP], 8)); 988 dumpmem((int *)fp->f_regs[SP], sbytes, 1); 989 } 990 } 991 doingdump = 0; 992 splx(s); 993 } 994 995 extern char kstack[]; 996 #define KSADDR ((int *)&(kstack[(UPAGES-1)*NBPG])) 997 998 dumpmem(ptr, sz, ustack) 999 register int *ptr; 1000 int sz; 1001 { 1002 register int i, val; 1003 extern char *hexstr(); 1004 1005 for (i = 0; i < sz; i++) { 1006 if ((i & 7) == 0) 1007 printf("\n%s: ", hexstr((int)ptr, 6)); 1008 else 1009 printf(" "); 1010 if (ustack == 1) { 1011 if ((val = fuword(ptr++)) == -1) 1012 break; 1013 } else { 1014 if (ustack == 0 && 1015 (ptr < KSADDR || ptr > KSADDR+(NBPG/4-1))) 1016 break; 1017 val = *ptr++; 1018 } 1019 printf("%s", hexstr(val, 8)); 1020 } 1021 printf("\n"); 1022 } 1023 1024 char * 1025 hexstr(val, len) 1026 register int val; 1027 { 1028 static char nbuf[9]; 1029 register int x, i; 1030 1031 if (len > 8) 1032 return(""); 1033 nbuf[len] = '\0'; 1034 for (i = len-1; i >= 0; --i) { 1035 x = val & 0xF; 1036 if (x > 9) 1037 nbuf[i] = x - 10 + 'A'; 1038 else 1039 nbuf[i] = x + '0'; 1040 val >>= 4; 1041 } 1042 return(nbuf); 1043 } 1044 1045 #ifdef DEBUG 1046 char oflowmsg[] = "k-stack overflow"; 1047 char uflowmsg[] = "k-stack underflow"; 1048 1049 badkstack(oflow, fr) 1050 int oflow; 1051 struct frame fr; 1052 { 1053 #ifdef notdef 1054 extern char kstackatbase[]; 1055 1056 printf("%s: sp should be %x\n", 1057 oflow ? oflowmsg : uflowmsg, 1058 kstackatbase - (exframesize[fr.f_format] + 8)); 1059 #endif 1060 printf("%s: sp should be ????????\n", oflow ? oflowmsg : uflowmsg); 1061 regdump(&fr, 0); 1062 panic(oflow ? oflowmsg : uflowmsg); 1063 } 1064 #endif 1065 1066 /* for LUNA */ 1067 1068 /* 1069 * Enable parity detection 1070 */ 1071 #define PARREG ((volatile short *)0x49000003) 1072 #define PARITY_ENABLE 0xC 1073 parityenable() 1074 { 1075 *PARREG = PARITY_ENABLE; 1076 } 1077 1078 #ifdef FPCOPROC 1079 #define EXT_FPP_ADDR 0x6F000000 /* External 68882 board */ 1080 #define INT_FPP_ADDR 0x6B000000 /* Internal 68881 chip */ 1081 1082 #define FPP_ON 0x80 /* selected fpp on */ 1083 #define FPP_OFF 0x00 /* selected fpp off */ 1084 1085 #define SET_INT_FPP (*(char *)INT_FPP_ADDR = FPP_ON);(*(char *)EXT_FPP_ADDR = FPP_OFF) 1086 #define SET_EXT_FPP (*(char *)INT_FPP_ADDR = FPP_OFF);(*(char *)EXT_FPP_ADDR = FPP_ON) 1087 1088 #define FPP68881 1 1089 #define FPP68882 2 1090 1091 unsigned char fpp_svarea[212]; 1092 1093 #ifndef OLD_LUNA 1094 /* 1095 * Check FPP type 68881/68882. 1096 */ 1097 1098 void checkfpp() 1099 { 1100 #ifdef LUNA2 1101 if (machineid == LUNA_II) { 1102 return; 1103 } 1104 #endif 1105 SET_INT_FPP; /* internal = on, external = off */ 1106 if( is_68882() ) 1107 fpptype = FPP68882; 1108 else 1109 fpptype = FPP68881; 1110 return; 1111 } 1112 #else 1113 1114 /* 1115 * Check in/ex-ternal fpp, and determine which we use. 1116 * Also set fpp type(MC68881/68882). 1117 */ 1118 1119 void checkfpp() 1120 { 1121 int internal_exist,external_exist; 1122 int external_68882; 1123 #ifdef LUNA2 1124 if (machineid == LUNA_II) { 1125 return; 1126 } 1127 #endif 1128 1129 SET_INT_FPP; /* internal = on, external = off */ 1130 if ( internal_exist = havefpp() && is_68882() ) { /* internal = 68882 */ 1131 fpptype = FPP68882; 1132 return; 1133 } else { /* internal don't exist or it is not 68882 */ 1134 SET_EXT_FPP; /* internal = off, external = on */ 1135 if ( internal_exist && /* internal = 68882, external <> 68882 */ 1136 (!(external_exist = havefpp()) || !(external_68882 = is_68882())) ) { 1137 SET_INT_FPP; /* internal = on, external = off */ 1138 fpptype = FPP68881; 1139 return; 1140 } 1141 if ( internal_exist ) { /* internal = 68881, external = 68882 */ 1142 fpptype = FPP68882; 1143 return; 1144 } 1145 if ( external_exist ) /* internal not exist, external exist */ 1146 if ( external_68882 ) { /* external = 68882 */ 1147 fpptype = FPP68882; 1148 return; 1149 } else { /* external = 68881 */ 1150 fpptype = FPP68881; 1151 return; 1152 } 1153 else /* in/ex-ternal non exist */ 1154 panic("fpp non-existence"); 1155 } 1156 } 1157 #endif 1158 #endif 1159