1/* $NetBSD: locore.s,v 1.97 2013/11/07 17:50:02 christos Exp $ */ 2 3/* 4 * Copyright (c) 1980, 1990, 1993 5 * The Regents of the University of California. 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 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. Neither the name of the University nor the names of its contributors 20 * may be used to endorse or promote products derived from this software 21 * without specific prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 26 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 33 * SUCH DAMAGE. 34 * 35 * from: Utah $Hdr: locore.s 1.66 92/12/22$ 36 * @(#)locore.s 8.6 (Berkeley) 5/27/94 37 */ 38 39/* 40 * Copyright (c) 1994, 1995 Gordon W. Ross 41 * Copyright (c) 1993 Adam Glass 42 * Copyright (c) 1988 University of Utah. 43 * 44 * This code is derived from software contributed to Berkeley by 45 * the Systems Programming Group of the University of Utah Computer 46 * Science Department. 47 * 48 * Redistribution and use in source and binary forms, with or without 49 * modification, are permitted provided that the following conditions 50 * are met: 51 * 1. Redistributions of source code must retain the above copyright 52 * notice, this list of conditions and the following disclaimer. 53 * 2. Redistributions in binary form must reproduce the above copyright 54 * notice, this list of conditions and the following disclaimer in the 55 * documentation and/or other materials provided with the distribution. 56 * 3. All advertising materials mentioning features or use of this software 57 * must display the following acknowledgement: 58 * This product includes software developed by the University of 59 * California, Berkeley and its contributors. 60 * 4. Neither the name of the University nor the names of its contributors 61 * may be used to endorse or promote products derived from this software 62 * without specific prior written permission. 63 * 64 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 65 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 66 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 67 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 68 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 69 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 70 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 71 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 72 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 73 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 74 * SUCH DAMAGE. 75 * 76 * from: Utah $Hdr: locore.s 1.66 92/12/22$ 77 * @(#)locore.s 8.6 (Berkeley) 5/27/94 78 */ 79 80#include "opt_compat_netbsd.h" 81#include "opt_compat_svr4.h" 82#include "opt_compat_sunos.h" 83#include "opt_kgdb.h" 84#include "opt_lockdebug.h" 85 86#include "assym.h" 87#include <machine/asm.h> 88#include <machine/trap.h> 89 90| Remember this is a fun project! 91 92| This is for kvm_mkdb, and should be the address of the beginning 93| of the kernel text segment (not necessarily the same as kernbase). 94 .text 95GLOBAL(kernel_text) 96 97| This is the entry point, as well as the end of the temporary stack 98| used during process switch (one 8K page ending at start) 99ASGLOBAL(tmpstk) 100ASGLOBAL(start) 101 102| First we need to set it up so we can access the sun MMU, and be otherwise 103| undisturbed. Until otherwise noted, all code must be position independent 104| as the boot loader put us low in memory, but we are linked high. 105 movw #PSL_HIGHIPL,%sr | no interrupts 106 moveq #FC_CONTROL,%d0 | make movs access "control" 107 movc %d0,%sfc | space where the sun3 designers 108 movc %d0,%dfc | put all the "useful" stuff 109 110| Set context zero and stay there until pmap_bootstrap. 111 moveq #0,%d0 112 movsb %d0,CONTEXT_REG 113 114| In order to "move" the kernel to high memory, we are going to copy the 115| first 4 Mb of pmegs such that we will be mapped at the linked address. 116| This is all done by copying in the segment map (top-level MMU table). 117| We will unscramble which PMEGs we actually need later. 118 119 movl #(SEGMAP_BASE+0),%a0 | src 120 movl #(SEGMAP_BASE+KERNBASE3),%a1 | dst 121 movl #(0x400000/NBSG),%d0 | count 122 123L_per_pmeg: 124 movsb %a0@,%d1 | copy segmap entry 125 movsb %d1,%a1@ 126 addl #NBSG,%a0 | increment pointers 127 addl #NBSG,%a1 128 subql #1,%d0 | decrement count 129 bgt L_per_pmeg 130 131| Kernel is now double mapped at zero and KERNBASE. 132| Force a long jump to the relocated code (high VA). 133 movl #IC_CLEAR,%d0 | Flush the I-cache 134 movc %d0,%cacr 135 jmp L_high_code:l | long jump 136 137L_high_code: 138| We are now running in the correctly relocated kernel, so 139| we are no longer restricted to position-independent code. 140 141| Do bootstrap stuff needed before main() gets called. 142| Make sure the initial frame pointer is zero so that 143| the backtrace algorithm used by KGDB terminates nicely. 144 lea _ASM_LABEL(tmpstk),%sp 145 movl #0,%a6 146 jsr _C_LABEL(_bootstrap) | See locore2.c 147 148| Now that _bootstrap() is done using the PROM functions, 149| we can safely set the %sfc/dfc to something != FC_CONTROL 150 moveq #FC_USERD,%d0 | make movs access "user data" 151 movc %d0,%sfc | space for copyin/copyout 152 movc %d0,%dfc 153 154| Setup process zero user/kernel stacks. 155 lea _C_LABEL(lwp0),%a0 | lwp0 156 movl %a0@(L_PCB),%a1 | XXXuvm_lwp_getuarea 157 lea %a1@(USPACE-4),%sp | set SSP to last word 158 movl #USRSTACK3-4,%a2 159 movl %a2,%usp | init user SP 160 161| Note curpcb was already set in _bootstrap(). 162| Will do fpu initialization during autoconfig (see fpu.c) 163| The interrupt vector table and stack are now ready. 164| Interrupts will be enabled later, AFTER autoconfiguration 165| is finished, to avoid spurrious interrupts. 166 167/* 168 * Create a fake exception frame so that cpu_lwp_fork() can copy it. 169 * main() nevers returns; we exit to user mode from a forked process 170 * later on. 171 */ 172 clrw %sp@- | tf_format,tf_vector 173 clrl %sp@- | tf_pc (filled in later) 174 movw #PSL_USER,%sp@- | tf_sr for user mode 175 clrl %sp@- | tf_stackadj 176 lea %sp@(-64),%sp | tf_regs[16] 177 movl %a1,%a0@(L_MD_REGS) | lwp0.p_md.md_regs = trapframe 178 jbsr _C_LABEL(main) | main(&trapframe) 179 PANIC("main() returned") 180 181| That is all the assembly startup code we need on the sun3! 182| The rest of this is like the hp300/locore.s where possible. 183 184/* 185 * Trap/interrupt vector routines 186 */ 187#include <m68k/m68k/trap_subr.s> 188 189GLOBAL(buserr) 190 tstl _C_LABEL(nofault) | device probe? 191 jeq _C_LABEL(addrerr) | no, handle as usual 192 movl _C_LABEL(nofault),%sp@- | yes, 193 jbsr _C_LABEL(longjmp) | longjmp(nofault) 194GLOBAL(addrerr) 195 clrl %sp@- | stack adjust count 196 moveml #0xFFFF,%sp@- | save user registers 197 movl %usp,%a0 | save the user SP 198 movl %a0,%sp@(FR_SP) | in the savearea 199 lea %sp@(FR_HW),%a1 | grab base of HW berr frame 200 moveq #0,%d0 201 movw %a1@(10),%d0 | grab SSW for fault processing 202 btst #12,%d0 | RB set? 203 jeq LbeX0 | no, test RC 204 bset #14,%d0 | yes, must set FB 205 movw %d0,%a1@(10) | for hardware too 206LbeX0: 207 btst #13,%d0 | RC set? 208 jeq LbeX1 | no, skip 209 bset #15,%d0 | yes, must set FC 210 movw %d0,%a1@(10) | for hardware too 211LbeX1: 212 btst #8,%d0 | data fault? 213 jeq Lbe0 | no, check for hard cases 214 movl %a1@(16),%d1 | fault address is as given in frame 215 jra Lbe10 | thats it 216Lbe0: 217 btst #4,%a1@(6) | long (type B) stack frame? 218 jne Lbe4 | yes, go handle 219 movl %a1@(2),%d1 | no, can use save PC 220 btst #14,%d0 | FB set? 221 jeq Lbe3 | no, try FC 222 addql #4,%d1 | yes, adjust address 223 jra Lbe10 | done 224Lbe3: 225 btst #15,%d0 | FC set? 226 jeq Lbe10 | no, done 227 addql #2,%d1 | yes, adjust address 228 jra Lbe10 | done 229Lbe4: 230 movl %a1@(36),%d1 | long format, use stage B address 231 btst #15,%d0 | FC set? 232 jeq Lbe10 | no, all done 233 subql #2,%d1 | yes, adjust address 234Lbe10: 235 movl %d1,%sp@- | push fault VA 236 movl %d0,%sp@- | and padded SSW 237 movw %a1@(6),%d0 | get frame format/vector offset 238 andw #0x0FFF,%d0 | clear out frame format 239 cmpw #12,%d0 | address error vector? 240 jeq Lisaerr | yes, go to it 241 242/* 243 * the sun3 specific code 244 * 245 * our mission: figure out whether what we are looking at is 246 * bus error in the UNIX sense, or 247 * a memory error i.e a page fault 248 * 249 * [this code replaces similarly mmu specific code in the hp300 code] 250 */ 251sun3_mmu_specific: 252 clrl %d0 | make sure top bits are cleard too 253 movl %d1,%sp@- | save %d1 254 movc %sfc,%d1 | save %sfc to %d1 255 moveq #FC_CONTROL,%d0 | %sfc = FC_CONTROL 256 movc %d0,%sfc 257 movsb BUSERR_REG,%d0 | get value of bus error register 258 movc %d1,%sfc | restore %sfc 259 movl %sp@+,%d1 | restore %d1 260 andb #BUSERR_MMU,%d0 | is this an MMU fault? 261 jeq Lisberr | non-MMU bus error 262/* End of sun3 specific code. */ 263 264Lismerr: 265 movl #T_MMUFLT,%sp@- | show that we are an MMU fault 266 jra _ASM_LABEL(faultstkadj) | and deal with it 267Lisaerr: 268 movl #T_ADDRERR,%sp@- | mark address error 269 jra _ASM_LABEL(faultstkadj) | and deal with it 270Lisberr: 271 movl #T_BUSERR,%sp@- | mark bus error 272 jra _ASM_LABEL(faultstkadj) | and deal with it 273 274/* 275 * FP exceptions. 276 */ 277GLOBAL(fpfline) 278 clrl %sp@- | stack adjust count 279 moveml #0xFFFF,%sp@- | save registers 280 moveq #T_FPEMULI,%d0 | denote as FP emulation trap 281 jra _ASM_LABEL(fault) | do it 282 283GLOBAL(fpunsupp) 284 clrl %sp@- | stack adjust count 285 moveml #0xFFFF,%sp@- | save registers 286 moveq #T_FPEMULD,%d0 | denote as FP emulation trap 287 jra _ASM_LABEL(fault) | do it 288 289/* 290 * Handles all other FP coprocessor exceptions. 291 * Note that since some FP exceptions generate mid-instruction frames 292 * and may cause signal delivery, we need to test for stack adjustment 293 * after the trap call. 294 */ 295GLOBAL(fpfault) 296 clrl %sp@- | stack adjust count 297 moveml #0xFFFF,%sp@- | save user registers 298 movl %usp,%a0 | and save 299 movl %a0,%sp@(FR_SP) | the user stack pointer 300 clrl %sp@- | no VA arg 301 movl _C_LABEL(curpcb),%a0 | current pcb 302 lea %a0@(PCB_FPCTX),%a0 | address of FP savearea 303 fsave %a0@ | save state 304 tstb %a0@ | null state frame? 305 jeq Lfptnull | yes, safe 306 clrw %d0 | no, need to tweak BIU 307 movb %a0@(1),%d0 | get frame size 308 bset #3,%a0@(0,%d0:w) | set exc_pend bit of BIU 309Lfptnull: 310 fmovem %fpsr,%sp@- | push fpsr as code argument 311 frestore %a0@ | restore state 312 movl #T_FPERR,%sp@- | push type arg 313 jra _ASM_LABEL(faultstkadj) | call trap and deal with stack cleanup 314 315/* 316 * Other exceptions only cause four and six word stack frame and require 317 * no post-trap stack adjustment. 318 */ 319GLOBAL(badtrap) 320 clrl %sp@- | stack adjust count 321 moveml #0xFFFF,%sp@- | save std frame regs 322 jbsr _C_LABEL(straytrap) | report 323 moveml %sp@+,#0xFFFF | restore regs 324 addql #4,%sp | stack adjust count 325 jra _ASM_LABEL(rei) | all done 326 327/* 328 * Trap 0 is for system calls 329 */ 330GLOBAL(trap0) 331 clrl %sp@- | stack adjust count 332 moveml #0xFFFF,%sp@- | save user registers 333 movl %usp,%a0 | save the user SP 334 movl %a0,%sp@(FR_SP) | in the savearea 335 movl %d0,%sp@- | push syscall number 336 jbsr _C_LABEL(syscall) | handle it 337 addql #4,%sp | pop syscall arg 338 movl %sp@(FR_SP),%a0 | grab and restore 339 movl %a0,%usp | user SP 340 moveml %sp@+,#0x7FFF | restore most registers 341 addql #8,%sp | pop SP and stack adjust 342 jra _ASM_LABEL(rei) | all done 343 344/* 345 * Trap 12 is the entry point for the cachectl "syscall" 346 * cachectl(command, addr, length) 347 * command in %d0, addr in %a1, length in %d1 348 */ 349GLOBAL(trap12) 350 movl _C_LABEL(curlwp),%a0 351 movl %a0@(L_PROC),%sp@- | push curproc pointer 352 movl %d1,%sp@- | push length 353 movl %a1,%sp@- | push addr 354 movl %d0,%sp@- | push command 355 jbsr _C_LABEL(cachectl1) | do it 356 lea %sp@(16),%sp | pop args 357 jra _ASM_LABEL(rei) | all done 358 359/* 360 * Trace (single-step) trap. Kernel-mode is special. 361 * User mode traps are simply passed on to trap(). 362 */ 363GLOBAL(trace) 364 clrl %sp@- | stack adjust count 365 moveml #0xFFFF,%sp@- 366 moveq #T_TRACE,%d0 367 368 | Check PSW and see what happen. 369 | T=0 S=0 (should not happen) 370 | T=1 S=0 trace trap from user mode 371 | T=0 S=1 trace trap on a trap instruction 372 | T=1 S=1 trace trap from system mode (kernel breakpoint) 373 374 movw %sp@(FR_HW),%d1 | get PSW 375 notw %d1 | XXX no support for T0 on 680[234]0 376 andw #PSL_TS,%d1 | from system mode (T=1, S=1)? 377 jeq _ASM_LABEL(kbrkpt) | yes, kernel brkpt 378 jra _ASM_LABEL(fault) | no, user-mode fault 379 380/* 381 * Trap 15 is used for: 382 * - GDB breakpoints (in user programs) 383 * - KGDB breakpoints (in the kernel) 384 * - trace traps for SUN binaries (not fully supported yet) 385 * User mode traps are simply passed to trap(). 386 */ 387GLOBAL(trap15) 388 clrl %sp@- | stack adjust count 389 moveml #0xFFFF,%sp@- 390 moveq #T_TRAP15,%d0 391 btst #5,%sp@(FR_HW) | was supervisor mode? 392 jne _ASM_LABEL(kbrkpt) | yes, kernel brkpt 393 jra _ASM_LABEL(fault) | no, user-mode fault 394 395ASLOCAL(kbrkpt) 396 | Kernel-mode breakpoint or trace trap. (%d0=trap_type) 397 | Save the system sp rather than the user sp. 398 movw #PSL_HIGHIPL,%sr | lock out interrupts 399 lea %sp@(FR_SIZE),%a6 | Save stack pointer 400 movl %a6,%sp@(FR_SP) | from before trap 401 402 | If we are not on tmpstk switch to it. 403 | (so debugger can change the stack pointer) 404 movl %a6,%d1 405 cmpl #_ASM_LABEL(tmpstk),%d1 406 jls Lbrkpt2 | already on tmpstk 407 | Copy frame to the temporary stack 408 movl %sp,%a0 | %a0=src 409 lea _ASM_LABEL(tmpstk)-96,%a1 | %a1=dst 410 movl %a1,%sp | sp=new frame 411 moveq #FR_SIZE,%d1 412Lbrkpt1: 413 movl %a0@+,%a1@+ 414 subql #4,%d1 415 bgt Lbrkpt1 416 417Lbrkpt2: 418 | Call the trap handler for the kernel debugger. 419 | Do not call trap() to handle it, so that we can 420 | set breakpoints in trap() if we want. We know 421 | the trap type is either T_TRACE or T_BREAKPOINT. 422 movl %d0,%sp@- | push trap type 423 jbsr _C_LABEL(trap_kdebug) 424 addql #4,%sp | pop args 425 426 | The stack pointer may have been modified, or 427 | data below it modified (by kgdb push call), 428 | so push the hardware frame at the current sp 429 | before restoring registers and returning. 430 movl %sp@(FR_SP),%a0 | modified sp 431 lea %sp@(FR_SIZE),%a1 | end of our frame 432 movl %a1@-,%a0@- | copy 2 longs with 433 movl %a1@-,%a0@- | ... predecrement 434 movl %a0,%sp@(FR_SP) | sp = h/w frame 435 moveml %sp@+,#0x7FFF | restore all but sp 436 movl %sp@,%sp | ... and sp 437 rte | all done 438 439/* Use common m68k sigreturn */ 440#include <m68k/m68k/sigreturn.s> 441 442/* 443 * Interrupt handlers. Most are auto-vectored, 444 * and hard-wired the same way on all sun3 models. 445 * Format in the stack is: 446 * %d0,%d1,%a0,%a1, sr, pc, vo 447 */ 448 449/* 450 * This is the common auto-vector interrupt handler, 451 * for which the CPU provides the vector=0x18+level. 452 * These are installed in the interrupt vector table. 453 */ 454#ifdef __ELF__ 455 .align 4 456#else 457 .align 2 458#endif 459GLOBAL(_isr_autovec) 460 INTERRUPT_SAVEREG 461 jbsr _C_LABEL(isr_autovec) 462 INTERRUPT_RESTOREREG 463 jra _ASM_LABEL(rei) 464 465/* clock: see clock.c */ 466#ifdef __ELF__ 467 .align 4 468#else 469 .align 2 470#endif 471GLOBAL(_isr_clock) 472 INTERRUPT_SAVEREG 473 jbsr _C_LABEL(clock_intr) 474 INTERRUPT_RESTOREREG 475 jra _ASM_LABEL(rei) 476 477| Handler for all vectored interrupts (i.e. VME interrupts) 478#ifdef __ELF__ 479 .align 4 480#else 481 .align 2 482#endif 483GLOBAL(_isr_vectored) 484 INTERRUPT_SAVEREG 485 jbsr _C_LABEL(isr_vectored) 486 INTERRUPT_RESTOREREG 487 jra _ASM_LABEL(rei) 488 489/* interrupt counters (needed by vmstat) */ 490GLOBAL(intrnames) 491 .asciz "spur" | 0 492 .asciz "lev1" | 1 493 .asciz "lev2" | 2 494 .asciz "lev3" | 3 495 .asciz "lev4" | 4 496 .asciz "clock" | 5 497 .asciz "lev6" | 6 498 .asciz "nmi" | 7 499GLOBAL(eintrnames) 500 501 .data 502 .even 503GLOBAL(intrcnt) 504 .long 0,0,0,0,0,0,0,0,0,0 505GLOBAL(eintrcnt) 506 .text 507 508/* 509 * Emulation of VAX REI instruction. 510 * 511 * This code is (mostly) un-altered from the hp300 code, 512 * except that sun machines do not need a simulated SIR 513 * because they have a real software interrupt register. 514 * 515 * This code deals with checking for and servicing ASTs 516 * (profiling, scheduling) and software interrupts (network, softclock). 517 * We check for ASTs first, just like the VAX. To avoid excess overhead 518 * the T_ASTFLT handling code will also check for software interrupts so we 519 * do not have to do it here. After identifying that we need an AST we 520 * drop the IPL to allow device interrupts. 521 * 522 * This code is complicated by the fact that sendsig may have been called 523 * necessitating a stack cleanup. 524 */ 525 526ASGLOBAL(rei) 527#ifdef DIAGNOSTIC 528 tstl _C_LABEL(panicstr) | have we paniced? 529 jne Ldorte | yes, do not make matters worse 530#endif 531 tstl _C_LABEL(astpending) | AST pending? 532 jeq Ldorte | no, done 533Lrei1: 534 btst #5,%sp@ | yes, are we returning to user mode? 535 jne Ldorte | no, done 536 movw #PSL_LOWIPL,%sr | lower SPL 537 clrl %sp@- | stack adjust 538 moveml #0xFFFF,%sp@- | save all registers 539 movl %usp,%a1 | including 540 movl %a1,%sp@(FR_SP) | the users SP 541 clrl %sp@- | VA == none 542 clrl %sp@- | code == none 543 movl #T_ASTFLT,%sp@- | type == async system trap 544 pea %sp@(12) | fp == address of trap frame 545 jbsr _C_LABEL(trap) | go handle it 546 lea %sp@(16),%sp | pop value args 547 movl %sp@(FR_SP),%a0 | restore user SP 548 movl %a0,%usp | from save area 549 movw %sp@(FR_ADJ),%d0 | need to adjust stack? 550 jne Laststkadj | yes, go to it 551 moveml %sp@+,#0x7FFF | no, restore most user regs 552 addql #8,%sp | toss SP and stack adjust 553 rte | and do real RTE 554Laststkadj: 555 lea %sp@(FR_HW),%a1 | pointer to HW frame 556 addql #8,%a1 | source pointer 557 movl %a1,%a0 | source 558 addw %d0,%a0 | + hole size = dest pointer 559 movl %a1@-,%a0@- | copy 560 movl %a1@-,%a0@- | 8 bytes 561 movl %a0,%sp@(FR_SP) | new SSP 562 moveml %sp@+,#0x7FFF | restore user registers 563 movl %sp@,%sp | and our SP 564Ldorte: 565 rte | real return 566 567/* 568 * Initialization is at the beginning of this file, because the 569 * kernel entry point needs to be at zero for compatibility with 570 * the Sun boot loader. This works on Sun machines because the 571 * interrupt vector table for reset is NOT at address zero. 572 * (The MMU has a "boot" bit that forces access to the PROM) 573 */ 574 575/* 576 * Use common m68k sigcode. 577 */ 578#include <m68k/m68k/sigcode.s> 579#ifdef COMPAT_SUNOS 580#include <m68k/m68k/sunos_sigcode.s> 581#endif 582#ifdef COMPAT_SVR4 583#include <m68k/m68k/svr4_sigcode.s> 584#endif 585 586 .text 587 588/* 589 * Primitives 590 */ 591 592/* 593 * Use common m68k support routines. 594 */ 595#include <m68k/m68k/support.s> 596 597/* 598 * Use common m68k process/lwp switch and context save subroutines. 599 */ 600#define FPCOPROC /* XXX: Temp. Reqd. */ 601#include <m68k/m68k/switch_subr.s> 602 603 604/* suline() */ 605/* TBIA, TBIS, TBIAS, TBIAU */ 606 607/* 608 * Invalidate instruction cache 609 */ 610ENTRY(ICIA) 611 movl #IC_CLEAR,%d0 612 movc %d0,%cacr | invalidate i-cache 613 rts 614 615/* DCIA, DCIS */ 616 617/* 618 * Invalidate data cache. 619 */ 620ENTRY(DCIU) 621 rts 622 623/* ICPL, ICPP, DCPL, DCPP, DCPA, DCFL, DCFP */ 624/* PCIA, ecacheon, ecacheoff */ 625 626/* 627 * Get callers current SP value. 628 * Note that simply taking the address of a local variable in a C function 629 * doesn't work because callee saved registers may be outside the stack frame 630 * defined by A6 (e.g. GCC generated code). 631 * 632 * [I don't think the ENTRY() macro will do the right thing with this -- glass] 633 */ 634GLOBAL(getsp) 635 movl %sp,%d0 | get current SP 636 addql #4,%d0 | compensate for return address 637 movl %d0,%a0 638 rts 639 640ENTRY(getvbr) 641 movc %vbr,%a0 642 rts 643 644ENTRY(setvbr) 645 movl %sp@(4),%d0 646 movc %d0,%vbr 647 rts 648 649/* loadustp, ptest_addr */ 650 651/* 652 * Set processor priority level calls. Most are implemented with 653 * inline asm expansions. However, we need one instantiation here 654 * in case some non-optimized code makes external references. 655 * Most places will use the inlined functions param.h supplies. 656 */ 657 658ENTRY(_getsr) 659 clrl %d0 660 movw %sr,%d0 661 movl %d0,%a0 662 rts 663 664ENTRY(_spl) 665 clrl %d0 666 movw %sr,%d0 667 movl %sp@(4),%d1 668 movw %d1,%sr 669 rts 670 671ENTRY(_splraise) 672 clrl %d0 673 movw %sr,%d0 674 movl %d0,%d1 675 andl #PSL_HIGHIPL,%d1 | old &= PSL_HIGHIPL 676 cmpl %sp@(4),%d1 | (old - new) 677 bge Lsplr 678 movl %sp@(4),%d1 679 movw %d1,%sr 680Lsplr: 681 rts 682 683/* 684 * _delay(unsigned N) 685 * Delay for at least (N/256) microseconds. 686 * This routine depends on the variable: delay_divisor 687 * which should be set based on the CPU clock rate. 688 * XXX: Currently this is set based on the CPU model, 689 * XXX: but this should be determined at run time... 690 */ 691GLOBAL(_delay) 692 | %d0 = arg = (usecs << 8) 693 movl %sp@(4),%d0 694 | %d1 = delay_divisor; 695 movl _C_LABEL(delay_divisor),%d1 696 jra L_delay /* Jump into the loop! */ 697 698 /* 699 * Align the branch target of the loop to a half-line (8-byte) 700 * boundary to minimize cache effects. This guarantees both 701 * that there will be no prefetch stalls due to cache line burst 702 * operations and that the loop will run from a single cache 703 * half-line. 704 */ 705#ifdef __ELF__ 706 .align 8 707#else 708 .align 3 709#endif 710L_delay: 711 subl %d1,%d0 712 jgt L_delay 713 rts 714 715/* 716 * void set_segmap_allctx(vaddr_t va, int sme) 717 */ 718ENTRY(set_segmap_allctx) 719 linkw %fp,#0 720 moveml #0x3000,%sp@- 721 movl 8(%fp),%d3 | d3 = va 722 andl #0xffffffc,%d3 723 bset #29,%d3 724 movl %d3,%a1 | a1 = ctrladdr, d3 avail 725 movl 12(%fp),%d1 | d1 = sme 726 moveq #FC_CONTROL,%d0 727 movl #CONTEXT_REG,%a0 | a0 = ctxreg 728 movc %sfc,%d3 | d3 = oldsfc 729 movc %d0,%sfc 730 movsb %a0@,%d2 731 andi #7,%d2 | d2 = oldctx 732 movc %d3,%sfc | restore sfc, d3 avail 733 movc %dfc,%d3 | d3 = olddfc 734 movc %d0,%dfc 735 movl #(CONTEXT_NUM - 1),%d0 | d0 = ctx number 7361: 737 movsb %d0,%a0@ | change to ctx 738 movsb %d1,%a1@ | set segmap 739 dbf %d0,1b | loop setting each ctx 740 movsb %d2,%a0@ | restore ctx 741 movc %d3,%dfc | restore dfc 742 moveml %sp@+,#0x000c 743 unlk %fp 744 rts 745 746| Define some addresses, mostly so DDB can print useful info. 747| Not using _C_LABEL() here because these symbols are never 748| referenced by any C code, and if the leading underscore 749| ever goes away, these lines turn into syntax errors... 750 .set _KERNBASE3,KERNBASE3 751 .set _MONSTART,SUN3_MONSTART 752 .set _PROM_BASE,SUN3_PROM_BASE 753 .set _MONEND,SUN3_MONEND 754 755|The end! 756