Mercurial > hg > Members > kono > nitros9-code
changeset 1785:9d95e3246a61
rb1773.asm: now saves/restores original NMI vector
clock2_ds1315.asm: now makes SuperBoard version
krn.asm: redid with tabs
author | boisy |
---|---|
date | Fri, 08 Apr 2005 02:37:48 +0000 |
parents | be93c36931ad |
children | 49c4db9a5f69 |
files | defs/boot.d defs/scf.d defs/stat.d level1/ChangeLog level1/modules/clock2_ds1315.asm level1/modules/rb1773.asm level2/coco3/ChangeLog level2/coco3_6309/ChangeLog level2/modules/kernel/krn.asm |
diffstat | 9 files changed, 1045 insertions(+), 1001 deletions(-) [+] |
line wrap: on
line diff
--- a/defs/boot.d Fri Apr 08 00:34:27 2005 +0000 +++ b/defs/boot.d Fri Apr 08 02:37:48 2005 +0000 @@ -57,5 +57,3 @@ L3.SCF == 0h0660 ; SCF block ptr L3.RBF == L3.SCF+1 ; RBF block ptr .endif - - .endif
--- a/defs/scf.d Fri Apr 08 00:34:27 2005 +0000 +++ b/defs/scf.d Fri Apr 08 02:37:48 2005 +0000 @@ -29,48 +29,46 @@ ; ; These definitions are for SCF device descriptors. - .org M$DTyp -IT.DVC:: .rmb 1 ; Device type (DT.SCF) -IT.UPC:: .rmb 1 ; Uppercase flag -IT.BSO:: .rmb 1 ; Backspace behavior -IT.DLO:: .rmb 1 ; Delete behavior -IT.EKO:: .rmb 1 ; Echo flag -IT.ALF:: .rmb 1 ; Auto linefeed flag -IT.NUL:: .rmb 1 ; End-of-line null count -IT.PAU:: .rmb 1 ; Page pause flag -IT.PAG:: .rmb 1 ; Number of lines per page -IT.BSP:: .rmb 1 ; Backspace character -IT.DEL:: .rmb 1 ; Delete-line character -IT.EOR:: .rmb 1 ; End-of-record character -IT.EOF:: .rmb 1 ; End-of-file character -IT.RPR:: .rmb 1 ; Reprint-line character -IT.DUP:: .rmb 1 ; Duplicate-last-line character -IT.PSC:: .rmb 1 ; Pause character -IT.INT:: .rmb 1 ; Interrupt character -IT.QUT:: .rmb 1 ; Quit character -IT.BSE:: .rmb 1 ; Backspace echo character -IT.OVF:: .rmb 1 ; Bell character -IT.PAR:: .rmb 1 ; Parity -IT.BAU:: .rmb 1 ; Baud rate -IT.D2P:: .rmb 2 ; Attached device name string offset -IT.XON:: .rmb 1 ; X-ON character -IT.XOFF:: .rmb 1 ; X-OFF character -IT.COL:: .rmb 1 ; Number of columns for display -IT.ROW:: .rmb 1 ; Number of rows for display -IT.XTYP:: .rmb 1 ; Extended type (added by BRI) +IT.DVC == 0h18 ; Device type (DT.SCF) +IT.UPC == 0h19 ; Uppercase flag +IT.BSO == 0h1A ; Backspace behavior +IT.DLO == 0h1B ; Delete behavior +IT.EKO == 0h1C ; Echo flag +IT.ALF == 0h1D ; Auto linefeed flag +IT.NUL == 0h1E ; End-of-line null count +IT.PAU == 0h1F ; Page pause flag +IT.PAG == 0h20 ; Number of lines per page +IT.BSP == 0h21 ; Backspace character +IT.DEL == 0h22 ; Delete-line character +IT.EOR == 0h23 ; End-of-record character +IT.EOF == 0h24 ; End-of-file character +IT.RPR == 0h25 ; Reprint-line character +IT.DUP == 0h26 ; Duplicate-last-line character +IT.PSC == 0h27 ; Pause character +IT.INT == 0h28 ; Interrupt character +IT.QUT == 0h29 ; Quit character +IT.BSE == 0h2A ; Backspace echo character +IT.OVF == 0h2B ; Bell character +IT.PAR == 0h2C ; Parity +IT.BAU == 0h2D ; Baud rate +IT.D2P == 0h2E ; Attached device name string offset +IT.XON == 0h30 ; X-ON character +IT.XOFF == 0h31 ; X-OFF character +IT.COL == 0h32 ; Number of columns for display +IT.ROW == 0h33 ; Number of rows for display +IT.XTYP == 0h34 ; Extended type (added by BRI) .ifgt Level-1 ; Window Descriptor Additions ; For CoCo window, where IT.PAR = $80 - .org IT.ROW+1 -IT.WND:: .rmb 1 ; Window number (matches device name) ($2E) -IT.VAL:: .rmb 1 ; Use defaults on Init (0=no, 1=yes) -IT.STY:: .rmb 1 ; Screen type default -IT.CPX:: .rmb 1 ; Column start default -IT.CPY:: .rmb 1 ; Row start default -IT.FGC:: .rmb 1 ; Foreground color default -IT.BGC:: .rmb 1 ; Background color default -IT.BDC:: .rmb 1 ; Border color default +IT.WND == 0h33 ; Window number (matches device name) ($2E) +IT.VAL == 0h34 ; Use defaults on Init (0=no, 1=yes) +IT.STY == 0h35 ; Screen type default +IT.CPX == 0h36 ; Column start default +IT.CPY == 0h37 ; Row start default +IT.FGC == 0h38 ; Foreground color default +IT.BGC == 0h39 ; Background color default +IT.BDC == 0h3A ; Border color default .endif @@ -80,23 +78,22 @@ ; ; SCF devices must reserve this space for SCF ; - .org V.USER -V.TYPE:: .rmb 1 ; Device type or parity -V.LINE:: .rmb 1 ; Lines left until end of page -V.PAUS:: .rmb 1 ; Immediate Pause request -V.DEV2:: .rmb 2 ; Attached device's static -V.INTR:: .rmb 1 ; Interrupt char -V.QUIT:: .rmb 1 ; Quit char -V.PCHR:: .rmb 1 ; Pause char -V.ERR:: .rmb 1 ; Accumulated errors -V.XON:: .rmb 1 ; X-On char -V.XOFF:: .rmb 1 ; X-Off char -V.KANJI:: .rmb 1 ; Kanji mode flag -V.KBUF:: .rmb 2 ; Kana - Kanji convert routine work address -V.MODADR:: .rmb 2 ; Kana - Kanji convert module address -V.PDLHd:: .rmb 2 ; Open path descriptor list head pointer -V.RSV:: .rmb 5 ; Reserve bytes for future expansion -V.SCF == . ; Total SCF manager static overhead +V.TYPE == 0h06 ; Device type or parity +V.LINE == 0h07 ; Lines left until end of page +V.PAUS == 0h08 ; Immediate Pause request +V.DEV2 == 0h09 ; Attached device's static +V.INTR == 0h0B ; Interrupt char +V.QUIT == 0h0C ; Quit char +V.PCHR == 0h0D ; Pause char +V.ERR == 0h0E ; Accumulated errors +V.XON == 0h0F ; X-On char +V.XOFF == 0h10 ; X-Off char +V.KANJI == 0h11 ; Kanji mode flag +V.KBUF == 0h12 ; Kana - Kanji convert routine work address +V.MODADR == 0h14 ; Kana - Kanji convert module address +V.PDLHd == 0h16 ; Open path descriptor list head pointer +V.RSV == 0h18 ; Reserve bytes for future expansion +V.SCF == 0h1D ; Total SCF manager static overhead .page ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; @@ -106,44 +103,43 @@ ; via the I$Open system call (processed by IOMan). Process ; descriptors track state information of a path. ; - .org PD.FST -PD.DV2:: .rmb 2 ; Output device table pointer -PD.RAW:: .rmb 1 ; Read/Write or ReadLn/WritLn mode -PD.MAX:: .rmb 2 ; ReadLn high byte count -PD.MIN:: .rmb 1 ; Devices are "mine" if clear -PD.STS:: .rmb 2 ; Status routine module addr -PD.STM:: .rmb 2 ; Reserved for status routine +PD.DV2 rmb 0h32 ; Output device table pointer +PD.RAW rmb 0h34 ; Read/Write or ReadLn/WritLn mode +PD.MAX rmb 0h35 ; ReadLn high byte count +PD.MIN rmb 0h37 ; Devices are "mine" if clear +PD.STS rmb 0h38 ; Status routine module addr +PD.STM rmb 0h3A ; Reserved for status routine .org PD.OPT .rmb 1 ; Device type -PD.UPC:: .rmb 1 ; Case (0=both, 1=upper only) -PD.BSO:: .rmb 1 ; Backspace (0=BSE, 1=BSE,SP,BSE) -PD.DLO:: .rmb 1 ; Delete (0=BSE over line, 1=CRLF) -PD.EKO:: .rmb 1 ; Echo (0=No Echo) -PD.ALF:: .rmb 1 ; Auto linefeed (0=No auto LF) -PD.NUL:: .rmb 1 ; End of Line null count -PD.PAU:: .rmb 1 ; Page pause (0=No end of page pause) -PD.PAG:: .rmb 1 ; Lines per page -PD.BSP:: .rmb 1 ; Backspace character -PD.DEL:: .rmb 1 ; Delete Line character -PD.EOR:: .rmb 1 ; End of Record character (read only) -PD.EOF:: .rmb 1 ; End of File character -PD.RPR:: .rmb 1 ; Reprint Line character -PD.DUP:: .rmb 1 ; Dup Last Line character -PD.PSC:: .rmb 1 ; Pause character -PD.INT:: .rmb 1 ; Keyboard interrupt character (CTRL-C) -PD.QUT:: .rmb 1 ; Keyboard quit character (CTRL-E) -PD.BSE:: .rmb 1 ; Backspace echo character -PD.OVF:: .rmb 1 ; Line overflow character (BELL) -PD.PAR:: .rmb 1 ; Parity code -PD.BAU:: .rmb 1 ; ACIA baud rate (Color Computer) -PD.D2P:: .rmb 2 ; Offset of DEV2 name -PD.XON:: .rmb 1 ; ACIA X-ON character -PD.XOFF:: .rmb 1 ; ACIA X-OFF character +PD.UPC == 1 ; Case (0=both, 1=upper only) +PD.BSO == 1 ; Backspace (0=BSE, 1=BSE,SP,BSE) +PD.DLO == 1 ; Delete (0=BSE over line, 1=CRLF) +PD.EKO == 1 ; Echo (0=No Echo) +PD.ALF == 1 ; Auto linefeed (0=No auto LF) +PD.NUL == 1 ; End of Line null count +PD.PAU == 1 ; Page pause (0=No end of page pause) +PD.PAG == 1 ; Lines per page +PD.BSP == 1 ; Backspace character +PD.DEL == 1 ; Delete Line character +PD.EOR == 1 ; End of Record character (read only) +PD.EOF == 1 ; End of File character +PD.RPR == 1 ; Reprint Line character +PD.DUP == 1 ; Dup Last Line character +PD.PSC == 1 ; Pause character +PD.INT == 1 ; Keyboard interrupt character (CTRL-C) +PD.QUT == 1 ; Keyboard quit character (CTRL-E) +PD.BSE == 1 ; Backspace echo character +PD.OVF == 1 ; Line overflow character (BELL) +PD.PAR == 1 ; Parity code +PD.BAU == 1 ; ACIA baud rate (Color Computer) +PD.D2P == 2 ; Offset of DEV2 name +PD.XON == 1 ; ACIA X-ON character +PD.XOFF == 1 ; ACIA X-OFF character OPTCNT == .-PD.OPT ; Total user settable options -PD.ERR:: .rmb 1 ; Most recent I/O error status -PD.TBL:: .rmb 2 ; Device table addr (copy) -PD.PLP:: .rmb 2 ; Path Descriptor List Pointer -PD.PST:: .rmb 1 ; Current path status +PD.ERR .rmb 1 ; Most recent I/O error status +PD.TBL .rmb 2 ; Device table addr (copy) +PD.PLP .rmb 2 ; Path Descriptor List Pointer +PD.PST .rmb 1 ; Current path status ; PD.PST values Path Descriptor Status byte
--- a/defs/stat.d Fri Apr 08 00:34:27 2005 +0000 +++ b/defs/stat.d Fri Apr 08 02:37:48 2005 +0000 @@ -14,7 +14,7 @@ .area STAT (ABS) .ifndef Level -Level == 1 +Level == 2 .endif .org 0
--- a/level1/ChangeLog Fri Apr 08 00:34:27 2005 +0000 +++ b/level1/ChangeLog Fri Apr 08 02:37:48 2005 +0000 @@ -1,3 +1,6 @@ +NitrOS-9/6809 Level 1 V03.02.05: +- rb1773 now properly saves/restores system's NMI vector. + NitrOS-9/6809 Level 1 V03.02.04: - Fixed several problems/mistakes in the V03.02.03 release.
--- a/level1/modules/clock2_ds1315.asm Fri Apr 08 00:34:27 2005 +0000 +++ b/level1/modules/clock2_ds1315.asm Fri Apr 08 02:37:48 2005 +0000 @@ -27,8 +27,12 @@ IFNE BNB RTC.Base equ $FF5C In SCS* Decode ELSE + IFNE SUPERBOARD +RTC.Base equ SBRTCBase + ELSE RTC.Base equ $FF7C Fully decoded RTC ENDC + ENDC RTC.Zero equ -4 Send zero bit by writing this offset RTC.One equ -3 Send one bit by writing this offset RTC.Read equ 0 Read data from this offset
--- a/level1/modules/rb1773.asm Fri Apr 08 00:34:27 2005 +0000 +++ b/level1/modules/rb1773.asm Fri Apr 08 02:37:48 2005 +0000 @@ -78,6 +78,10 @@ * Separated the sector write and format write loops so that the CPU clock * can be slowed down during formats. This "corrects" problems some hardware * have with the current NitrOS-9 during formats. +* +* 1r1 2005/04/07 Boisy G. Pitre +* We now save the contents of D.NMI (Level 2) or D.XNMI (Level 1) before +* overwriting them, and then restore the original values at term time. nam rb1773 ttl Western Digital 1773 Disk Controller Driver @@ -99,7 +103,7 @@ tylg set Drivr+Objct atrv set ReEnt+rev -rev set $00 +rev set $01 edition set 1 * Configuration Settings @@ -152,6 +156,9 @@ IFGT Level-1 FBlock rmb 2 block number for format FTask rmb 1 task number for format +NMISave rmb 2 + ELSE +NMISave rmb 2 ENDC VIRQPak rmb 2 Vi.Cnt word for VIRQ u00B3 rmb 2 Vi.Rst word for VIRQ @@ -221,10 +228,19 @@ leax <DRVMEM,x point to next drive table decb done all drives yet? bne l1 no, init them all - leax >NMISvc,pc point to NMI service routine +*** Fix on 04/06/2005: we now save the contents of D.NMI (Level 2) +*** or D.XNMI (Level 1) before overwriting them. IFGT Level-1 - stx <D.NMI install as system NMI + ldx >D.NMI + stx NMISave,u + leax >NMISvc,pc point to NMI service routine + stx >D.NMI install as system NMI ELSE + ldx >D.XNMI + stx NMISave,u + lda >D.XNMI+2 + sta NMISave+2,u + leax >NMISvc,pc point to NMI service routine stx >D.XNMI+1 NMI jump vector operand lda #$7E JMP code sta >D.XNMI NMI jump vector opcode @@ -282,6 +298,18 @@ ENDC leay >IRQSvc,pc point to IRQ service routine os9 F$IRQ Remove IRQ +*** Fix: we now restore original D.NMI (Level 2) or D.XNMI (Level 1) +*** before overwriting them. + IFGT Level-1 + ldx NMISave,u + stx >D.NMI + ELSE + ldx NMISave,u + stx >D.XNMI + lda NMISave+2,u + sta >D.XNMI+2 + ENDC +*** pshs u Save device mem ptr ldu >sectbuf,u Get pointer to sector buffer ldd #512 Return sector buffer memory
--- a/level2/coco3/ChangeLog Fri Apr 08 00:34:27 2005 +0000 +++ b/level2/coco3/ChangeLog Fri Apr 08 02:37:48 2005 +0000 @@ -1,3 +1,6 @@ +NitrOS-9/6809 Level 2 V03.02.05: +- rb1773 now properly saves/restores system's NMI vector. + NitrOS-9/6809 Level 2 V03.02.04: - Fixed several problems/mistakes in the V03.02.03 release.
--- a/level2/coco3_6309/ChangeLog Fri Apr 08 00:34:27 2005 +0000 +++ b/level2/coco3_6309/ChangeLog Fri Apr 08 02:37:48 2005 +0000 @@ -1,3 +1,6 @@ +NitrOS-9/6809 Level 2 V03.02.05: +- rb1773 now properly saves/restores system's NMI vector. + NitrOS-9/6809 Level 2 V03.02.04: - Fixed several problems/mistakes in the V03.02.03 release.
--- a/level2/modules/kernel/krn.asm Fri Apr 08 00:34:27 2005 +0000 +++ b/level2/modules/kernel/krn.asm Fri Apr 08 02:37:48 2005 +0000 @@ -21,113 +21,114 @@ * 19r9 2004/07/12 Boisy G. Pitre * F$SRqMem now properly scans the DAT images of the system to update * the D.SysMem map. - - nam krn - ttl NitrOS-9 Level 2 Kernel - - IFP1 - use defsfile - ENDC - + + nam krn + ttl NitrOS-9 Level 2 Kernel + + ifp1 + use defsfile + endc + * defines for customizations -Revision set 9 module revision -Edition set 19 module Edition -Where equ $F000 absolute address of where Kernel starts in memory - - mod eom,MName,Systm,ReEnt+Revision,entry,0 - -MName fcs /Krn/ - fcb Edition - +Revision set 9 module revision +Edition set 19 module Edition +Where equ $F000 absolute address of where Kernel starts in memory + + mod eom,MName,Systm,ReEnt+Revision,entry,0 + +MName fcs /Krn/ + fcb Edition + * FILL - all unused bytes are now here - fcc /www.katvixen.com/ - fcc /www.katvixen.com/ - fcc /www.katvixen.com/ - IFNE H6309 - fcc /www.katvixen.com/ - fcc /www.katvixen.com/ - fcc /www.katvixen./ - ELSE - fcc /www.katvixen.com/ - fcc /01/ - ENDC - + fcc /www.katvixen.com/ + fcc /www.katvixen.com/ + fcc /www.katvixen.com/ + ifne H6309 + fcc /www.katvixen.com/ + fcc /www.katvixen.com/ + fcc /www.katvixen./ + else + fcc /www.katvixen.c/ + fcc /01/ + endc + * Might as well have this here as just past the end of Kernel... -DisTable fdb L0CD2+Where D.Clock absolute address at the start - fdb XSWI3+Where D.XSWI3 - fdb XSWI2+Where D.XSWI2 - fdb D.Crash D.XFIRQ crash on an FIRQ - fdb XIRQ+Where D.XIRQ - fdb XSWI+Where D.XSWI - fdb D.Crash D.XNMI crash on an NMI - fdb $0055 D.ErrRst ??? Not used as far as I can tell - fdb Sys.Vec+Where Initial Kernel system call vector -DisSize equ *-DisTable +DisTable + fdb L0CD2+Where D.Clock absolute address at the start + fdb XSWI3+Where D.XSWI3 + fdb XSWI2+Where D.XSWI2 + fdb D.Crash D.XFIRQ crash on an FIRQ + fdb XIRQ+Where D.XIRQ + fdb XSWI+Where D.XSWI + fdb D.Crash D.XNMI crash on an NMI + fdb $0055 D.ErrRst ??? Not used as far as I can tell + fdb Sys.Vec+Where Initial Kernel system call vector +DisSize equ *-DisTable * DO NOT ADD ANYTHING BETWEEN THESE 2 TABLES: see code using 'SubSiz', below -LowSub equ $0160 start of low memory subroutines -SubStrt equ * +LowSub equ $0160 start of low memory subroutines +SubStrt equ * * D.Flip0 - switch to system task 0 -R.Flip0 equ * - IFNE H6309 - aim #$FE,<D.TINIT map type 0 - lde <D.TINIT 'nother 2 bytes saved if GRFDRV does a 'tfr cc,e' - ste >DAT.Task and we can use A here, instead of E - ELSE - pshs a - lda <D.TINIT - anda #$FE - sta <D.TINIT - sta >DAT.Task - puls a - ENDC - clr <D.SSTskN - tfr x,s - tfr a,cc - rts -SubSiz equ *-SubStrt +R.Flip0 equ * + ifne H6309 + aim #$FE,<D.TINIT map type 0 + lde <D.TINIT another 2 bytes saved if GRFDRV does: tfr cc,e + ste >DAT.Task and we can use A here, instead of E + else + pshs a + lda <D.TINIT + anda #$FE + sta <D.TINIT + sta >DAT.Task + puls a + endc + clr <D.SSTskN + tfr x,s + tfr a,cc + rts +SubSiz equ *-SubStrt * Don't add any code here: See L0065, below. * Interrupt service routine -Vectors jmp [<-(D.SWI3-D.XSWI3),x] (-$10) (Jmp to 2ndary vector) - +Vectors jmp [<-(D.SWI3-D.XSWI3),x] (-$10) (Jmp to 2ndary vector) + * Let's start by initializing system page -entry equ * - IFEQ Level-1 - IFNE H6309 - ldq #(D.FMBM*256)+($400-D.FMBM) - leay <entry+2,pc - tfm y,d+ - tfr d,x - ELSE - ldx #D.FMBM - ldy #$400-D.FMBM - clra - clrb -loop1 std ,x++ - leay -2,y - bne loop1 - ENDC - ELSE - IFNE H6309 - ldq #$01001f00 Start address to clear & # bytes to clear - leay <entry+2,pc Point to a 0 - tfm y,d+ - std <D.CCStk Set pointer to top of global memory to $2000 - lda #$01 set task user table to $0100 - ELSE - ldx #$100 - ldy #$2000-$100 - clra - clrb -L001C std ,x++ - leay -2,y - bne L001C - stx <D.CCStk Set pointer to top of global memory to $2000 - inca D = $0100 - ENDC - ENDC - +entry equ * + ifeq Level-1 + ifne H6309 + ldq #(D.FMBM*256)+($400-D.FMBM) + leay <entry+2,pc + tfm y,d+ + tfr d,x + else + ldx #D.FMBM + ldy #$400-D.FMBM + clra + clrb +loop1 std ,x++ + leay -2,y + bne loop1 + endc + else + ifne H6309 + ldq #$01001f00 Start address to clear & # bytes to clear + leay <entry+2,pc Point to a 0 + tfm y,d+ + std <D.CCStk Set pointer to top of global memory to $2000 + lda #$01 set task user table to $0100 + else + ldx #$100 + ldy #$2000-$100 + clra + clrb +L001C std ,x++ + leay -2,y + bne L001C + stx <D.CCStk Set pointer to top of global memory to $2000 + inca D = $0100 + endc + endc + * Setup system direct page variables - IFEQ Level-1 + ifeq Level-1 * For Level 1 this is how the memory map looks after * the kernel has initialized: * @@ -157,834 +158,836 @@ * $0400-$04FF | System Stack | * | | * $0500---->|==================================| - - ldd #$200 - std <D.FMBM $200 = start of free memory bitmap - addb #$20 - std D.FMBM+2 $220 = end of free memory bitmap - addb #$02 - std <D.SysDis $222 = addr of sys dispatch table - addb #$70 - std <D.UsrDis $292 = addr of sys dispatch table - clrb - inca D = $300 - std <D.ModDir $300 = module dir start - stx <D.ModDir+2 $400 = module dir start - leas >$0100,x S = $500 (system stack) - ELSE - std <D.Tasks - addb #$20 set Task image table to $0120 - std <D.TskIPt - clrb set memory block map to $0200 - inca - std <D.BlkMap - addb #$40 set second block map to $0240 - std <D.BlkMap+2 - clrb set system service dispatch table to $0300 - inca - std <D.SysDis - inca set user dispatch table to $0400 - std <D.UsrDis - inca set process descriptor block to $0500 - std <D.PrcDBT - inca set system process descriptor to $0600 - std <D.SysPrc - std <D.Proc set user process descriptor to $0600 - adda #$02 set stack pointer to $0800 - tfr d,s - inca set system stack to $0900 - std <D.SysStk - std <D.SysMem set system memory map ptr $0900 - inca set module directory start to $0a00 - std <D.ModDir - std <D.ModEnd set module directory end to $0a00 - adda #$06 set secondary module directory start to $1000 - std <D.ModDir+2 - std <D.ModDAT set module directory DAT pointer to $1000 - std <D.CCMem set pointer to beginning of global memory to $1000 - ENDC + + ldd #$200 + std <D.FMBM $200 = start of free memory bitmap + addb #$20 + std D.FMBM+2 $220 = end of free memory bitmap + addb #$02 + std <D.SysDis $222 = addr of sys dispatch table + addb #$70 + std <D.UsrDis $292 = addr of sys dispatch table + clrb + inca D = $300 + std <D.ModDir $300 = module dir start + stx <D.ModDir+2 $400 = module dir start + leas >$0100,x S = $500 (system stack) + else + std <D.Tasks + addb #$20 set Task image table to $0120 + std <D.TskIPt + clrb set memory block map to $0200 + inca + std <D.BlkMap + addb #$40 set second block map to $0240 + std <D.BlkMap+2 + clrb set system service dispatch table to $0300 + inca + std <D.SysDis + inca set user dispatch table to $0400 + std <D.UsrDis + inca set process descriptor block to $0500 + std <D.PrcDBT + inca set system process descriptor to $0600 + std <D.SysPrc + std <D.Proc set user process descriptor to $0600 + adda #$02 set stack pointer to $0800 + tfr d,s + inca set system stack to $0900 + std <D.SysStk + std <D.SysMem set system memory map ptr $0900 + inca set module directory start to $0a00 + std <D.ModDir + std <D.ModEnd set module directory end to $0a00 + adda #$06 set secondary module directory start to $1000 + std <D.ModDir+2 + std <D.ModDAT set module directory DAT pointer to $1000 + std <D.CCMem set pointer to beginning of global memory to $1000 + endc * In following line, CRC=ON if it is STA <D.CRC, CRC=OFF if it is a STB <D.CRC - stb <D.CRC set CRC checking flag to off - + stb <D.CRC set CRC checking flag to off + * Initialize interrupt vector tables - leay <DisTable,pcr point to table of absolute vector addresses - ldx #D.Clock where to put it in memory - IFNE H6309 - ldf #DisSize size of the table - E=0 from TFM, above - tfm y+,x+ move it over - ELSE - ldb #DisSize -LoopCopy lda ,y+ - sta ,x+ - decb - bne LoopCopy - ENDC - + leay <DisTable,pcr point to table of absolute vector addresses + ldx #D.Clock where to put it in memory + ifne H6309 + ldf #DisSize size of the table - E=0 from TFM, above + tfm y+,x+ move it over + else + ldb #DisSize +l@ + lda ,y+ + sta ,x+ + decb + bne l@ + endc + * initialize D.Flip0 routine in low memory * Y=ptr to R.Flip0 already * leay >R.Flip0,pc - ldu #LowSub somewhere in block 0 that's never modified - stu <D.Flip0 switch to system task 0 - IFNE H6309 - ldf #SubSiz size of it - tfm y+,u+ copy it over - ELSE - ldb #SubSiz -Loop2 lda ,y+ - sta ,u+ - decb - bne Loop2 - ENDC - + ldu #LowSub somewhere in block 0 that's never modified + stu <D.Flip0 switch to system task 0 + ifne H6309 + ldf #SubSiz size of it + tfm y+,u+ copy it over + else + ldb #SubSiz +Loop2 lda ,y+ + sta ,u+ + decb + bne Loop2 + endc + * leau <Vectors,pc point to vector - tfr y,u move the pointer to a faster register -L0065 stu ,x++ Set all IRQ vectors to go to Vectors for now - cmpx #D.NMI - bls L0065 - + tfr y,u move the pointer to a faster register +L0065 stu ,x++ Set all IRQ vectors to go to Vectors for now + cmpx #D.NMI + bls L0065 + * Initialize user interupt vectors - ldx <D.XSWI2 Get SWI2 (os9 command) service routine pointer - stx <D.UsrSvc Save it as user service routine pointer - ldx <D.XIRQ Get IRQ service routine pointer - stx <D.UsrIRQ Save it as user IRQ routine pointer - - leax >SysCall,pc Setup System service routine entry vector - stx <D.SysSvc - stx <D.XSWI2 - - leax >S.SysIRQ,pc Setup system IRQ service vector - stx <D.SysIRQ - stx <D.XIRQ - - leax >S.SvcIRQ,pc Setup in system IRQ service vector - stx <D.SvcIRQ - leax >S.Poll,pc Setup interrupt polling vector - stx <D.Poll ORCC #$01;RTS - leax >S.AltIRQ,pc Setup alternate IRQ vector: pts to an RTS - stx <D.AltIRQ - - lda #'K --- in Kernel - jsr <D.BtBug --- - - leax >S.Flip1,pc Setup change to task 1 vector - stx <D.Flip1 - + ldx <D.XSWI2 Get SWI2 (os9 command) service routine pointer + stx <D.UsrSvc Save it as user service routine pointer + ldx <D.XIRQ Get IRQ service routine pointer + stx <D.UsrIRQ Save it as user IRQ routine pointer + + leax >SysCall,pc Setup System service routine entry vector + stx <D.SysSvc + stx <D.XSWI2 + + leax >S.SysIRQ,pc Setup system IRQ service vector + stx <D.SysIRQ + stx <D.XIRQ + + leax >S.SvcIRQ,pc Setup in system IRQ service vector + stx <D.SvcIRQ + leax >S.Poll,pc Setup interrupt polling vector + stx <D.Poll ORCC #$01;RTS + leax >S.AltIRQ,pc Setup alternate IRQ vector: pts to an RTS + stx <D.AltIRQ + + lda #'K --- in Kernel + jsr <D.BtBug --- + + leax >S.Flip1,pc Setup change to task 1 vector + stx <D.Flip1 + * Setup System calls - leay >SysCalls,pc - lbsr SysSvc - + leay >SysCalls,pc + lbsr SysSvc + * Initialize system process descriptor - ldu <D.PrcDBT get process table pointer - ldx <D.SysPrc get system process pointer - + ldu <D.PrcDBT get process table pointer + ldx <D.SysPrc get system process pointer + * These overlap because it is quicker than trying to strip hi byte from X - stx ,u save it as first process in table - stx 1,u save it as the second as well - IFNE H6309 - oim #$01,P$ID,x Set process ID to 1 (inited to 0) - oim #SysState,P$State,x Set to system state (inited to 0) - ELSE - ldd #$01*256+SysState - sta P$ID,x - stb P$State,x - ENDC - clra System task is task #0 - sta <D.SysTsk - sta P$Task,x - coma Setup its priority & age ($FF) - sta P$Prior,x - sta P$Age,x - leax <P$DATImg,x point to DAT image - stx <D.SysDAT save it as a pointer in DP + stx ,u save it as first process in table + stx 1,u save it as the second as well + ifne H6309 + oim #$01,P$ID,x Set process ID to 1 (inited to 0) + oim #SysState,P$State,x Set to system state (inited to 0) + else + ldd #$01*256+SysState + sta P$ID,x + stb P$State,x + endc + clra System task is task #0 + sta <D.SysTsk + sta P$Task,x + coma Setup its priority & age ($FF) + sta P$Prior,x + sta P$Age,x + leax <P$DATImg,x point to DAT image + stx <D.SysDAT save it as a pointer in DP * actually, since block 0 is tfm'd to be zero, we can skip the next 2 lines - IFNE H6309 - clrd - ELSE - clra - clrb - ENDC - std ,x++ initialize 1st block to 0 (for this DP) - + ifne H6309 + clrd + else + clra + clrb + endc + std ,x++ initialize 1st block to 0 (for this DP) + * Dat.BlCt-ROMCount-RAMCount - lda #$06 initialize the rest of the blocks to be free - ldu #DAT.Free -L00EF stu ,x++ - deca - bne L00EF - - ldu #$003F Block $3F is in use, at the top of system DAT image - stu ,x - - ldx <D.Tasks Point to task user table - inc ,x mark first 2 in use (system & GrfDrv) - inc 1,x - + lda #$06 initialize the rest of the blocks to be free + ldu #DAT.Free +L00EF stu ,x++ + deca + bne L00EF + + ldu #$003F Block $3F is in use, at the top of system DAT image + stu ,x + + ldx <D.Tasks Point to task user table + inc ,x mark first 2 in use (system & GrfDrv) + inc 1,x + * Setup system memory map - ldx <D.SysMem Get system memory map pointer - ldb <D.CCStk Get MSB of top of CC memory -L0104 inc ,x+ Mark it as used - decb Done? - bne L0104 No, go back till done - + ldx <D.SysMem Get system memory map pointer + ldb <D.CCStk Get MSB of top of CC memory +L0104 inc ,x+ Mark it as used + decb Done? + bne L0104 No, go back till done + * Calculate memory size - ldx <D.BlkMap get ptr to 8k block map - inc <$3F,x mark block $3F as used (kernel) - IFNE H6309 - ldq #$00080100 e=Marker, D=Block # to check -L0111 asld get next block # - stb >$FFA5 Map block into block 6 of my task - ste >-$6000,x save marker to that block - cmpe ,x did it ghost to block 0? - bne L0111 No, keep going till ghost is found - stb <D.MemSz Save # 8k mem blocks that exist - addr x,d add number of blocks to block map start - ELSE - ldd #$0008 -L0111 aslb - rola - stb >$FFA5 - pshs a - lda #$01 - sta >-$6000,x - cmpa ,x - puls a - bne L0111 - stb <D.MemSz - pshs x - addd ,s++ - ENDC - std <D.BlkMap+2 save block map end pointer - + ldx <D.BlkMap get ptr to 8k block map + inc <$3F,x mark block $3F as used (kernel) + ifne H6309 + ldq #$00080100 e=Marker, D=Block # to check +L0111 asld get next block # + stb >$FFA5 Map block into block 6 of my task + ste >-$6000,x save marker to that block + cmpe ,x did it ghost to block 0? + bne L0111 No, keep going till ghost is found + stb <D.MemSz Save # 8k mem blocks that exist + addr x,d add number of blocks to block map start + else + ldd #$0008 +L0111 aslb + rola + stb >$FFA5 + pshs a + lda #$01 + sta >-$6000,x + cmpa ,x + puls a + bne L0111 + stb <D.MemSz + pshs x + addd ,s++ + endc + std <D.BlkMap+2 save block map end pointer + * [D] at this point will contain 1 of the following: * $0210 - 128k * $0220 - 256k * $0240 - 512k * $0280 - 1024k * $0300 - 2048k - bitb #%00110000 block above 128K-256K? - beq L0170 yes, no need to mark block map - tstb 2 meg? - beq L0170 yes, skip this + bitb #%00110000 block above 128K-256K? + beq L0170 yes, no need to mark block map + tstb 2 meg? + beq L0170 yes, skip this * Mark blocks from 128k-256K to block $3F as NOT RAM - abx add maximum block number to block map start - leax -1,x Skip good blocks that are RAM - lda #NotRAM Not RAM flag - subb #$3F Calculate # blocks to mark as not RAM -L0127 sta ,x+ Mark them all - decb - bne L0127 - -L0170 ldx #Bt.Start start address of the boot track in memory - lda #18 size of the boot track: B=$00 from L0127 loop, above - lbsr I.VBlock go verify it - - bsr L01D2 go mark system map - + abx add maximum block number to block map start + leax -1,x Skip good blocks that are RAM + lda #NotRAM Not RAM flag + subb #$3F Calculate # blocks to mark as not RAM +L0127 sta ,x+ Mark them all + decb + bne L0127 + +L0170 ldx #Bt.Start start address of the boot track in memory + lda #18 size of the boot track: B=$00 from L0127 loop, above + lbsr I.VBlock go verify it + + bsr L01D2 go mark system map + * See if init module is in memory already -L01B0 leax <init,pc point to 'Init' module name - bsr link try & link it - bcc L01BF no error, go on -L01B8 os9 F$Boot error linking init, try & load boot file - bcc L01B0 got it, try init again - bra L01CE error, re-booting do D.Crash +L01B0 leax <init,pc point to 'Init' module name + bsr link try & link it + bcc L01BF no error, go on +L01B8 os9 F$Boot error linking init, try & load boot file + bcc L01B0 got it, try init again + bra L01CE error, re-booting do D.Crash * Save pointer to init module and execute krnp2 -L01BF stu <D.Init Save init module pointer - lda Feature1,u Get feature byte #1 from init module - bita #CRCOn CRC feature on? - beq ShowI if not, continue - inc <D.CRC else inc. CRC flag -ShowI lda #'i found init module - jsr <D.BtBug - -L01C1 leax <krnp2,pc Point to it's name - bsr link Try to link it - bcc L01D0 It worked, execute it - os9 F$Boot It doesn't exist try re-booting - bcc L01C1 No error's, let's try to link it again -L01CE jmp <D.Crash obviously can't do it, crash machine -L01D0 jmp ,y execute krnp2 - +L01BF stu <D.Init Save init module pointer + lda Feature1,u Get feature byte #1 from init module + bita #CRCOn CRC feature on? + beq ShowI if not, continue + inc <D.CRC else inc. CRC flag +ShowI lda #'i found init module + jsr <D.BtBug + +L01C1 leax <krnp2,pc Point to it's name + bsr link Try to link it + bcc L01D0 It worked, execute it + os9 F$Boot It doesn't exist try re-booting + bcc L01C1 No error's, let's try to link it again +L01CE jmp <D.Crash obviously can't do it, crash machine +L01D0 jmp ,y execute krnp2 + * Mark kernel in system memory map as used memory (256 byte blocks) -L01D2 ldx <D.SysMem Get system mem ptr - ldd #NotRAM*256+(Bt.Start/256) B = MSB of start of the boot - abx point to Bt.Start - start of boot track - comb we have $FF-$ED pages to mark as used - sta b,x Mark I/O as not RAM -L01DF lda #RAMinUse get in use flag -L01E1 sta ,x+ save it - decb done? - bne L01E1 no, keep going - ldx <D.BlkMap get pointer to start of block map - sta <$3f,x mark kernel block as RAMinUse, instead of ModInBlk -S.AltIRQ rts return - +L01D2 ldx <D.SysMem Get system mem ptr + ldd #NotRAM*256+(Bt.Start/256) B = MSB of start of the boot + abx point to Bt.Start - start of boot track + comb we have $FF-$ED pages to mark as used + sta b,x Mark I/O as not RAM +L01DF lda #RAMinUse get in use flag +L01E1 sta ,x+ save it + decb done? + bne L01E1 no, keep going + ldx <D.BlkMap get pointer to start of block map + sta <$3f,x mark kernel block as RAMinUse, instead of ModInBlk +S.AltIRQ rts return + * Link module pointed to by X -link lda #Systm Attempt to link system module - os9 F$Link - rts - -init fcs 'Init' -krnp2 fcs 'krnp2' - +link lda #Systm Attempt to link system module + os9 F$Link + rts + +init fcs 'Init' +krnp2 fcs 'krnp2' + * Service vector call pointers -SysCalls fcb F$Link - fdb FLink-*-2 - fcb F$PrsNam - fdb FPrsNam-*-2 - fcb F$CmpNam - fdb FCmpNam-*-2 - fcb F$CmpNam+SysState - fdb FSCmpNam-*-2 - fcb F$CRC - fdb FCRC-*-2 - fcb F$SRqMem+SysState - fdb FSRqMem-*-2 - fcb F$SRtMem+SysState - fdb FSRtMem-*-2 - fcb F$AProc+SysState - fdb FAProc-*-2 - fcb F$NProc+SysState - fdb FNProc-*-2 - fcb F$VModul+SysState - fdb FVModul-*-2 - fcb F$SSvc+SysState - fdb FSSvc-*-2 - fcb F$SLink+SysState - fdb FSLink-*-2 - fcb F$Boot+SysState - fdb FBoot-*-2 - fcb F$BtMem+SysState - fdb FSRqMem-*-2 - IFNE H6309 - fcb F$CpyMem - fdb FCpyMem-*-2 - ENDC - fcb F$Move+SysState - fdb FMove-*-2 - fcb F$AllImg+SysState - fdb FAllImg-*-2 - fcb F$SetImg+SysState - fdb FFreeLB-*-2 - fcb F$FreeLB+SysState - fdb FSFreeLB-*-2 - fcb F$FreeHB+SysState - fdb FFreeHB-*-2 - fcb F$AllTsk+SysState - fdb FAllTsk-*-2 - fcb F$DelTsk+SysState - fdb FDelTsk-*-2 - fcb F$SetTsk+SysState - fdb FSetTsk-*-2 - fcb F$ResTsk+SysState - fdb FResTsk-*-2 - fcb F$RelTsk+SysState - fdb FRelTsk-*-2 - fcb F$DATLog+SysState - fdb FDATLog-*-2 - fcb F$LDAXY+SysState - fdb FLDAXY-*-2 - fcb F$LDDDXY+SysState - fdb FLDDDXY-*-2 - fcb F$LDABX+SysState - fdb FLDABX-*-2 - fcb F$STABX+SysState - fdb FSTABX-*-2 - fcb F$ELink+SysState - fdb FELink-*-2 - fcb F$FModul+SysState - fdb FFModul-*-2 - fcb F$VBlock+SysState - fdb FVBlock-*-2 - IFNE H6309 - fcb F$DelRAM - fdb FDelRAM-*-2 - ENDC - fcb $80 - +SysCalls fcb F$Link + fdb FLink-*-2 + fcb F$PrsNam + fdb FPrsNam-*-2 + fcb F$CmpNam + fdb FCmpNam-*-2 + fcb F$CmpNam+SysState + fdb FSCmpNam-*-2 + fcb F$CRC + fdb FCRC-*-2 + fcb F$SRqMem+SysState + fdb FSRqMem-*-2 + fcb F$SRtMem+SysState + fdb FSRtMem-*-2 + fcb F$AProc+SysState + fdb FAProc-*-2 + fcb F$NProc+SysState + fdb FNProc-*-2 + fcb F$VModul+SysState + fdb FVModul-*-2 + fcb F$SSvc+SysState + fdb FSSvc-*-2 + fcb F$SLink+SysState + fdb FSLink-*-2 + fcb F$Boot+SysState + fdb FBoot-*-2 + fcb F$BtMem+SysState + fdb FSRqMem-*-2 + ifne H6309 + fcb F$CpyMem + fdb FCpyMem-*-2 + endc + fcb F$Move+SysState + fdb FMove-*-2 + fcb F$AllImg+SysState + fdb FAllImg-*-2 + fcb F$SetImg+SysState + fdb FFreeLB-*-2 + fcb F$FreeLB+SysState + fdb FSFreeLB-*-2 + fcb F$FreeHB+SysState + fdb FFreeHB-*-2 + fcb F$AllTsk+SysState + fdb FAllTsk-*-2 + fcb F$DelTsk+SysState + fdb FDelTsk-*-2 + fcb F$SetTsk+SysState + fdb FSetTsk-*-2 + fcb F$ResTsk+SysState + fdb FResTsk-*-2 + fcb F$RelTsk+SysState + fdb FRelTsk-*-2 + fcb F$DATLog+SysState + fdb FDATLog-*-2 + fcb F$LDAXY+SysState + fdb FLDAXY-*-2 + fcb F$LDDDXY+SysState + fdb FLDDDXY-*-2 + fcb F$LDABX+SysState + fdb FLDABX-*-2 + fcb F$STABX+SysState + fdb FSTABX-*-2 + fcb F$ELink+SysState + fdb FELink-*-2 + fcb F$FModul+SysState + fdb FFModul-*-2 + fcb F$VBlock+SysState + fdb FVBlock-*-2 + ifne H6309 + fcb F$DelRAM + fdb FDelRAM-*-2 + endc + fcb $80 + * SWI3 vector entry -XSWI3 lda #P$SWI3 point to SWI3 vector - fcb $8C skip 2 bytes - +XSWI3 lda #P$SWI3 point to SWI3 vector + fcb $8C skip 2 bytes + * SWI vector entry -XSWI lda #P$SWI point to SWI vector - ldx <D.Proc get process pointer - ldu a,x user defined SWI[x]? - beq L028E no, go get option byte -GoUser lbra L0E5E Yes, go call users's routine - +XSWI lda #P$SWI point to SWI vector + ldx <D.Proc get process pointer + ldu a,x user defined SWI[x]? + beq L028E no, go get option byte +GoUser lbra L0E5E Yes, go call users's routine + * SWI2 vector entry -XSWI2 ldx <D.Proc get current process descriptor - ldu P$SWI2,x any SWI vector? - bne GoUser yes, go execute it - +XSWI2 ldx <D.Proc get current process descriptor + ldu P$SWI2,x any SWI vector? + bne GoUser yes, go execute it + * Process software interupts from a user state * Entry: X=Process descriptor pointer of process that made system call * U=Register stack pointer -L028E ldu <D.SysSvc set system call processor to system side - stu <D.XSWI2 - ldu <D.SysIRQ do the same thing for IRQ's - stu <D.XIRQ - IFNE H6309 - oim #SysState,P$State,x mark process as in system state - ELSE - lda P$State,x - ora #SysState - sta P$State,x - ENDC +L028E ldu <D.SysSvc set system call processor to system side + stu <D.XSWI2 + ldu <D.SysIRQ do the same thing for IRQ's + stu <D.XIRQ + ifne H6309 + oim #SysState,P$State,x mark process as in system state + else + lda P$State,x + ora #SysState + sta P$State,x + endc * copy register stack to process descriptor - sts P$SP,x save stack pointer - leas (P$Stack-R$Size),x point S to register stack destination - - IFNE H6309 - leau R$Size-1,s point to last byte of destination register stack - leay -1,y point to caller's register stack in $FEE1 - ldw #R$Size size of the register stack - tfm y-,u- - leau ,s needed because the TFM is u-, not -u (post, not pre) - ELSE + sts P$SP,x save stack pointer + leas (P$Stack-R$Size),x point S to register stack destination + + ifne H6309 + leau R$Size-1,s point to last byte of destination register stack + leay -1,y point to caller's register stack in $FEE1 + ldw #R$Size size of the register stack + tfm y-,u- + leau ,s needed because the TFM is u-, not -u (post, not pre) + else * Note! R$Size MUST BE an EVEN number of bytes for this to work! - leau R$Size,s point to last byte of destination register stack - lda #R$Size/2 -Loop3 ldx ,--y - stx ,--u - deca - bne Loop3 - ENDC - andcc #^IntMasks + leau R$Size,s point to last byte of destination register stack + lda #R$Size/2 +Loop3 ldx ,--y + stx ,--u + deca + bne Loop3 + endc + andcc #^IntMasks * B=function code already from calling process: DON'T USE IT! - ldx R$PC,u get where PC was from process - leax 1,x move PC past option - stx R$PC,u save updated PC to process + ldx R$PC,u get where PC was from process + leax 1,x move PC past option + stx R$PC,u save updated PC to process * execute function call - ldy <D.UsrDis get user dispatch table pointer - lbsr L033B go execute option - IFNE H6309 - aim #^IntMasks,R$CC,u Clear interrupt flags in caller's CC - ELSE - lda R$CC,u - anda #^IntMasks - sta R$CC,u - ENDC - ldx <D.Proc get current process ptr - IFNE H6309 - aim #^(SysState+TimOut),P$State,x Clear system & timeout flags - ELSE - lda P$State,x - anda #^(SysState+TimOut) - sta P$State,x - ENDC - + ldy <D.UsrDis get user dispatch table pointer + lbsr L033B go execute option + ifne H6309 + aim #^IntMasks,R$CC,u Clear interrupt flags in caller's CC + else + lda R$CC,u + anda #^IntMasks + sta R$CC,u + endc + ldx <D.Proc get current process ptr + ifne H6309 + aim #^(SysState+TimOut),P$State,x Clear system & timeout flags + else + lda P$State,x + anda #^(SysState+TimOut) + sta P$State,x + endc + * Check for image change now, which lets stuff like F$MapBlk and F$ClrBlk * do the short-circuit thing, too. Adds about 20 cycles to each system call. - lbsr TstImg it doesn't hurt to call this twice - lda P$State,x get current state of the process - ora <P$Signal,x is there a pending signal? - sta <D.Quick save quick return flag - beq AllClr if nothing's have changed, do full checks - -DoFull bsr L02DA move the stack frame back to user state - lbra L0D80 go back to the process - + lbsr TstImg it doesn't hurt to call this twice + lda P$State,x get current state of the process + ora <P$Signal,x is there a pending signal? + sta <D.Quick save quick return flag + beq AllClr if nothing's have changed, do full checks + +DoFull bsr L02DA move the stack frame back to user state + lbra L0D80 go back to the process + * add ldu P$SP,x, etc... -AllClr equ * - IFNE H6309 - inc <D.QCnt - aim #$1F,<D.QCnt - beq DoFull every 32 system calls, do the full check - ldw #R$Size --- size of the register stack - ldy #Where+SWIStack --- to stack at top of memory - orcc #IntMasks - tfm u+,y+ --- move the stack to the top of memory - ELSE - lda <D.QCnt - inca - anda #$1F - sta <D.QCnt - beq DoFull - ldb #R$Size - ldy #Where+SWIStack - orcc #IntMasks -Loop4 lda ,u+ - sta ,y+ - decb - bne Loop4 - ENDC - lbra BackTo1 otherwise simply return to the user - +AllClr equ * + ifne H6309 + inc <D.QCnt + aim #$1F,<D.QCnt + beq DoFull every 32 system calls, do the full check + ldw #R$Size --- size of the register stack + ldy #Where+SWIStack --- to stack at top of memory + orcc #IntMasks + tfm u+,y+ --- move the stack to the top of memory + else + lda <D.QCnt + inca + anda #$1F + sta <D.QCnt + beq DoFull + ldb #R$Size + ldy #Where+SWIStack + orcc #IntMasks +Loop4 lda ,u+ + sta ,y+ + decb + bne Loop4 + endc + lbra BackTo1 otherwise simply return to the user + * Copy register stack from user to system * Entry: U=Ptr to Register stack in process dsc -L02CB pshs cc,x,y,u preserve registers - ldb P$Task,x get task # - ldx P$SP,x get stack pointer - lbsr L0BF3 calculate block offset (only affects A&X) - leax -$6000,x adjust pointer to where memory map will be - bra L02E9 go copy it - +L02CB pshs cc,x,y,u preserve registers + ldb P$Task,x get task # + ldx P$SP,x get stack pointer + lbsr L0BF3 calculate block offset (only affects A&X) + leax -$6000,x adjust pointer to where memory map will be + bra L02E9 go copy it + * Copy register stack from system to user * Entry: U=Ptr to Register stack in process dsc -L02DA pshs cc,x,y,u preserve registers - ldb P$Task,x get task # of destination - ldx P$SP,x get stack pointer - lbsr L0BF3 calculate block offset (only affects A&X) - leax -$6000,x adjust pointer to where memory map will be - exg x,y swap pointers & copy +L02DA pshs cc,x,y,u preserve registers + ldb P$Task,x get task # of destination + ldx P$SP,x get stack pointer + lbsr L0BF3 calculate block offset (only affects A&X) + leax -$6000,x adjust pointer to where memory map will be + exg x,y swap pointers & copy * Copy a register stack * Entry: X=Source * Y=Destination * A=Offset into DAT image of stack * B=Task # -L02E9 leau a,u point to block # of where stack is - lda 1,u get first block - ldb 3,u get a second just in case of overlap - orcc #IntMasks shutdown interupts while we do this - std >$FFA5 map blocks in - IFNE H6309 - ldw #R$Size get size of register stack - tfm x+,y+ copy it - ELSE - ldb #R$Size -Loop5 lda ,x+ - sta ,y+ - decb - bne Loop5 - ENDC - ldx <D.SysDAT remap the blocks we took out - lda $0B,x - ldb $0D,x - std >$FFA5 - puls cc,x,y,u,pc restore & return - +L02E9 leau a,u point to block # of where stack is + lda 1,u get first block + ldb 3,u get a second just in case of overlap + orcc #IntMasks shutdown interupts while we do this + std >$FFA5 map blocks in + ifne H6309 + ldw #R$Size get size of register stack + tfm x+,y+ copy it + else + ldb #R$Size +Loop5 lda ,x+ + sta ,y+ + decb + bne Loop5 + endc + ldx <D.SysDAT remap the blocks we took out + lda $0B,x + ldb $0D,x + std >$FFA5 + puls cc,x,y,u,pc restore & return + * Process software interupts from system state * Entry: U=Register stack pointer -SysCall leau ,s get pointer to register stack - lda <D.SSTskN Get system task # (0=SYSTEM, 1=GRFDRV) - clr <D.SSTskN Force to System Process - pshs a Save the system task number - lda ,u Restore callers CC register (R$CC=$00) - tfr a,cc make it current - ldx R$PC,u Get my caller's PC register - leax 1,x move PC to next position - stx R$PC,u Save my caller's updated PC register - ldy <D.SysDis get system dispatch table pointer - bsr L033B execute system call - puls a restore system state task number - lbra L0E2B return to process - +SysCall leau ,s get pointer to register stack + lda <D.SSTskN Get system task # (0=SYSTEM, 1=GRFDRV) + clr <D.SSTskN Force to System Process + pshs a Save the system task number + lda ,u Restore callers CC register (R$CC=$00) + tfr a,cc make it current + ldx R$PC,u Get my caller's PC register + leax 1,x move PC to next position + stx R$PC,u Save my caller's updated PC register + ldy <D.SysDis get system dispatch table pointer + bsr L033B execute system call + puls a restore system state task number + lbra L0E2B return to process + * Entry: X = system call vector to jump to -Sys.Vec jmp ,x execute service call - +Sys.Vec jmp ,x execute service call + * Execute system call * Entry: B=Function call # * Y=Function dispatch table pointer (D.SysDis or D.UsrDis) -L033B - lslb is it a I/O call? (Also multiplys by 2 for offset) - bcc L0345 no, go get normal vector +L033B + lslb is it a I/O call? (Also multiplys by 2 for offset) + bcc L0345 no, go get normal vector * Execute I/O system calls - ldx IOEntry,y get IOMan vector + ldx IOEntry,y get IOMan vector * Execute the system call -L034F pshs u preserve register stack pointer - jsr [D.SysVec] perform a vectored system call - puls u restore pointer -L0355 tfr cc,a move CC to A for stack update - bcc L035B go update it if no error from call - stb R$B,u save error code to caller's B -L035B ldb R$CC,u get callers CC, R$CC=$00 - IFNE H6309 - andd #$2FD0 [A]=H,N,Z,V,C [B]=E,F,I - orr b,a merge them together - ELSE - anda #$2F [A]=H,N,Z,V,C - andb #$D0 [B]=E,F,I - pshs b - ora ,s+ - ENDC - sta R$CC,u return it to caller, R$CC=$00 - rts - +L034F pshs u preserve register stack pointer + jsr [D.SysVec] perform a vectored system call + puls u restore pointer +L0355 tfr cc,a move CC to A for stack update + bcc L035B go update it if no error from call + stb R$B,u save error code to caller's B +L035B ldb R$CC,u get callers CC, R$CC=$00 + ifne H6309 + andd #$2FD0 [A]=H,N,Z,V,C [B]=E,F,I + orr b,a merge them together + else + anda #$2F [A]=H,N,Z,V,C + andb #$D0 [B]=E,F,I + pshs b + ora ,s+ + endc + sta R$CC,u return it to caller, R$CC=$00 + rts + * Execute regular system calls -L0345 - clra clear MSB of offset - ldx d,y get vector to call - bne L034F it's initialized, go execute it - comb set carry for error - ldb #E$UnkSvc get error code - bra L0355 return with it - - use freboot.asm - - use fssvc.asm - - use flink.asm - - use fvmodul.asm - - use ffmodul.asm - - use fprsnam.asm - - use fcmpnam.asm - - use fsrqmem.asm - +L0345 + clra clear MSB of offset + ldx d,y get vector to call + bne L034F it's initialized, go execute it + comb set carry for error + ldb #E$UnkSvc get error code + bra L0355 return with it + + use freboot.asm + + use fssvc.asm + + use flink.asm + + use fvmodul.asm + + use ffmodul.asm + + use fprsnam.asm + + use fcmpnam.asm + + use fsrqmem.asm + * use fallram.asm - - - IFNE H6309 - use fdelram.asm - ENDC - - use fallimg.asm - - use ffreehb.asm - - use fdatlog.asm - - use fld.asm - - IFNE H6309 - use fcpymem.asm - ENDC - - use fmove.asm - - use fldabx.asm - - use falltsk.asm - - use faproc.asm - + + + ifne H6309 + use fdelram.asm + endc + + use fallimg.asm + + use ffreehb.asm + + use fdatlog.asm + + use fld.asm + + ifne H6309 + use fcpymem.asm + endc + + use fmove.asm + + use fldabx.asm + + use falltsk.asm + + use faproc.asm + * System IRQ service routine -XIRQ ldx <D.Proc get current process pointer - sts P$SP,x save the stack pointer - lds <D.SysStk get system stack pointer - ldd <D.SysSvc set system service routine to current - std <D.XSWI2 - ldd <D.SysIRQ set system IRQ routine to current - std <D.XIRQ - jsr [>D.SvcIRQ] execute irq service - bcc L0D5B - - ldx <D.Proc get current process pointer - ldb P$Task,x - ldx P$SP,x get it's stack pointer - - pshs u,d,cc save some registers - leau ,s point to a 'caller register stack' - lbsr L0C40 do a LDB 0,X in task B - puls u,d,cc and now A ( R$A,U ) = the CC we want - - ora #IntMasks disable it's IRQ's - lbsr L0C28 save it back -L0D5B orcc #IntMasks shut down IRQ's - ldx <D.Proc get current process pointer - tst <D.QIRQ was it a clock IRQ? - lbne L0DF7 if not, do a quick return - - lda P$State,x Get it's state - bita #TimOut Is it timed out? - bne L0D7C yes, wake it up +XIRQ ldx <D.Proc get current process pointer + sts P$SP,x save the stack pointer + lds <D.SysStk get system stack pointer + ldd <D.SysSvc set system service routine to current + std <D.XSWI2 + ldd <D.SysIRQ set system IRQ routine to current + std <D.XIRQ + jsr [>D.SvcIRQ] execute irq service + bcc L0D5B + + ldx <D.Proc get current process pointer + ldb P$Task,x + ldx P$SP,x get it's stack pointer + + pshs u,d,cc save some registers + leau ,s point to a 'caller register stack' + lbsr L0C40 do a LDB 0,X in task B + puls u,d,cc and now A ( R$A,U ) = the CC we want + + ora #IntMasks disable it's IRQ's + lbsr L0C28 save it back +L0D5B orcc #IntMasks shut down IRQ's + ldx <D.Proc get current process pointer + tst <D.QIRQ was it a clock IRQ? + lbne L0DF7 if not, do a quick return + + lda P$State,x Get it's state + bita #TimOut Is it timed out? + bne L0D7C yes, wake it up * Update active process queue - ldu #(D.AProcQ-P$Queue) point to active process queue - ldb #Suspend get suspend flag -L0D6A ldu P$Queue,u get a active process pointer - beq L0D78 - bitb P$State,u is it suspended? - bne L0D6A yes, go to next one in chain - ldb P$Prior,x get current process priority - cmpb P$Prior,u do we bump this one? - blo L0D7C - -L0D78 ldu P$SP,x - bra L0DB9 - -L0D7C anda #^TimOut - sta P$State,x - -L0D80 equ * -L0D83 bsr L0D11 activate next process - - use fnproc.asm - + ldu #(D.AProcQ-P$Queue) point to active process queue + ldb #Suspend get suspend flag +L0D6A ldu P$Queue,u get a active process pointer + beq L0D78 + bitb P$State,u is it suspended? + bne L0D6A yes, go to next one in chain + ldb P$Prior,x get current process priority + cmpb P$Prior,u do we bump this one? + blo L0D7C + +L0D78 ldu P$SP,x + bra L0DB9 + +L0D7C anda #^TimOut + sta P$State,x + +L0D80 equ * +L0D83 bsr L0D11 activate next process + + use fnproc.asm + * The following routines must appear no earlier than $E00 when assembled, as * they have to always be in the vector RAM page ($FE00-$FEFF) - + * Default routine for D.SysIRQ -S.SysIRQ lda <D.SSTskN Get current task's GIME task # (0 or 1) - beq FastIRQ Use super-fast version for system state - clr <D.SSTskN Clear out memory copy (task 0) - jsr [>D.SvcIRQ] (Normally routine in Clock calling D.Poll) - inc <D.SSTskN Save task # for system state - lda #1 Task 1 - ora <D.TINIT Merge task bit's into Shadow version - sta <D.TINIT Update shadow - sta >DAT.Task Save to GIME as well & return - bra DoneIRQ Check for error and exit - -FastIRQ jsr [>D.SvcIRQ] (Normally routine in Clock calling D.Poll) -DoneIRQ bcc L0E28 No error on IRQ, exit - IFNE H6309 - oim #IntMasks,0,s Setup RTI to shut interrupts off again - ELSE - lda ,s - ora #IntMasks - sta ,s - ENDC -L0E28 rti - +S.SysIRQ lda <D.SSTskN Get current task's GIME task # (0 or 1) + beq FastIRQ Use super-fast version for system state + clr <D.SSTskN Clear out memory copy (task 0) + jsr [>D.SvcIRQ] (Normally routine in Clock calling D.Poll) + inc <D.SSTskN Save task # for system state + lda #1 Task 1 + ora <D.TINIT Merge task bit's into Shadow version + sta <D.TINIT Update shadow + sta >DAT.Task Save to GIME as well & return + bra DoneIRQ Check for error and exit + +FastIRQ jsr [>D.SvcIRQ] (Normally routine in Clock calling D.Poll) +DoneIRQ bcc L0E28 No error on IRQ, exit + ifne H6309 + oim #IntMasks,0,s Setup RTI to shut interrupts off again + else + lda ,s + ora #IntMasks + sta ,s + endc +L0E28 rti + * return from a system call -L0E29 clra Force System task # to 0 (non-GRDRV) -L0E2B ldx <D.SysPrc Get system process dsc. ptr - lbsr TstImg check image, and F$SetTsk (PRESERVES A) - orcc #IntMasks Shut interrupts off - sta <D.SSTskN Save task # for system state - beq Fst2 If task 0, skip subroutine - ora <D.TINIT Merge task bit's into Shadow version - sta <D.TINIT Update shadow - sta >DAT.Task Save to GIME as well & return -Fst2 leas ,u Stack ptr=U & return - rti - +L0E29 clra Force System task # to 0 (non-GRDRV) +L0E2B ldx <D.SysPrc Get system process dsc. ptr + lbsr TstImg check image, and F$SetTsk (PRESERVES A) + orcc #IntMasks Shut interrupts off + sta <D.SSTskN Save task # for system state + beq Fst2 If task 0, skip subroutine + ora <D.TINIT Merge task bit's into Shadow version + sta <D.TINIT Update shadow + sta >DAT.Task Save to GIME as well & return +Fst2 leas ,u Stack ptr=U & return + rti + * Switch to new process, X=Process descriptor pointer, U=Stack pointer -L0E4C equ * - IFNE H6309 - oim #$01,<D.TINIT switch GIME shadow to user state - lda <D.TINIT - ELSE - lda <D.TINIT - ora #$01 - sta <D.TINIT - ENDC - sta >DAT.Task save it to GIME - leas ,y point to new stack - tstb is the stack at SWISTACK? - bne MyRTI no, we're doing a system-state rti - - IFNE H6309 - ldf #R$Size E=0 from call to L0E8D before - ldu #Where+SWIStack point to the stack - tfm u+,y+ move the stack from top of memory to user memory - ELSE - ldb #R$Size - ldu #Where+SWIStack point to the stack -RtiLoop lda ,u+ - sta ,y+ - decb - bne RtiLoop - ENDC -MyRTI rti return from IRQ - - +L0E4C equ * + ifne H6309 + oim #$01,<D.TINIT switch GIME shadow to user state + lda <D.TINIT + else + lda <D.TINIT + ora #$01 + sta <D.TINIT + endc + sta >DAT.Task save it to GIME + leas ,y point to new stack + tstb is the stack at SWISTACK? + bne MyRTI no, we're doing a system-state rti + + ifne H6309 + ldf #R$Size E=0 from call to L0E8D before + ldu #Where+SWIStack point to the stack + tfm u+,y+ move the stack from top of memory to user memory + else + ldb #R$Size + ldu #Where+SWIStack point to the stack +RtiLoop lda ,u+ + sta ,y+ + decb + bne RtiLoop + endc +MyRTI rti return from IRQ + + * Execute routine in task 1 pointed to by U * comes from user requested SWI vectors -L0E5E equ * - IFNE H6309 - oim #$01,<D.TINIT switch GIME shadow to user state - ldb <D.TINIT - ELSE - ldb <D.TINIT - orb #$01 - stb <D.TINIT - ENDC - stb >DAT.Task - jmp ,u - +L0E5E equ * + ifne H6309 + oim #$01,<D.TINIT switch GIME shadow to user state + ldb <D.TINIT + else + ldb <D.TINIT + orb #$01 + stb <D.TINIT + endc + stb >DAT.Task + jmp ,u + * Flip to task 1 (used by GRF/WINDInt to switch to GRFDRV) (pointed to * by <D.Flip1). All regs are already preserved on stack for the RTI -S.Flip1 ldb #2 get Task image entry numberx2 for Grfdrv (task 1) - bsr L0E8D copy over the DAT image - IFNE H6309 - oim #$01,<D.TINIT - lda <D.TINIT get copy of GIME Task side - ELSE - lda <D.TINIT - ora #$01 - sta <D.TINIT - ENDC - sta >DAT.Task save it to GIME register - inc <D.SSTskN increment system state task number - rti return - +S.Flip1 ldb #2 get Task image entry numberx2 for Grfdrv (task 1) + bsr L0E8D copy over the DAT image + ifne H6309 + oim #$01,<D.TINIT + lda <D.TINIT get copy of GIME Task side + else + lda <D.TINIT + ora #$01 + sta <D.TINIT + endc + sta >DAT.Task save it to GIME register + inc <D.SSTskN increment system state task number + rti return + * Setup MMU in task 1, B=Task # to swap to, shifted left 1 bit -L0E8D cmpb <D.Task1N are we going back to the same task - beq L0EA3 without the DAT image changing? - stb <D.Task1N nope, save current task in map type 1 - ldx #$FFA8 get MMU start register for process's - ldu <D.TskIPt get task image pointer table - ldu b,u get address of DAT image -L0E93 leau 1,u point to actual MMU block - IFNE H6309 - lde #4 get # banks/2 for task - ELSE - lda #4 - pshs a - ENDC -L0E9B lda ,u++ get a bank - ldb ,u++ and next one - std ,x++ Save it to MMU - IFNE H6309 - dece done? - ELSE - dec ,s - ENDC - bne L0E9B no, keep going - IFEQ H6309 - leas 1,s - ENDC -L0EA3 rts return - -* Execute SWI3 vector -* Execute FIRQ vector -FIRQVCT ldx #D.FIRQ get DP offset of vector - bra L0EB8 go execute it +L0E8D cmpb <D.Task1N are we going back to the same task + beq L0EA3 without the DAT image changing? + stb <D.Task1N nope, save current task in map type 1 + ldx #$FFA8 get MMU start register for process's + ldu <D.TskIPt get task image pointer table + ldu b,u get address of DAT image +L0E93 leau 1,u point to actual MMU block + ifne H6309 + lde #4 get # banks/2 for task + else + lda #4 + pshs a + endc +L0E9B lda ,u++ get a bank + ldb ,u++ and next one + std ,x++ Save it to MMU + ifne H6309 + dece done? + else + dec ,s + endc + bne L0E9B no, keep going + ifeq H6309 + leas 1,s + endc +L0EA3 rts return + +* Execute FIRQ vector (called from $FEF4) +FIRQVCT ldx #D.FIRQ get DP offset of vector + bra L0EB8 go execute it + +* Execute IRQ vector (called from $FEF7) +IRQVCT orcc #IntMasks disasble IRQ's + ldx #D.IRQ get DP offset of vector -* Execute IRQ vector -IRQVCT orcc #IntMasks disasble IRQ's - ldx #D.IRQ get DP offset of vector * Execute interrupt vector, B=DP Vector offset -L0EB8 clra (faster than CLR >$xxxx) - sta >DAT.Task Force to Task 0 (system state) - IFNE H6309 - tfr 0,dp setup DP - ELSE - tfr a,dp - ENDC -MapGrf equ * - IFNE H6309 - aim #$FE,<D.TINIT switch GIME shadow to system state - lda <D.TINIT set GIME again just in case timer is used - ELSE - lda <D.TINIT - anda #$FE - sta <D.TINIT - ENDC -MapT0 sta >DAT.Task - jmp [,x] execute it - -SWI3VCT orcc #IntMasks disable IRQ's - ldx #D.SWI3 get DP offset of vector - bra SWICall go execute it - -* Execute SWI2 vector -SWI2VCT orcc #IntMasks disasble IRQ's - ldx #D.SWI2 get DP offset of vector - +L0EB8 clra (faster than CLR >$xxxx) + sta >DAT.Task Force to Task 0 (system state) + ifne H6309 + tfr 0,dp setup DP + else + tfr a,dp + endc +MapGrf equ * + ifne H6309 + aim #$FE,<D.TINIT switch GIME shadow to system state + lda <D.TINIT set GIME again just in case timer is used + else + lda <D.TINIT + anda #$FE + sta <D.TINIT + endc +MapT0 sta >DAT.Task + jmp [,x] execute it + +* Execute SWI3 vector (called from $FEEE) +SWI3VCT orcc #IntMasks disable IRQ's + ldx #D.SWI3 get DP offset of vector + bra SWICall go execute it + +* Execute SWI2 vector (called from $FEF1) +SWI2VCT orcc #IntMasks disasble IRQ's + ldx #D.SWI2 get DP offset of vector + * saves 1 cycle on system-system calls * saves about 200 cycles (calls to I.LDABX and L029E) on grfdrv-system, * or user-system calls. -SWICall ldb [R$PC,s] --- get callcode of the system call +SWICall ldb [R$PC,s] --- get callcode of the system call * NOTE: Alan DeKok claims that this is BAD. It crashed Colin McKay's * CoCo 3. Instead, we should do a clra/sta >DAT.Task. * clr >DAT.Task go to map type 1 - clra + clra sta >DAT.Task - IFNE H6309 - tfr 0,dp set DP to zero - ELSE + ifne H6309 + tfr 0,dp set DP to zero + else * 6809 version: we don't need to clra anymore since we're doing it above now * clra - tfr a,dp - ENDC - + tfr a,dp + endc + * These lines add a total of 81 addition cycles to each SWI(2,3) call, * and 36 bytes+12 for R$Size in the constant page at $FExx * It takes no more time for a SWI(2,3) from system state than previously, @@ -992,69 +995,75 @@ * For processes that re-vector SWI, SWI3, it adds 81 cycles. BUT SWI(3) * CANNOT be vectored to L0EBF cause the user SWI service routine has been * changed - lda <D.TINIT get map type flag - bita #$01 check it without changing it - + lda <D.TINIT get map type flag + bita #$01 check it without changing it + * Change to LBEQ R.SysSvc to avoid JMP [,X] * and add R.SysSvc STA >DAT.Task ??? - beq MapT0 in map 0: restore hardware and do system service - tst <D.SSTskN get system state 0,1 - bne MapGrf if in grfdrv, go to map 0 and do system service - + beq MapT0 in map 0: restore hardware and do system service + tst <D.SSTskN get system state 0,1 + bne MapGrf if in grfdrv, go to map 0 and do system service + * the preceding few lines are necessary, as all SWI's still pass thru * here before being vectored to the system service routine... which * doesn't copy the stack from user state. - sta >DAT.Task go to map type X again to get user's stack + sta >DAT.Task go to map type X again to get user's stack * a byte less, a cycle more than ldy #$FEED-R$Size, or ldy #$F000+SWIStack - leay <SWIStack,pc where to put the register stack: to $FEDF - tfr s,u get a copy of where the stack is - IFNE H6309 - ldw #R$Size get the size of the stack - tfm u+,y+ move the stack to the top of memory - ELSE - pshs b - ldb #R$Size -Looper lda ,u+ - sta ,y+ - decb - bne Looper - puls b - ENDC - bra L0EB8 and go from map type 1 to map type 0 - -* Execute SWI vector -SWIVCT ldx #D.SWI get DP offset of vector - bra SWICall go execute it - -* Execute NMI vector -NMIVCT ldx #D.NMI get DP offset of vector - bra L0EB8 go execute it - - emod -eom equ * - -*SWIStack fcc /REGISTER STACK/ R$Size data bytes -SWIStack fcb $88,$03,$00 - IFNE H6309 - fcb $45,$72 - ENDC - fcb $00,$cd,$00,$12,$00,$00,$00,$e5,$7f - - fcb $55 D.ErrRst - -* Now bra instead of lbra since 2 cycles/interrupt faster - bra SWI3VCT SWI3 vector - nop - bra SWI2VCT SWI2 vector - nop - bra FIRQVCT FIRQ vector - nop - bra IRQVCT IRQ vector - nop - bra SWIVCT SWI vector - nop - bra NMIVCT NMI vector - nop - - end - + leay <SWIStack,pc where to put the register stack: to $FEDF + tfr s,u get a copy of where the stack is + ifne H6309 + ldw #R$Size get the size of the stack + tfm u+,y+ move the stack to the top of memory + else + pshs b + ldb #R$Size +Looper lda ,u+ + sta ,y+ + decb + bne Looper + puls b + endc + bra L0EB8 and go from map type 1 to map type 0 + +* Execute SWI vector (called from $FEFA) +SWIVCT ldx #D.SWI get DP offset of vector + bra SWICall go execute it + +* Execute NMI vector (called from $FEFD) +NMIVCT ldx #D.NMI get DP offset of vector + bra L0EB8 go execute it + +* The end of the kernel module is here + emod +eom equ * + +* What follows after the kernel module is the register stack, starting +* at $FEDE. This register stack area is used by the kernel to save the +* caller's registers in the $FEXX area of memory because it doesn't +* get "switched out" no matter the contents of the MMU registers. +SWIStack + fcc /REGISTER STACK/ same # bytes as R$Size for 6809 + ifne H6309 + fcc /63/ if 6309, add two more spaces + endc + + fcb $55 D.ErrRst + +* This list of addresses ends up at $FFEE after the kernel track is loaded +* into memory. All interrupts come through the 6809 vectors at $FFF0-$FFFE +* and get directed to here. From here, the BRA takes CPU control to the +* various handlers in the kernel. + bra SWI3VCT SWI3 vector comes here + nop + bra SWI2VCT SWI2 vector comes here + nop + bra FIRQVCT FIRQ vector comes here + nop + bra IRQVCT IRQ vector comes here + nop + bra SWIVCT SWI vector comes here + nop + bra NMIVCT NMI vector comes here + nop + + end