Annotation of sys/arch/mvme68k/mvme68k/locore.s, Revision 1.1.1.1
1.1 nbrk 1: /* $OpenBSD: locore.s,v 1.54 2007/05/15 13:46:22 martin Exp $ */
2:
3: /*
4: * Copyright (c) 1995 Theo de Raadt
5: * Copyright (c) 1999 Steve Murphree, Jr. (68060 support)
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: *
16: * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
17: * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18: * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19: * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
20: * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26: * SUCH DAMAGE.
27: *
28: * Copyright (c) 1988 University of Utah.
29: * Copyright (c) 1980, 1990, 1993
30: * The Regents of the University of California. All rights reserved.
31: *
32: * This code is derived from software contributed to Berkeley by
33: * the Systems Programming Group of the University of Utah Computer
34: * Science Department.
35: *
36: * Redistribution and use in source and binary forms, with or without
37: * modification, are permitted provided that the following conditions
38: * are met:
39: * 1. Redistributions of source code must retain the above copyright
40: * notice, this list of conditions and the following disclaimer.
41: * 2. Redistributions in binary form must reproduce the above copyright
42: * notice, this list of conditions and the following disclaimer in the
43: * documentation and/or other materials provided with the distribution.
44: * 3. Neither the name of the University nor the names of its contributors
45: * may be used to endorse or promote products derived from this software
46: * without specific prior written permission.
47: *
48: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
49: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
50: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
51: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
52: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
53: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
54: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
55: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
56: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
57: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
58: * SUCH DAMAGE.
59: *
60: * from: Utah $Hdr: locore.s 1.66 92/12/22$
61: *
62: * @(#)locore.s 8.6 (Berkeley) 5/27/94
63: */
64:
65: #include "assym.h"
66: #include "ksyms.h"
67: #include <machine/asm.h>
68: #include <machine/prom.h>
69: #include <machine/trap.h>
70:
71: /*
72: * Relocate a symbol, used before MMU is enabled.
73: */
74: #define _RELOC(var, ar) \
75: lea var,ar
76:
77: #define RELOC(var, ar) _RELOC(_C_LABEL(var), ar)
78: #define ASRELOC(var, ar) _RELOC(_ASM_LABEL(var), ar)
79:
80: /*
81: * Invoke a BUG routine.
82: */
83: #define BUGCALL(id) \
84: trap #15; \
85: .short id
86:
87: /*
88: * Temporary stack for a variety of purposes.
89: * Try and make this the first thing is the data segment so it
90: * is page aligned. Note that if we overflow here, we run into
91: * our text segment.
92: */
93: .data
94: .space NBPG
95: ASLOCAL(tmpstk)
96:
97: /*
98: * Initialization
99: *
100: * The bootstrap loader loads us in starting at 0, and VBR is non-zero.
101: * On entry, args on stack are boot device, boot filename, console unit,
102: * boot flags (howto), boot device name, filesystem type name.
103: */
104: BSS(esym, 4)
105: BSS(emini, 4)
106: BSS(smini, 4)
107: BSS(promvbr, 4)
108: BSS(promcall, 4)
109:
110: .text
111: /*
112: GLOBAL(edata)
113: GLOBAL(etext)
114: GLOBAL(end)
115: */
116: GLOBAL(kernel_text)
117:
118: ASENTRY_NOPROFILE(start)
119: movw #PSL_HIGHIPL,sr | no interrupts
120: movl sp@(4), d7 | get boothowto
121: movl sp@(8), d6 | get bootaddr
122: movl sp@(12),d5 | get bootctrllun
123: movl sp@(16),d4 | get bootdevlun
124: movl sp@(20),d3 | get bootpart
125: movl sp@(24),d2 | get esyms
126: /* note: d2-d7 in use */
127:
128: ASRELOC(tmpstk, a0)
129: movl a0,sp | give ourselves a temporary stack
130:
131: RELOC(edata, a0) | clear out BSS
132: movl #_C_LABEL(end)-4,d0 | (must be <= 256 kB)
133: subl #_C_LABEL(edata),d0
134: lsrl #2,d0
135: 1: clrl a0@+
136: dbra d0,1b
137:
138: movc vbr,d0 | save prom's trap #15 vector
139: RELOC(promvbr, a0)
140: movl d0, a0@
141: RELOC(esym, a0)
142: movl d2,a0@ | store end of symbol table
143: /* note: d2 now free, d3-d7 still in use */
144:
145: clrl sp@-
146: BUGCALL(MVMEPROM_GETBRDID)
147: movl sp@+, a1
148:
149: movl #SIZEOF_MVMEPROM_BRDID, d0 | copy to local variables
150: RELOC(brdid, a0)
151: 1: movb a1@+, a0@+
152: subql #1, d0
153: bne 1b
154:
155: clrl d0
156: RELOC(brdid, a1)
157: movw a1@(MVMEPROM_BRDID_MODEL), d0
158: RELOC(cputyp, a0)
159: movl d0, a0@ | init _cputyp
160:
161: #ifdef MVME147
162: cmpw #CPU_147, d0
163: beq is147
164: #endif
165:
166: #ifdef MVME162
167: cmpw #CPU_162, d0
168: beq is162
169: #endif
170:
171: #ifdef MVME167
172: cmpw #CPU_166, d0
173: beq is167
174: cmpw #CPU_167, d0
175: beq is167
176: #endif
177:
178: #ifdef MVME177
179: #ifdef notyet
180: cmpw #CPU_176, d0
181: beq is177
182: #endif
183: cmpw #CPU_177, d0
184: beq is177
185: #endif
186:
187: #ifdef MVME172
188: cmpw #CPU_172, d0
189: beq is172
190: #endif
191:
192: .data
193: notsup: .asciz "kernel does not support this model."
194: notsupend:
195: .even
196: .text
197:
198: | first we bitch, then we die.
199: movl #notsupend, sp@-
200: movl #notsup, sp@-
201: BUGCALL(MVMEPROM_OUTSTRCRLF)
202: addql #8,sp
203:
204: BUGCALL(MVMEPROM_EXIT) | return to m68kbug
205: /*NOTREACHED*/
206:
207: #ifdef MVME147
208: is147:
209: RELOC(mmutype, a0) | no, we have 68030
210: movl #MMU_68030,a0@ | set to reflect 68030 PMMU
211:
212: RELOC(cputype, a0) | no, we have 68030
213: movl #CPU_68030,a0@ | set to reflect 68030 CPU
214:
215: movl #CACHE_OFF,d0
216: movc d0,cacr | clear and disable on-chip cache(s)
217:
218: movb #0, 0xfffe1026 | XXX serial interrupt off
219: movb #0, 0xfffe1018 | XXX timer 1 off
220: movb #0, 0xfffe1028 | XXX ethernet off
221:
222: movl #0xfffe0000, a0 | mvme147 nvram base
223: | move nvram component of etheraddr (only last 3 bytes)
224: RELOC(myea, a1)
225: movw a0@(NVRAM_147_ETHER+0), a1@(3+0)
226: movb a0@(NVRAM_147_ETHER+2), a1@(3+2)
227: movl a0@(NVRAM_147_EMEM), d1 | pass memory size
228:
229: RELOC(iiomapsize, a1)
230: movl #INTIOSIZE_147, a1@
231: RELOC(iiomapbase, a1)
232: movl #INTIOBASE_147, a1@
233: bra Lstart1
234: #endif
235:
236: #ifdef MVME162
237: is162:
238: #if 0
239: | the following 3 things are "just in case". they won't make
240: | the kernel work properly, but they will at least let it get
241: | far enough that you can figure out that something had an
242: | interrupt pending. which the bootrom shouldn't allow, i don't
243: | think..
244: clrb 0xfff42002 | XXX MCchip irq off
245: clrl 0xfff42018 | XXX MCchip timers irq off
246: clrb 0xfff4201d | XXX MCchip scc irq off
247: #endif
248: RELOC(memsize162, a1) | how much memory?
249: jbsr a1@
250: movl d0, d2
251:
252: RELOC(mmutype, a0)
253: movl #MMU_68040,a0@ | with a 68040 MMU
254:
255: RELOC(cputype, a0) | no, we have 68040
256: movl #CPU_68040,a0@ | set to reflect 68040 CPU
257:
258: RELOC(fputype, a0)
259: movl #FPU_68040,a0@ | and a 68040 FPU
260:
261: RELOC(vectab, a1)
262: movl #_C_LABEL(buserr40),a1@(8)
263: movl #_C_LABEL(addrerr4060),a1@(12)
264:
265: bra is16x
266: #endif
267:
268: #ifdef MVME167
269: is167:
270: RELOC(memsize1x7, a1) | how much memory?
271: jbsr a1@
272:
273: RELOC(mmutype, a0)
274: movl #MMU_68040,a0@ | with a 68040 MMU
275:
276: RELOC(cputype, a0) | no, we have 68040
277: movl #CPU_68040,a0@ | set to reflect 68040 CPU
278:
279: RELOC(fputype, a0)
280: movl #FPU_68040,a0@ | and a 68040 FPU
281:
282: RELOC(vectab, a1)
283: movl #_C_LABEL(buserr40),a1@(8)
284: movl #_C_LABEL(addrerr4060),a1@(12)
285:
286: bra is16x
287: #endif
288:
289: #ifdef MVME172
290: is172:
291:
292: RELOC(memsize162, a1) | how much memory?
293: jbsr a1@
294: movl d0, d2
295:
296: /* enable Super Scalar Dispatch */
297: .word 0x4e7a,0x0808 | movc pcr,d0
298: bset #0,d0 | turn on bit 0.
299: .word 0x4e7b,0x0808 | movc d0,pcr Bang!
300:
301: RELOC(mmutype, a0)
302: movl #MMU_68060,a0@ | with a 68060 MMU
303:
304: RELOC(cputype, a0) | no, we have 68060
305: movl #CPU_68060,a0@ | set to reflect 68060 CPU
306:
307: RELOC(fputype, a0)
308: movl #FPU_68060,a0@ | and a 68060 FPU
309:
310: RELOC(vectab, a1)
311: movl #_C_LABEL(buserr60),a1@(8)
312: movl #_C_LABEL(addrerr4060),a1@(12)
313:
314: bra is16x
315: #endif
316:
317: #ifdef MVME177
318: is177:
319: RELOC(memsize1x7, a1) | how much memory?
320: jbsr a1@
321:
322: /* enable Super Scalar Dispatch */
323: .word 0x4e7a,0x0808 | movc pcr,d0
324: bset #0,d0 | turn on bit 0.
325: .word 0x4e7b,0x0808 | movc d0,pcr Bang! We are smokin' !
326:
327: RELOC(mmutype, a0)
328: movl #MMU_68060,a0@ | with a 68060 MMU
329:
330: RELOC(cputype, a0) | no, we have 68060
331: movl #CPU_68060,a0@ | set to reflect 68060 CPU
332:
333: RELOC(fputype, a0)
334: movl #FPU_68060,a0@ | and a 68060 FPU
335:
336: RELOC(vectab, a1)
337: movl #_C_LABEL(buserr60),a1@(8)
338: movl #_C_LABEL(addrerr4060),a1@(12)
339:
340: bra is16x
341: #endif
342:
343: #if defined(MVME162) || defined(MVME167) || defined(MVME177) || defined(MVME172)
344: #define ROMPKT_LEN 200
345: BSS(rompkt, ROMPKT_LEN)
346: .even
347: .text
348: is16x:
349: RELOC(iiomapsize, a1)
350: movl #INTIOSIZE_162, a1@
351: RELOC(iiomapbase, a1)
352: movl #INTIOBASE_162, a1@
353:
354: /* get ethernet address */
355: RELOC(rompkt, a0) | build a .NETCTRL packet
356: movb #0, a0@(NETCTRL_DEV) | onboard ethernet
357: movb #0, a0@(NETCTRL_CTRL) | onboard ethernet
358: movl #NETCTRLCMD_GETETHER, a0@(NETCTRL_CMD)
359: RELOC(myea, a1)
360: movl a1, a0@(NETCTRL_ADDR) | where to put it
361: movl #6, a0@(NETCTRL_LEN) | it is 6 bytes long
362:
363: movl a0, sp@-
364: BUGCALL(MVMEPROM_NETCTRL) | ask the rom
365: addl #4, sp
366:
367: | if memory size is unknown, print a diagnostic and make an
368: | assumption
369: movl d2, d1
370: cmpl #0, d1
371: bne Lstart1
372:
373: movl #unkmemend, sp@-
374: movl #unkmem, sp@-
375: BUGCALL(MVMEPROM_OUTSTRCRLF)
376: addql #8,sp
377:
378: movl #4*1024*1024, d1 | XXX assume 4M of ram
379: bra Lstart1
380:
381: .data
382: unkmem: .asciz "could not figure out how much memory; assuming 4M."
383: unkmemend:
384: .even
385: .text
386:
387: #endif
388:
389: Lstart1:
390: /* initialize source/destination control registers for movs */
391: moveq #FC_USERD,d0 | user space
392: movc d0,sfc | as source
393: movc d0,dfc | and destination of transfers
394: moveq #PGSHIFT,d2
395: lsrl d2,d1 | convert to pages
396: RELOC(physmem, a0)
397: movl d1,a0@ | save as physmem
398:
399: /* configure kernel and proc0 VA space so we can get going */
400: #if defined(DDB) || NKSYMS > 0
401: RELOC(esym,a0) | end of static kernel text/data/syms
402: movl a0@,d2
403: jne Lstart2
404: #endif
405: movl #_C_LABEL(end),d2 | end of static kernel text/data
406: Lstart2:
407: addl #NBPG-1,d2
408: andl #PG_FRAME,d2 | round to a page
409: movl d2,a4
410: #if 0
411: | XXX clear from end-of-kernel to 1M, as a workaround for an
412: | insane pmap_bootstrap bug I cannot find (68040-specific)
413: movl a4,a0
414: movl #1024*1024,d0
415: cmpl a0,d0 | end of kernel is beyond 1M?
416: jlt 2f
417: subl a0,d0
418: 1: clrb a0@+
419: subql #1,d0
420: bne 1b
421: 2:
422: #endif
423:
424: /* do pmap_bootstrap stuff */
425: clrl sp@- | firstpa
426: pea a4@ | nextpa
427: RELOC(pmap_bootstrap,a0)
428: jbsr a0@ | pmap_bootstrap(firstpa, nextpa)
429: addql #8,sp
430:
431: /*
432: * While still running physical, override copypage() with the 68040
433: * optimized version, copypage040(), if possible.
434: * This relies upon the fact that copypage() immediately follows
435: * copypage040() in memory.
436: */
437: RELOC(mmutype, a0)
438: cmpl #MMU_68040,a0@
439: jgt Lmmu_enable
440: RELOC(copypage040, a0)
441: RELOC(copypage, a1)
442: movl a1, a2
443: 1:
444: movw a0@+, a2@+
445: cmpl a0, a1
446: jgt 1b
447:
448: /*
449: * Enable the MMU.
450: * Since the kernel is mapped logical == physical, we just turn it on.
451: */
452: Lmmu_enable:
453: RELOC(Sysseg, a0) | system segment table addr
454: movl a0@,d1 | read value (a KVA)
455: RELOC(mmutype, a0)
456: cmpl #MMU_68040,a0@ | 68040 or 68060?
457: jgt Lmotommu1 | no, skip
458: .long 0x4e7b1807 | movc d1,srp
459: .long 0x4e7b1806 | movc d1,urp
460: jra Lstploaddone
461: Lmotommu1:
462: RELOC(protorp, a0)
463: movl #0x80000202,a0@ | nolimit + share global + 4 byte PTEs
464: movl d1,a0@(4) | + segtable address
465: pmove a0@,srp | load the supervisor root pointer
466: movl #0x80000002,a0@ | reinit upper half for CRP loads
467: Lstploaddone:
468: RELOC(mmutype, a0)
469: cmpl #MMU_68040,a0@ | 68040 or 68060?
470: jgt Lmotommu2 | no, skip
471:
472: moveq #0,d0 | ensure TT regs are disabled
473: .long 0x4e7b0004 | movc d0,itt0
474: .long 0x4e7b0005 | movc d0,itt1
475: .long 0x4e7b0006 | movc d0,dtt0
476: .long 0x4e7b0007 | movc d0,dtt1
477:
478: .word 0xf4d8 | cinva bc
479: .word 0xf518 | pflusha
480: movl #0x8000,d0
481: .long 0x4e7b0003 | movc d0,tc
482: /* Enable 68060 extensions here */
483: RELOC(mmutype, a0)
484: cmpl #MMU_68060,a0@ | 68060?
485: jne Lchache040
486: movl #CACHE60_ON,d0 | branch cache, etc...
487: movc d0,cacr | turn on both caches
488: jmp Lenab1
489: Lchache040:
490: movl #CACHE40_ON,d0
491: movc d0,cacr | turn on both caches
492: jmp Lenab1
493: Lmotommu2:
494: movl #0x82c0aa00,a2@ | value to load TC with
495: pmove a2@,tc | load it
496: Lenab1:
497:
498: /*
499: * Should be running mapped from this point on
500: */
501: /* select the software page size now */
502: lea _ASM_LABEL(tmpstk),sp | temporary stack
503: jbsr _C_LABEL(uvm_setpagesize) | select software page size
504: /* set kernel stack, user SP, and initial pcb */
505: movl _C_LABEL(proc0paddr),a1 | get proc0 pcb addr
506: lea a1@(USPACE-4),sp | set kernel stack to end of area
507: lea _C_LABEL(proc0), a2 | initialize proc0.p_addr so that
508: movl a1,a2@(P_ADDR) | we don't deref NULL in trap()
509: movl #USRSTACK-4,a2
510: movl a2,usp | init user SP
511: movl a1,_C_LABEL(curpcb) | proc0 is running
512:
513: tstl _C_LABEL(fputype) | Have an FPU?
514: jeq Lenab2 | No, skip.
515: clrl a1@(PCB_FPCTX) | ensure null FP context
516: movl a1,sp@-
517: jbsr _C_LABEL(m68881_restore) | restore it (does not kill a1)
518: addql #4,sp
519: Lenab2:
520: /* flush TLB and turn on caches */
521: jbsr _ASM_LABEL(TBIA) | invalidate TLB
522: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040 or 68060?
523: jle Lnocache0 | yes, cache already on
524: movl #CACHE_ON,d0
525: movc d0,cacr | clear cache(s)
526: Lnocache0:
527: /* final setup for C code */
528: #if 1
529: movl #_vectab,d2 | set VBR
530: movc d2,vbr
531: #endif
532: movw #PSL_LOWIPL,sr | lower SPL
533: movl d3, _C_LABEL(bootpart) | save bootpart
534: movl d4, _C_LABEL(bootdevlun) | save bootdevlun
535: movl d5, _C_LABEL(bootctrllun) | save bootctrllun
536: movl d6, _C_LABEL(bootaddr) | save bootaddr
537: movl d7, _C_LABEL(boothowto) | save boothowto
538: /* d3-d7 now free */
539:
540: /* Final setup for call to main(). */
541: jbsr _C_LABEL(mvme68k_init)
542:
543: /*
544: * Create a fake exception frame so that cpu_fork() can copy it.
545: * main() never returns; we exit to user mode from a forked process
546: * later on.
547: */
548: clrw sp@- | vector offset/frame type
549: clrl sp@- | PC - filled in by "execve"
550: movw #PSL_USER,sp@- | in user mode
551: clrl sp@- | stack adjust count and padding
552: lea sp@(-64),sp | construct space for D0-D7/A0-A7
553: lea _C_LABEL(proc0),a0 | save pointer to frame
554: movl sp,a0@(P_MD_REGS) | in proc0.p_md.md_regs
555:
556: jra _C_LABEL(main) | main()
557: PANIC("main() returned")
558: /* NOTREACHED */
559:
560: #if defined(MVME162) || defined(MVME167) || defined(MVME177) || defined(MVME172)
561: /*
562: * Figure out the size of onboard DRAM by querying the memory controller(s).
563: * This has to be done in locore as badaddr() can not yet be used at this
564: * point.
565: */
566: GLOBAL(memsize1x7)
567: movl #0xfff43008,a0 | MEMC040/MEMECC Controller #1
568: jbsr memc040read
569: movl d0,d2
570:
571: movl #0xfff43108,a0 | MEMC040/MEMECC Controller #2
572: jbsr memc040read
573: addl d0,d2
574:
575: rts
576:
577: /*
578: * Probe for a memory controller ASIC (MEMC040 or MEMECC) at the
579: * address in a0. If found, return the size in bytes of any RAM
580: * controller by the ASIC in d0. Otherwise return zero.
581: */
582: ASLOCAL(memc040read)
583: moveml d1-d2/a1-a2,sp@- | save scratch regs
584: movc vbr,d2 | Save vbr
585: RELOC(vectab,a2) | Install our own vectab, temporarily
586: movc a2,vbr
587: ASRELOC(Lmemc040berr,a1) | get address of bus error handler
588: movl a2@(8),sp@- | Save current bus error handler addr
589: movl a1,a2@(8) | Install our own handler
590: movl sp,d0 | Save current stack pointer value
591: movql #0x07,d1
592: andb a0@,d1 | Access MEMC040/MEMECC
593: movl #0x400000,d0
594: lsll d1,d0 | Convert to memory size, in bytes
595: Lmemc040ret:
596: movc d2,vbr | Restore original vbr
597: movl sp@+,a2@(8) | Restore original bus error handler
598: moveml sp@+,d1-d2/a1-a2
599: rts
600: /*
601: * If the memory controller doesn't exist, we get a bus error trying
602: * to access a0@ above. Control passes here, where we flag 'no bytes',
603: * ditch the exception frame and return as normal.
604: */
605: Lmemc040berr:
606: movl d0,sp | Get rid of the exception frame
607: clrl d0 | No ASIC at this location, then!
608: jbra Lmemc040ret | Done
609: #endif
610:
611: /*
612: * proc_trampoline: call function in register a2 with a3 as an arg
613: * and then rei.
614: */
615: GLOBAL(proc_trampoline)
616: movl a3,sp@- | push function arg
617: jbsr a2@ | call function
618: addql #4,sp | pop arg
619: movl sp@(FR_SP),a0 | grab and load
620: movl a0,usp | user SP
621: moveml sp@+,#0x7FFF | restore most user regs
622: addql #8,sp | toss SP and stack adjust
623: jra _ASM_LABEL(rei) | and return
624:
625:
626: /*
627: * Trap/interrupt vector routines - new for 060
628: */
629: #include <m68k/m68k/trap_subr.s>
630:
631: #if defined(M68040) || defined(M68060)
632: ENTRY_NOPROFILE(addrerr4060)
633: clrl sp@- | stack adjust count
634: moveml #0xFFFF,sp@- | save user registers
635: movl usp,a0 | save the user SP
636: movl a0,sp@(FR_SP) | in the savearea
637: movl sp@(FR_HW+8),sp@-
638: clrl sp@- | dummy code
639: movl #T_ADDRERR,sp@- | mark address error
640: jra _ASM_LABEL(faultstkadj) | and deal with it
641: #endif
642:
643: #if defined(M68060)
644: ENTRY_NOPROFILE(buserr60)
645: clrl sp@- | stack adjust count
646: moveml #0xFFFF,sp@- | save user registers
647: movl usp,a0 | save the user SP
648: movl a0,sp@(FR_SP) | in the savearea
649: movel sp@(FR_HW+12),d0 | FSLW
650: btst #2,d0 | branch prediction error?
651: jeq Lnobpe
652: movc cacr,d2
653: orl #IC60_CABC,d2 | clear all branch cache entries
654: movc d2,cacr
655: movl d0,d1
656: andl #0x7ffd,d1
657: jeq _ASM_LABEL(faultstkadjnotrap2)
658: Lnobpe:
659: | we need to adjust for misaligned addresses
660: movl sp@(FR_HW+8),d1 | grab VA
661: btst #27,d0 | check for mis-aligned access
662: jeq Lberr3 | no, skip
663: addl #28,d1 | yes, get into next page
664: | operand case: 3,
665: | instruction case: 4+12+12
666: andl #PG_FRAME,d1 | and truncate
667: Lberr3:
668: movl d1,sp@-
669: movl d0,sp@- | code is FSLW now.
670: andw #0x1f80,d0
671: jeq Lbuserr60 | no, handle as usual
672: movl #T_MMUFLT,sp@- | show that we are an MMU fault
673: jra _ASM_LABEL(faultstkadj) | and deal with it
674: Lbuserr60:
675: tstl _C_LABEL(nofault) | device probe?
676: jeq Lisberr | Bus Error?
677: movl _C_LABEL(nofault),sp@- | yes,
678: jbsr _C_LABEL(longjmp) | longjmp(nofault)
679: #endif
680: #if defined(M68040)
681: ENTRY_NOPROFILE(buserr40)
682: clrl sp@- | stack adjust count
683: moveml #0xFFFF,sp@- | save user registers
684: movl usp,a0 | save the user SP
685: movl a0,sp@(FR_SP) | in the savearea
686: movl sp@(FR_HW+20),d1 | get fault address
687: moveq #0,d0
688: movw sp@(FR_HW+12),d0 | get SSW
689: btst #11,d0 | check for mis-aligned
690: jeq Lbe1stpg | no skip
691: addl #3,d1 | get into next page
692: andl #PG_FRAME,d1 | and truncate
693: Lbe1stpg:
694: movl d1,sp@- | pass fault address.
695: movl d0,sp@- | pass SSW as code
696: btst #10,d0 | test ATC
697: jeq Lbuserr40 | no, handle as usual
698: movl #T_MMUFLT,sp@- | show that we are an MMU fault
699: jra _ASM_LABEL(faultstkadj) | and deal with it
700: Lbuserr40:
701: tstl _C_LABEL(nofault) | device probe?
702: jeq Lisberr | it is a bus error
703: movl _C_LABEL(nofault),sp@- | yes,
704: jbsr _C_LABEL(longjmp) | longjmp(nofault)
705: /* NOTREACHED */
706: #endif
707:
708: ENTRY_NOPROFILE(busaddrerr2030)
709: clrl sp@- | stack adjust count
710: moveml #0xFFFF,sp@- | save user registers
711: movl usp,a0 | save the user SP
712: movl a0,sp@(FR_SP) | in the savearea
713: lea sp@(FR_HW),a1 | grab base of HW berr frame
714: moveq #0,d0
715: movw a1@(10),d0 | grab SSW for fault processing
716: btst #12,d0 | RB set?
717: jeq LbeX0 | no, test RC
718: bset #14,d0 | yes, must set FB
719: movw d0,a1@(10) | for hardware too
720: LbeX0:
721: btst #13,d0 | RC set?
722: jeq LbeX1 | no, skip
723: bset #15,d0 | yes, must set FC
724: movw d0,a1@(10) | for hardware too
725: LbeX1:
726: btst #8,d0 | data fault?
727: jeq Lbe0 | no, check for hard cases
728: movl a1@(16),d1 | fault address is as given in frame
729: jra Lbe10 | thats it
730: Lbe0:
731: btst #4,a1@(6) | long (type B) stack frame?
732: jne Lbe4 | yes, go handle
733: movl a1@(2),d1 | no, can use save PC
734: btst #14,d0 | FB set?
735: jeq Lbe3 | no, try FC
736: addql #4,d1 | yes, adjust address
737: jra Lbe10 | done
738: Lbe3:
739: btst #15,d0 | FC set?
740: jeq Lbe10 | no, done
741: addql #2,d1 | yes, adjust address
742: jra Lbe10 | done
743: Lbe4:
744: movl a1@(36),d1 | long format, use stage B address
745: btst #15,d0 | FC set?
746: jeq Lbe10 | no, all done
747: subql #2,d1 | yes, adjust address
748: Lbe10:
749: movl d1,sp@- | push fault VA
750: movl d0,sp@- | and padded SSW
751: movw a1@(6),d0 | get frame format/vector offset
752: andw #0x0FFF,d0 | clear out frame format
753: cmpw #12,d0 | address error vector?
754: jeq Lisaerr | yes, go to it
755: movl d1,a0 | fault address
756: movl sp@,d0 | function code from ssw
757: btst #8,d0 | data fault?
758: jne Lbe10a
759: movql #1,d0 | user program access FC
760: | (we dont separate data/program)
761: btst #5,a1@ | supervisor mode?
762: jeq Lbe10a | if no, done
763: movql #5,d0 | else supervisor program access
764: Lbe10a:
765: ptestr d0,a0@,#7 | do a table search
766: pmove psr,sp@ | save result
767: movb sp@,d1
768: btst #2,d1 | invalid (incl. limit viol. and berr)?
769: jeq Lmightnotbemerr | no -> wp check
770: btst #7,d1 | is it MMU table berr?
771: jeq Lismerr | no, must be fast
772: jra Lisberr1 | real bus err needs not be fast.
773: Lmightnotbemerr:
774: btst #3,d1 | write protect bit set?
775: jeq Lisberr1 | no: must be bus error
776: movl sp@,d0 | ssw into low word of d0
777: andw #0xc0,d0 | Write protect is set on page:
778: cmpw #0x40,d0 | was it read cycle?
779: jeq Lisberr1 | yes, was not WPE, must be bus err
780: Lismerr:
781: movl #T_MMUFLT,sp@- | show that we are an MMU fault
782: jra _ASM_LABEL(faultstkadj) | and deal with it
783: Lisaerr:
784: movl #T_ADDRERR,sp@- | mark address error
785: jra _ASM_LABEL(faultstkadj) | and deal with it
786: Lisberr1:
787: clrw sp@ | re-clear pad word
788: Lisberr:
789: movl #T_BUSERR,sp@- | mark bus error
790: jra _ASM_LABEL(faultstkadj) | and deal with it
791:
792: /*
793: * FP exceptions.
794: */
795: ENTRY_NOPROFILE(fpfline)
796: #if defined(M68040) || defined(M68060)
797: cmpl #FPU_68040,_C_LABEL(fputype) | 68040 or 68060 FPU?
798: jlt Lfp_unimp | no, skip FPSP
799: cmpw #0x202c,sp@(6) | format type 2?
800: jne _C_LABEL(illinst) | no, not an FP emulation
801: Ldofp_unimp:
802: #ifdef FPSP
803: jmp _ASM_LABEL(fpsp_unimp) | yes, go handle it
804: #endif
805: Lfp_unimp:
806: #endif/* M68040 || M68060 */
807: #ifdef FPU_EMULATE
808: clrl sp@- | stack adjust count
809: moveml #0xFFFF,sp@- | save registers
810: moveq #T_FPEMULI,d0 | denote as FP emulation trap
811: jra _ASM_LABEL(fault) | do it
812: #else
813: jra _C_LABEL(illinst)
814: #endif
815:
816: ENTRY_NOPROFILE(fpunsupp)
817: #if defined(M68040) || defined(M68060)
818: cmpl #FPU_68040,_C_LABEL(fputype) | 68040 or 68060 FPU?
819: jlt _C_LABEL(illinst) | no, treat as illinst
820: #ifdef FPSP
821: jmp _ASM_LABEL(fpsp_unsupp) | yes, go handle it
822: #endif
823: Lfp_unsupp:
824: #endif /* M68040 */
825: #ifdef FPU_EMULATE
826: clrl sp@- | stack adjust count
827: moveml #0xFFFF,sp@- | save registers
828: moveq #T_FPEMULD,d0 | denote as FP emulation trap
829: jra _ASM_LABEL(fault) | do it
830: #else
831: jra _C_LABEL(illinst)
832: #endif
833:
834: /*
835: * Handles all other FP coprocessor exceptions.
836: * Note that since some FP exceptions generate mid-instruction frames
837: * and may cause signal delivery, we need to test for stack adjustment
838: * after the trap call.
839: */
840: ENTRY_NOPROFILE(fpfault)
841: clrl sp@- | stack adjust count
842: moveml #0xFFFF,sp@- | save user registers
843: movl usp,a0 | and save
844: movl a0,sp@(FR_SP) | the user stack pointer
845: clrl sp@- | no VA arg
846: movl _C_LABEL(curpcb),a0 | current pcb
847: lea a0@(PCB_FPCTX),a0 | address of FP savearea
848: fsave a0@ | save state
849: #if defined(M68040) || defined(M68060)
850: /* always null state frame on 68040, 68060 */
851: cmpl #CPU_68040,_C_LABEL(cputype)
852: jge Lfptnull
853: #endif
854: tstb a0@ | null state frame?
855: jeq Lfptnull | yes, safe
856: clrw d0 | no, need to tweak BIU
857: movb a0@(1),d0 | get frame size
858: bset #3,a0@(0,d0:w) | set exc_pend bit of BIU
859: Lfptnull:
860: fmovem fpsr,sp@- | push fpsr as code argument
861: frestore a0@ | restore state
862: movl #T_FPERR,sp@- | push type arg
863: jra _ASM_LABEL(faultstkadj) | call trap and deal with stack cleanup
864:
865: /*
866: * Other exceptions only cause four and six word stack frame and require
867: * no post-trap stack adjustment.
868: */
869: ENTRY_NOPROFILE(hardtrap)
870: moveml #0xC0C0,sp@- | save scratch regs
871: lea sp@(16),a1 | get pointer to frame
872: movl a1,sp@-
873: movw sp@(26),d0
874: movl d0,sp@- | push exception vector info
875: movl sp@(26),sp@- | and PC
876: jbsr _C_LABEL(hardintr) | doit
877: lea sp@(12),sp | pop args
878: moveml sp@+,#0x0303 | restore regs
879: jra _ASM_LABEL(rei) | all done
880:
881: ENTRY_NOPROFILE(badtrap)
882: moveml #0xC0C0,sp@- | save scratch regs
883: movw sp@(22),sp@- | push exception vector info
884: clrw sp@-
885: movl sp@(22),sp@- | and PC
886: jbsr _C_LABEL(straytrap) | report
887: addql #8,sp | pop args
888: moveml sp@+,#0x0303 | restore regs
889: jra _ASM_LABEL(rei) | all done
890:
891: ENTRY_NOPROFILE(trap0)
892: clrl sp@- | stack adjust count
893: moveml #0xFFFF,sp@- | save user registers
894: movl usp,a0 | save the user SP
895: movl a0,sp@(FR_SP) | in the savearea
896: movl d0,sp@- | push syscall number
897: jbsr _C_LABEL(syscall) | handle it
898: addql #4,sp | pop syscall arg
899: tstl _C_LABEL(astpending)
900: jne Lrei2
901: tstb _C_LABEL(ssir)
902: jeq Ltrap1
903: movw #SPL1,sr
904: tstb _C_LABEL(ssir)
905: jne Lsir1
906: Ltrap1:
907: movl sp@(FR_SP),a0 | grab and restore
908: movl a0,usp | user SP
909: moveml sp@+,#0x7FFF | restore most registers
910: addql #8,sp | pop SP and stack adjust
911: rte
912:
913: /*
914: * Trap 1 - sigreturn
915: */
916: ENTRY_NOPROFILE(trap1)
917: jra _ASM_LABEL(sigreturn)
918:
919: /*
920: * Trap 2 - trace trap
921: */
922: ENTRY_NOPROFILE(trap2)
923: jra _C_LABEL(trace)
924:
925: /*
926: * Trap 12 is the entry point for the cachectl "syscall" (both HPUX & BSD)
927: * cachectl(command, addr, length)
928: * command in d0, addr in a1, length in d1
929: */
930: ENTRY_NOPROFILE(trap12)
931: movl d1,sp@- | push length
932: movl a1,sp@- | push addr
933: movl d0,sp@- | push command
934: movl CURPROC,sp@- | push proc pointer
935: jbsr _C_LABEL(cachectl) | do it
936: lea sp@(16),sp | pop args
937: jra _ASM_LABEL(rei) | all done
938:
939: /*
940: * Trace (single-step) trap (trap 1 or 2) instruction. Kernel-mode is
941: * special. User mode traps are simply passed on to trap().
942: */
943: ENTRY_NOPROFILE(trace)
944: clrl sp@-
945: moveml #0xFFFF,sp@-
946: moveq #T_TRACE,d0
947:
948: | Check PSW and see what happened.
949: | T=0 S=0 (should not happen)
950: | T=1 S=0 trace trap from user mode
951: | T=0 S=1 trace trap on a trap instruction
952: | T=0 S=0 trace trap from system mode (kernel breakpoint)
953:
954: movw sp@(FR_HW),d1 | get SSW
955: notw d1 | XXX no support for T0 on 680[234]0
956: andw #PSL_S,d1 | from system mode (T=1, S=1)?
957: jeq Lkbrkpt | yes, kernel breakpoint
958: jra _ASM_LABEL(fault) | no, user-mode fault
959:
960: /*
961: * Trap 15 is used for:
962: * - GDB breakpoints (in user programs)
963: * - KGDB breakpoints (in the kernel)
964: * - trace traps for SUN binaries (not fully supported yet)
965: * - calling the prom, but only from the kernel
966: * We just pass it on and let trap() sort it all out
967: */
968: ENTRY_NOPROFILE(trap15)
969: clrl sp@- | stack adjust count
970: moveml #0xFFFF,sp@-
971:
972: tstl _C_LABEL(promcall)
973: jeq L_notpromcall
974: moveml sp@+,#0xFFFF
975: addql #4, sp
976: | unwind stack to put to known value
977: | this routine is from the 147 BUG manual
978: | currently save and restore are excessive.
979: subql #4,sp
980: link a6,#0
981: moveml #0xFFFE,sp@-
982: movl _C_LABEL(promvbr),a0
983: movw a6@(14),d0
984: andl #0xfff,d0
985: movl a0@(d0:w),a6@(4)
986: moveml sp@+,#0x7FFF
987: unlk a6
988: rts
989: | really jumps to the bug trap handler
990: L_notpromcall:
991: moveq #T_TRAP15,d0
992: movw sp@(FR_HW),d1 | get PSW
993: andw #PSL_S,d1 | from system mode?
994: jne Lkbrkpt | yes, kernel breakpoint
995: jra _ASM_LABEL(fault) | no, user-mode fault
996:
997: Lkbrkpt: | Kernel-mode breakpoint or trace trap. (d0=trap_type)
998: | Save the system sp rather than the user sp.
999: movw #PSL_HIGHIPL,sr | lock out interrupts
1000: lea sp@(FR_SIZE),a6 | Save stack pointer
1001: movl a6,sp@(FR_SP) | from before trap
1002:
1003: | If we are not on tmpstk switch to it.
1004: | (so debugger can change the stack pointer)
1005: movl a6,d1
1006: cmpl #_ASM_LABEL(tmpstk),d1
1007: jls Lbrkpt2 | already on tmpstk
1008: | Copy frame to the temporary stack
1009: movl sp,a0 | a0=src
1010: lea _ASM_LABEL(tmpstk)-96,a1 | a1=dst
1011: movl a1,sp | sp=new frame
1012: moveq #FR_SIZE,d1
1013: Lbrkpt1:
1014: movl a0@+,a1@+
1015: subql #4,d1
1016: bgt Lbrkpt1
1017:
1018: Lbrkpt2:
1019: | Call the trap handler for the kernel debugger.
1020: | Do not call trap() to do it, so that we can
1021: | set breakpoints in trap() if we want. We know
1022: | the trap type is either T_TRACE or T_BREAKPOINT.
1023: | If we have both DDB and KGDB, let KGDB see it first,
1024: | because KGDB will just return 0 if not connected.
1025: | Save args in d2, a2
1026: movl d0,d2 | trap type
1027: movl sp,a2 | frame ptr
1028: #ifdef KGDB
1029: | Let KGDB handle it (if connected)
1030: movl a2,sp@- | push frame ptr
1031: movl d2,sp@- | push trap type
1032: jbsr _C_LABEL(kgdb_trap) | handle the trap
1033: addql #8,sp | pop args
1034: cmpl #0,d0 | did kgdb handle it?
1035: jne Lbrkpt3 | yes, done
1036: #endif
1037: #ifdef DDB
1038: | Let DDB handle it
1039: movl a2,sp@- | push frame ptr
1040: movl d2,sp@- | push trap type
1041: jbsr _C_LABEL(kdb_trap) | handle the trap
1042: addql #8,sp | pop args
1043: cmpl #0,d0 | did ddb handle it?
1044: jne Lbrkpt3 | yes, done
1045: #endif
1046: | Drop into the prom
1047: BUGCALL(MVMEPROM_EXIT)
1048: Lbrkpt3:
1049: | The stack pointer may have been modified, or
1050: | data below it modified (by kgdb push call),
1051: | so push the hardware frame at the current sp
1052: | before restoring registers and returning.
1053:
1054: movl sp@(FR_SP),a0 | modified sp
1055: lea sp@(FR_SIZE),a1 | end of our frame
1056: movl a1@-,a0@- | copy 2 longs with
1057: movl a1@-,a0@- | ... predecrement
1058: movl a0,sp@(FR_SP) | sp = h/w frame
1059: moveml sp@+,#0x7FFF | restore all but sp
1060: movl sp@,sp | ... and sp
1061: rte | all done
1062:
1063: /* Use common m68k sigreturn */
1064: #include <m68k/m68k/sigreturn.s>
1065:
1066: /*
1067: * Interrupt handlers.
1068: * No device interrupts are auto-vectored.
1069: */
1070:
1071: ENTRY_NOPROFILE(spurintr)
1072: addql #1,_C_LABEL(uvmexp)+UVMEXP_INTRS
1073: jra _ASM_LABEL(rei) | all done
1074:
1075: /*
1076: * Emulation of VAX REI instruction.
1077: *
1078: * This code deals with checking for and servicing ASTs
1079: * (profiling, scheduling) and software interrupts (network, softclock).
1080: * We check for ASTs first, just like the VAX. To avoid excess overhead
1081: * the T_ASTFLT handling code will also check for software interrupts so we
1082: * do not have to do it here. After identifing that we need an AST we
1083: * drop the IPL to allow device interrupts.
1084: *
1085: * This code is complicated by the fact that sendsig may have been called
1086: * necessitating a stack cleanup.
1087: */
1088:
1089: BSS(ssir,1)
1090:
1091: ASENTRY_NOPROFILE(rei)
1092: tstl _C_LABEL(astpending) | AST pending?
1093: jeq Lchksir | no, go check for SIR
1094: Lrei1:
1095: btst #5,sp@ | yes, are we returning to user mode?
1096: jne Lchksir | no, go check for SIR
1097: movw #PSL_LOWIPL,sr | lower SPL
1098: clrl sp@- | stack adjust
1099: moveml #0xFFFF,sp@- | save all registers
1100: movl usp,a1 | including
1101: movl a1,sp@(FR_SP) | the users SP
1102: Lrei2:
1103: clrl sp@- | VA == none
1104: clrl sp@- | code == none
1105: movl #T_ASTFLT,sp@- | type == async system trap
1106: jbsr _C_LABEL(trap) | go handle it
1107: lea sp@(12),sp | pop value args
1108: movl sp@(FR_SP),a0 | restore user SP
1109: movl a0,usp | from save area
1110: movw sp@(FR_ADJ),d0 | need to adjust stack?
1111: jne Laststkadj | yes, go to it
1112: moveml sp@+,#0x7FFF | no, restore most user regs
1113: addql #8,sp | toss SP and stack adjust
1114: rte | and do real RTE
1115: Laststkadj:
1116: lea sp@(FR_HW),a1 | pointer to HW frame
1117: addql #8,a1 | source pointer
1118: movl a1,a0 | source
1119: addw d0,a0 | + hole size = dest pointer
1120: movl a1@-,a0@- | copy
1121: movl a1@-,a0@- | 8 bytes
1122: movl a0,sp@(FR_SP) | new SSP
1123: moveml sp@+,#0x7FFF | restore user registers
1124: movl sp@,sp | and our SP
1125: rte | and do real RTE
1126: Lchksir:
1127: tstb _C_LABEL(ssir) | SIR pending?
1128: jeq Ldorte | no, all done
1129: movl d0,sp@- | need a scratch register
1130: movw sp@(4),d0 | get SR
1131: andw #PSL_IPL7,d0 | mask all but IPL
1132: jne Lnosir | came from interrupt, no can do
1133: movl sp@+,d0 | restore scratch register
1134: Lgotsir:
1135: movw #SPL1,sr | prevent others from servicing int
1136: tstb _C_LABEL(ssir) | too late?
1137: jeq Ldorte | yes, oh well...
1138: clrl sp@- | stack adjust
1139: moveml #0xFFFF,sp@- | save all registers
1140: movl usp,a1 | including
1141: movl a1,sp@(FR_SP) | the users SP
1142: Lsir1:
1143: clrl sp@- | VA == none
1144: clrl sp@- | code == none
1145: movl #T_SSIR,sp@- | type == software interrupt
1146: jbsr _C_LABEL(trap) | go handle it
1147: lea sp@(12),sp | pop value args
1148: movl sp@(FR_SP),a0 | restore
1149: movl a0,usp | user SP
1150: moveml sp@+,#0x7FFF | and all remaining registers
1151: addql #8,sp | pop SP and stack adjust
1152: rte
1153: Lnosir:
1154: movl sp@+,d0 | restore scratch register
1155: Ldorte:
1156: rte | real return
1157:
1158: /*
1159: * Use common m68k signal trampoline.
1160: */
1161: #include <m68k/m68k/sigcode.s>
1162:
1163: /*
1164: * Use common m68k support routines.
1165: */
1166: #include <m68k/m68k/support.s>
1167:
1168: /*
1169: * Use common m68k process manipulation routines.
1170: */
1171: #include <m68k/m68k/proc_subr.s>
1172:
1173: .data
1174: GLOBAL(curpcb)
1175: .long 0
1176:
1177: ASBSS(nullpcb,SIZEOF_PCB)
1178:
1179: /*
1180: * At exit of a process, do a switch for the last time.
1181: * Switch to a safe stack and PCB, and deallocate the process's resources.
1182: */
1183: ENTRY(switch_exit)
1184: movl sp@(4),a0
1185: | save state into garbage pcb
1186: movl #_ASM_LABEL(nullpcb),_C_LABEL(curpcb)
1187: lea _ASM_LABEL(tmpstk),sp | goto a tmp stack
1188:
1189: /* Schedule the vmspace and stack to be freed. */
1190: movl a0,sp@- | exit2(p)
1191: jbsr _C_LABEL(exit2)
1192: lea sp@(4),sp | pop args
1193:
1194: jra _C_LABEL(cpu_switch)
1195:
1196: /*
1197: * When no processes are on the runq, Swtch branches to Idle
1198: * to wait for something to come ready.
1199: */
1200: ASENTRY_NOPROFILE(Idle)
1201: stop #PSL_LOWIPL
1202: movw #PSL_HIGHIPL,sr
1203: movl _C_LABEL(whichqs),d0
1204: jeq _ASM_LABEL(Idle)
1205: jra Lsw1
1206:
1207: Lbadsw:
1208: PANIC("switch")
1209: /*NOTREACHED*/
1210:
1211: /*
1212: * cpu_switch()
1213: *
1214: * NOTE: On the mc68851 we attempt to avoid flushing the
1215: * entire ATC. The effort involved in selective flushing may not be
1216: * worth it, maybe we should just flush the whole thing?
1217: *
1218: * NOTE 2: With the new VM layout we now no longer know if an inactive
1219: * user's PTEs have been changed (formerly denoted by the SPTECHG p_flag
1220: * bit). For now, we just always flush the full ATC.
1221: */
1222: ENTRY(cpu_switch)
1223: movl _C_LABEL(curpcb),a0 | current pcb
1224: movw sr,a0@(PCB_PS) | save sr before changing ipl
1225: #ifdef notyet
1226: movl CURPROC,sp@- | remember last proc running
1227: #endif
1228: clrl CURPROC
1229:
1230: /*
1231: * Find the highest-priority queue that isn't empty,
1232: * then take the first proc from that queue.
1233: */
1234: movw #PSL_HIGHIPL,sr | lock out interrupts
1235: movl _C_LABEL(whichqs),d0
1236: jeq _ASM_LABEL(Idle)
1237: Lsw1:
1238: movl d0,d1
1239: negl d0
1240: andl d1,d0
1241: bfffo d0{#0:#32},d1
1242: eorib #31,d1
1243:
1244: movl d1,d0
1245: lslb #3,d1 | convert queue number to index
1246: addl #_C_LABEL(qs),d1 | locate queue (q)
1247: movl d1,a1
1248: movl a1@(P_FORW),a0 | p = q->p_forw
1249: cmpal d1,a0 | anyone on queue?
1250: jeq Lbadsw | no, panic
1251: movl a0@(P_FORW),a1@(P_FORW) | q->p_forw = p->p_forw
1252: movl a0@(P_FORW),a1 | n = p->p_forw
1253: movl d1,a1@(P_BACK) | n->p_back = q
1254: cmpal d1,a1 | anyone left on queue?
1255: jne Lsw2 | yes, skip
1256: movl _C_LABEL(whichqs),d1
1257: bclr d0,d1 | no, clear bit
1258: movl d1,_C_LABEL(whichqs)
1259: Lsw2:
1260: movl a0,CURPROC
1261: clrl _C_LABEL(want_resched)
1262: #ifdef notyet
1263: movl sp@+,a1
1264: cmpl a0,a1 | switching to same proc?
1265: jeq Lswdone | yes, skip save and restore
1266: #endif
1267: /*
1268: * Save state of previous process in its pcb.
1269: */
1270: movl _C_LABEL(curpcb),a1
1271: moveml #0xFCFC,a1@(PCB_REGS) | save non-scratch registers
1272: movl usp,a2 | grab USP (a2 has been saved)
1273: movl a2,a1@(PCB_USP) | and save it
1274: #ifdef FPU_EMULATE
1275: tstl _C_LABEL(fputype) | do we have any FPU?
1276: jeq Lswnofpsave | no, dont save
1277: #endif
1278: lea a1@(PCB_FPCTX),a2 | pointer to FP save area
1279: fsave a2@ | save FP state
1280: #ifdef M68060
1281: cmpl #FPU_68060,_C_LABEL(fputype) | is 68060?
1282: jeq Lsavfp60 | yes, goto Lsavfp60
1283: #endif /* M68060 */
1284: tstb a2@ | null state frame?
1285: jeq Lswnofpsave | yes, all done
1286: fmovem fp0-fp7,a2@(FPF_REGS) | save FP general registers
1287: fmovem fpcr/fpsr/fpi,a2@(FPF_FPCR) | save FP control registers
1288: #ifdef M68060
1289: jra Lswnofpsave
1290: Lsavfp60:
1291: tstb a2@(2) | null state frame?
1292: jeq Lswnofpsave | yes, all done
1293: fmovem fp0-fp7,a2@(FPF_REGS) | save FP general registers
1294: fmovem fpcr,a2@(FPF_FPCR) | save FP control registers
1295: fmovem fpsr,a2@(FPF_FPSR)
1296: fmovem fpi,a2@(FPF_FPI)
1297: #endif /* M68060 */
1298: Lswnofpsave:
1299: #ifdef DIAGNOSTIC
1300: tstl a0@(P_WCHAN)
1301: jne Lbadsw
1302: cmpb #SRUN,a0@(P_STAT)
1303: jne Lbadsw
1304: #endif
1305: movb #SONPROC,a0@(P_STAT)
1306: clrl a0@(P_BACK) | clear back link
1307: movl a0@(P_ADDR),a1 | get p_addr
1308: movl a1,_C_LABEL(curpcb)
1309:
1310: /*
1311: * Activate process's address space.
1312: * XXX Should remember the last USTP value loaded, and call this
1313: * XXX only of it has changed.
1314: */
1315: pea a0@ | push proc
1316: jbsr _C_LABEL(pmap_activate) | pmap_activate(p)
1317: addql #4,sp
1318: movl _C_LABEL(curpcb),a1 | restore p_addr
1319:
1320: lea _ASM_LABEL(tmpstk),sp | now goto a tmp stack for NMI
1321:
1322: moveml a1@(PCB_REGS),#0xFCFC | and registers
1323: movl a1@(PCB_USP),a0
1324: movl a0,usp | and USP
1325:
1326: #ifdef FPU_EMULATE
1327: tstl _C_LABEL(fputype) | do we _have_ any fpu?
1328: jne Lresnonofpatall
1329: movw a1@(PCB_PS),sr | no, restore PS
1330: moveq #1,d0 | return 1 (for alternate returns)
1331: rts
1332: Lresnonofpatall:
1333: #endif
1334: lea a1@(PCB_FPCTX),a0 | pointer to FP save area
1335: #ifdef M68060
1336: cmpl #FPU_68060,_C_LABEL(fputype) | is 68060?
1337: jeq Lresfp60rest1 | yes, goto Lresfp60rest1
1338: #endif /* M68060 */
1339: tstb a0@ | null state frame?
1340: jeq Lresfprest2 | yes, easy
1341: fmovem a0@(FPF_FPCR),fpcr/fpsr/fpi | restore FP control registers
1342: fmovem a0@(FPF_REGS),fp0-fp7 | restore FP general registers
1343: Lresfprest2:
1344: frestore a0@ | restore state
1345: movw a1@(PCB_PS),sr | no, restore PS
1346: moveq #1,d0 | return 1 (for alternate returns)
1347: rts
1348:
1349: #ifdef M68060
1350: Lresfp60rest1:
1351: tstb a0@(2) | null state frame?
1352: jeq Lresfp60rest2 | yes, easy
1353: fmovem a0@(FPF_FPCR),fpcr | restore FP control registers
1354: fmovem a0@(FPF_FPSR),fpsr
1355: fmovem a0@(FPF_FPI),fpi
1356: fmovem a0@(FPF_REGS),fp0-fp7 | restore FP general registers
1357: Lresfp60rest2:
1358: frestore a0@ | restore state
1359: movw a1@(PCB_PS),sr | no, restore PS
1360: moveq #1,d0 | return 1 (for alternate returns)
1361: rts
1362: #endif /* M68060 */
1363:
1364:
1365: /*
1366: * savectx(pcb)
1367: * Update pcb, saving current processor state.
1368: */
1369: ENTRY(savectx)
1370: movl sp@(4),a1
1371: movw sr,a1@(PCB_PS)
1372: movl usp,a0 | grab USP
1373: movl a0,a1@(PCB_USP) | and save it
1374: moveml #0xFCFC,a1@(PCB_REGS) | save non-scratch registers
1375: #ifdef FPU_EMULATE
1376: tstl _C_LABEL(fputype)
1377: jeq Lsavedone
1378: #endif
1379: lea a1@(PCB_FPCTX),a0 | pointer to FP save area
1380: fsave a0@ | save FP state
1381: #ifdef M68060
1382: cmpl #FPU_68060,_C_LABEL(fputype) | is 68060?
1383: jeq Lsavctx60 | yes, goto Lsavctx60
1384: #endif
1385: tstb a0@ | null state frame?
1386: jeq Lsavedone | yes, all done
1387: fmovem fp0-fp7,a0@(FPF_REGS) | save FP general registers
1388: fmovem fpcr/fpsr/fpi,a0@(FPF_FPCR) | save FP control registers
1389: moveq #0,d0
1390: rts
1391: #ifdef M68060
1392: Lsavctx60:
1393: tstb a0@(2)
1394: jeq Lsavedone
1395: fmovem fp0-fp7,a0@(FPF_REGS) | save FP general registers
1396: fmovem fpcr,a0@(FPF_FPCR) | save FP control registers
1397: fmovem fpsr,a0@(FPF_FPSR)
1398: fmovem fpi,a0@(FPF_FPI)
1399: #endif
1400: Lsavedone:
1401: moveq #0,d0 | return 0
1402: rts
1403:
1404: #if defined(M68040) || defined(M68060)
1405: ENTRY(suline)
1406: movl sp@(4),a0 | address to write
1407: movl _C_LABEL(curpcb),a1 | current pcb
1408: movl #Lslerr,a1@(PCB_ONFAULT) | where to return to on a fault
1409: movl sp@(8),a1 | address of line
1410: movl a1@+,d0 | get lword
1411: movsl d0,a0@+ | put lword
1412: nop | sync
1413: movl a1@+,d0 | get lword
1414: movsl d0,a0@+ | put lword
1415: nop | sync
1416: movl a1@+,d0 | get lword
1417: movsl d0,a0@+ | put lword
1418: nop | sync
1419: movl a1@+,d0 | get lword
1420: movsl d0,a0@+ | put lword
1421: nop | sync
1422: moveq #0,d0 | indicate no fault
1423: jra Lsldone
1424: Lslerr:
1425: moveq #-1,d0
1426: Lsldone:
1427: movl _C_LABEL(curpcb),a1 | current pcb
1428: clrl a1@(PCB_ONFAULT) | clear fault address
1429: rts
1430: #endif
1431:
1432: /*
1433: * Invalidate entire TLB.
1434: */
1435: ASENTRY_NOPROFILE(TBIA)
1436: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040 or 68060?
1437: jle Ltbia040 | yes, goto Ltbia040
1438: pflusha | flush entire TLB
1439: tstl _C_LABEL(mmutype)
1440: jpl Lmc68851a | 68851 implies no d-cache
1441: movl #DC_CLEAR,d0
1442: movc d0,cacr | invalidate on-chip d-cache
1443: Lmc68851a:
1444: rts
1445: Ltbia040:
1446: .word 0xf518 | pflusha
1447: #ifdef M68060
1448: cmpl #MMU_68060,_C_LABEL(mmutype) | is 68060?
1449: jne Ltbiano60 | no, skip
1450: movc cacr,d0
1451: orl #IC60_CABC,d0 | and clear all branch cache entries
1452: movc d0,cacr
1453: #endif
1454: Ltbiano60:
1455: rts
1456:
1457:
1458: /*
1459: * Invalidate any TLB entry for given VA (TB Invalidate Single)
1460: */
1461: ENTRY(TBIS)
1462: movl sp@(4),a0 | get addr to flush
1463: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040 or 68060 ?
1464: jle Ltbis040 | yes, goto Ltbis040
1465: tstl _C_LABEL(mmutype)
1466: jpl Lmc68851b | is 68851?
1467: pflush #0,#0,a0@ | flush address from both sides
1468: movl #DC_CLEAR,d0
1469: movc d0,cacr | invalidate on-chip data cache
1470: rts
1471: Lmc68851b:
1472: pflushs #0,#0,a0@ | flush address from both sides
1473: rts
1474: Ltbis040:
1475: moveq #FC_SUPERD,d0 | select supervisor
1476: movc d0,dfc
1477: .word 0xf508 | pflush a0@
1478: moveq #FC_USERD,d0 | select user
1479: movc d0,dfc
1480: .word 0xf508 | pflush a0@
1481: #ifdef M68060
1482: cmpl #MMU_68060,_C_LABEL(mmutype) | is 68060?
1483: jne Ltbisno60 | no, skip
1484: movc cacr,d0
1485: orl #IC60_CABC,d0 | and clear all branch cache entries
1486: movc d0,cacr
1487: Ltbisno60:
1488: #endif
1489: rts
1490:
1491: /*
1492: * Invalidate supervisor side of TLB
1493: */
1494: #if defined(M68060)
1495: ENTRY(TBIAS)
1496: | 68060 cannot specify supervisor/user on pflusha, so we flush all
1497: .word 0xf518 | pflusha
1498: movc cacr,d0
1499: orl #IC60_CABC,d0 | and clear all branch cache entries
1500: movc d0,cacr
1501: rts
1502: #endif
1503:
1504: #if defined(COMPAT_HPUX) || defined(M68060)
1505: /*
1506: * Invalidate user side of TLB
1507: */
1508: ENTRY(TBIAU)
1509: cmpl #MMU_68040,_C_LABEL(mmutype)
1510: jle Ltbiau040
1511: tstl _C_LABEL(mmutype)
1512: jpl Lmc68851d | 68851?
1513: pflush #0,#4 | flush user TLB entries
1514: movl #DC_CLEAR,d0
1515: movc d0,cacr | invalidate on-chip d-cache
1516: rts
1517: Lmc68851d:
1518: pflushs #0,#4 | flush user TLB entries
1519: rts
1520: Ltbiau040:
1521: | 68040 cannot specify supervisor/user on pflusha, so we flush all
1522: .word 0xf518 | pflusha
1523: #ifdef M68060
1524: cmpl #MMU_68060,_C_LABEL(mmutype)
1525: jne Ltbiauno60
1526: movc cacr,d0
1527: orl #IC60_CUBC,d0 | but only user branch cache entries
1528: movc d0,cacr
1529: Ltbiauno60:
1530: #endif
1531: rts
1532: #endif /* defined(COMPAT_HPUX) || defined(M68060) */
1533:
1534: /*
1535: * Invalidate instruction cache
1536: */
1537: ENTRY(ICIA)
1538: #if defined(M68040) || defined(M68060)
1539: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040 or 68060?
1540: jgt 1f | no, skip
1541: .word 0xf498 | cinva ic
1542: rts
1543: 1:
1544: #endif
1545: movl #IC_CLEAR,d0
1546: movc d0,cacr | invalidate i-cache
1547: rts
1548:
1549: /*
1550: * Invalidate data cache.
1551: *
1552: * NOTE: we do not flush 68030 on-chip cache as there are no aliasing
1553: * problems with DC_WA. The only cases we have to worry about are context
1554: * switch and TLB changes, both of which are handled "in-line" in resume
1555: * and TBI*.
1556: * Because of this, since there is no way on 68040 and 68060 to flush
1557: * user and supervisor modes specfically, DCIS and DCIU are the same entry
1558: * point as DCIA.
1559: */
1560: ENTRY(DCIA)
1561: ENTRY(DCIS)
1562: ENTRY(DCIU)
1563: #if defined(M68040) || defined(M68060)
1564: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040 or 68060?
1565: jgt 1f | no, skip
1566: .word 0xf478 | cpusha dc
1567: #endif
1568: rts
1569:
1570: #if defined(M68040) || defined(M68060)
1571: ENTRY(ICPA)
1572: .word 0xf498 | cinva ic
1573: rts
1574: ENTRY(DCFA)
1575: .word 0xf478 | cpusha dc
1576: rts
1577: ENTRY(ICPL)
1578: movl sp@(4),a0 | address
1579: .word 0xf488 | cinvl ic,a0@
1580: rts
1581: ENTRY(ICPP)
1582: movl sp@(4),a0 | address
1583: .word 0xf490 | cinvp ic,a0@
1584: rts
1585: ENTRY(DCPL)
1586: movl sp@(4),a0 | address
1587: .word 0xf448 | cinvl dc,a0@
1588: rts
1589: ENTRY(DCPP)
1590: movl sp@(4),a0 | address
1591: .word 0xf450 | cinvp dc,a0@
1592: rts
1593: ENTRY(DCFL)
1594: movl sp@(4),a0 | address
1595: .word 0xf468 | cpushl dc,a0@
1596: rts
1597: ENTRY(DCFP)
1598: movl sp@(4),a0 | address
1599: .word 0xf470 | cpushp dc,a0@
1600: rts
1601: #endif
1602:
1603: ENTRY(getsfc)
1604: movc sfc,d0
1605: rts
1606:
1607: ENTRY(getdfc)
1608: movc dfc,d0
1609: rts
1610:
1611: /*
1612: * Load a new user segment table pointer.
1613: */
1614: ENTRY(loadustp)
1615: movl sp@(4),d0 | new USTP
1616: moveq #PGSHIFT,d1
1617: lsll d1,d0 | convert to addr
1618: #if defined(M68040) || defined(M68060)
1619: cmpl #MMU_68040,_C_LABEL(mmutype)
1620: #ifdef M68060
1621: jlt Lldustp060
1622: #endif
1623: #ifdef M68040
1624: jeq Lldustp040
1625: #endif
1626: #endif
1627: pflusha | flush entire TLB
1628: lea _C_LABEL(protorp),a0 | CRP prototype
1629: movl d0,a0@(4) | stash USTP
1630: pmove a0@,crp | load root pointer
1631: movl #CACHE_CLR,d0
1632: movc d0,cacr | invalidate cache(s)
1633: rts
1634:
1635: #ifdef M68060
1636: Lldustp060:
1637: movc cacr,d1
1638: orl #IC60_CUBC,d1 | clear user branch cache entries
1639: movc d1,cacr
1640: /* FALLTHROUGH */
1641: #endif
1642: Lldustp040:
1643: .word 0xf518 | pflusha
1644: .long 0x4e7b0806 | movec d0,URP
1645: rts
1646:
1647: /*
1648: * Set processor priority level calls. Most are implemented with
1649: * inline asm expansions. However, spl0 requires special handling
1650: * as we need to check for our emulated software interrupts.
1651: */
1652:
1653: ENTRY(spl0)
1654: moveq #0,d0
1655: movw sr,d0 | get old SR for return
1656: movw #PSL_LOWIPL,sr | restore new SR
1657: tstb _C_LABEL(ssir) | software interrupt pending?
1658: jeq Lspldone | no, all done
1659: subql #4,sp | make room for RTE frame
1660: movl sp@(4),sp@(2) | position return address
1661: clrw sp@(6) | set frame type 0
1662: movw #PSL_LOWIPL,sp@ | and new SR
1663: jra Lgotsir | go handle it
1664: Lspldone:
1665: rts
1666:
1667: /*
1668: * Save and restore 68881 state.
1669: * Pretty awful looking since our assembler does not
1670: * recognize FP mnemonics.
1671: */
1672: ENTRY(m68881_save)
1673: movl sp@(4),a0 | save area pointer
1674: fsave a0@ | save state
1675: #ifdef M68060
1676: cmpl #FPU_68060,_C_LABEL(fputype) | is 68060?
1677: jeq Lm68060fpsave | yes, goto Lm68060fpsave
1678: #endif
1679: tstb a0@ | null state frame?
1680: jeq Lm68881sdone | yes, all done
1681: fmovem fp0-fp7,a0@(FPF_REGS) | save FP general registers
1682: fmovem fpcr/fpsr/fpi,a0@(FPF_FPCR) | save FP control registers
1683: Lm68881sdone:
1684: rts
1685:
1686: #ifdef M68060
1687: Lm68060fpsave:
1688: tstb a0@(2) | null state frame?
1689: jeq Lm68060sdone | yes, all done
1690: fmovem fp0-fp7,a0@(FPF_REGS) | save FP general registers
1691: fmovem fpcr,a0@(FPF_FPCR) | save FP control registers
1692: fmovem fpsr,a0@(FPF_FPSR)
1693: fmovem fpi,a0@(FPF_FPI)
1694: Lm68060sdone:
1695: rts
1696: #endif
1697:
1698: ENTRY(m68881_restore)
1699: movl sp@(4),a0 | save area pointer
1700: #ifdef M68060
1701: cmpl #FPU_68060,_C_LABEL(fputype) | is 68060?
1702: jeq Lm68060fprestore | yes, goto Lm68060fprestore
1703: #endif
1704: tstb a0@ | null state frame?
1705: jeq Lm68881rdone | yes, easy
1706: fmovem a0@(FPF_FPCR),fpcr/fpsr/fpi | restore FP control registers
1707: fmovem a0@(FPF_REGS),fp0-fp7 | restore FP general registers
1708: Lm68881rdone:
1709: frestore a0@ | restore state
1710: rts
1711:
1712: #ifdef M68060
1713: Lm68060fprestore:
1714: tstb a0@(2) | null state frame?
1715: jeq Lm68060fprdone | yes, easy
1716: fmovem a0@(FPF_FPCR),fpcr | restore FP control registers
1717: fmovem a0@(FPF_FPSR),fpsr
1718: fmovem a0@(FPF_FPI),fpi
1719: fmovem a0@(FPF_REGS),fp0-fp7 | restore FP general registers
1720: Lm68060fprdone:
1721: frestore a0@ | restore state
1722: rts
1723: #endif
1724:
1725: /*
1726: * Handle the nitty-gritty of rebooting the machine.
1727: * Basically we just turn off the MMU and jump to the appropriate ROM routine.
1728: * XXX add support for rebooting -- that means looking at boothowto and doing
1729: * the right thing
1730: */
1731: ENTRY_NOPROFILE(doboot)
1732: lea _ASM_LABEL(tmpstk),sp | physical SP in case of NMI
1733: #if defined(M68040) || defined(M68060)
1734: cmpl #MMU_68040,_C_LABEL(mmutype) | 68040?
1735: jgt Lbootnot040 | no, skip
1736: movl #0,d0
1737: movc d0,cacr | caches off
1738: .long 0x4e7b0003 | movc d0,tc (turn off MMU)
1739: bra 1f
1740: Lbootnot040:
1741: #endif
1742: movl #CACHE_OFF,d0
1743: movc d0,cacr | disable on-chip cache(s)
1744: movl #0,a7@ | value for pmove to TC (turn off MMU)
1745: pmove a7@,tc | disable MMU
1746:
1747: 1: movl #0,d0
1748: movc d0,vbr | ROM VBR
1749:
1750: /*
1751: * We're going down. Make various sick attempts to reset the board.
1752: */
1753: RELOC(cputyp, a0)
1754: movl a0@,d0
1755: cmpw #CPU_147,d0
1756: bne not147
1757: movl #0xfffe2000,a0 | MVME147: "struct vme1reg *"
1758: movw a0@,d0
1759: movl d0,d1
1760: andw #0x0001,d1 | is VME1_SCON_SWITCH set?
1761: beq 1f | not SCON. may not use SRESET.
1762: orw #0x0002,d0 | ok, assert VME1_SCON_SRESET
1763: movw d0,a0@
1764: 1:
1765: movl #0xff800000,a0 | if we get here, SRESET did not work.
1766: movl a0@(4),a0 | try jumping directly to the ROM.
1767: jsr a0@
1768: | still alive! just return to the prom..
1769: bra 3f
1770:
1771: not147:
1772: movl #0xfff40000,a0 | MVME16x: "struct vme2reg *"
1773: movl a0@(0x60),d0
1774: movl d0,d1
1775: andl #0x40000000,d1 | is VME2_TCTL_SCON set?
1776: beq 1f | not SCON. may not use SRESET.
1777: orl #0x00800000,d0 | ok, assert VME2_TCTL_SRST
1778: movl d0,a0@(0x60)
1779: 1:
1780: | lets try the local bus reset
1781: movl #0xfff40000,a0 | MVME16x: "struct vme2reg *"
1782: movl a0@(0x104),d0
1783: orw #0x00000080,d0
1784: movl d0,a0@(0x104)
1785: | lets try jumping off to rom.
1786: movl #0xff800000,a0 | if we get here, SRESET did not work.
1787: movl a0@(4),a0 | try jumping directly to the ROM.
1788: jsr a0@
1789: | still alive! just return to the prom..
1790:
1791: 3: BUGCALL(MVMEPROM_EXIT) | return to m68kbug
1792: /*NOTREACHED*/
1793:
1794: #if defined(M68060) && defined(M060SP)
1795: GLOBAL(intemu60)
1796: jra _I_CALL_TOP+128+0x00
1797: GLOBAL(fpiemu60)
1798: jra _FP_CALL_TOP+128+0x30
1799: GLOBAL(fpdemu60)
1800: jra _FP_CALL_TOP+128+0x38
1801: GLOBAL(fpeaemu60)
1802: jra _FP_CALL_TOP+128+0x40
1803: #endif
1804:
1805: .data
1806: GLOBAL(mmutype)
1807: .long MMU_68030 | default to MMU_68030
1808: GLOBAL(cputype)
1809: .long CPU_68030 | default to CPU_68030
1810: GLOBAL(fputype)
1811: .long FPU_68881 | default to 68881 FPU
1812: GLOBAL(protorp)
1813: .long 0,0 | prototype root pointer
1814: GLOBAL(cold)
1815: .long 1 | cold start flag
1816: GLOBAL(want_resched)
1817: .long 0
1818: GLOBAL(proc0paddr)
1819: .long 0 | KVA of proc0 u-area
1820: GLOBAL(intiobase)
1821: .long 0 | KVA of base of internal IO space
1822: GLOBAL(intiolimit)
1823: .long 0 | KVA of end of internal IO space
1824: GLOBAL(extiobase)
1825: .long 0 | KVA of base of external IO space
1826:
1827: #include <mvme68k/mvme68k/vectors.s>
CVSweb