Mercurial > hg > Members > kono > nitros9-code
changeset 1145:ca83286ded5b
Start of new OS-9 L2 Kernel
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/defsfile Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,1 @@ + use ../../defsfile
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fallbit.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,313 @@ +************************************************** +* System Call: F$AllBit +* +* Function: Sets bits in an allocation bitmap +* +* Input: X = Address of allocation bitmap +* D = Number of first bit to set +* Y = Bit count (number of bits to set) +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FAllBit ldd R$D,u get bit # to start with + ldx R$X,u get address of allocation bit map + bsr CalcBit calculate byte & position & get first bit mask + ldy <D.Proc get current task # + ldb P$Task,y get task number + bra SetBit go do it + +* F$AllBit (System State) +FSAllBit ldd R$D,u get bit # to start with + ldx R$X,u get address of allocation bit map + bsr CalcBit calculate byte & pos & get first bit mask + ldb <D.SysTsk Get system task # + +* Main bit setting loop +SetBit equ * + IFNE H6309 + ldw R$Y,u get # bits to set + ELSE + ldy R$Y,u get # bits to set + ENDC + beq BitEx nothing to set, return + sta ,-s preserve current mask + bmi SkpBit If high bit set, skip ahead + os9 F$LDABX Go get original value from bit map +NxtBitLp ora ,s OR it with the current mask + IFNE H6309 + decw Dec the bit counter + ELSE + leay -1,y + ENDC + beq BitStEx Done, go put the byte back into the task's map + lsr ,s Shift out the lowest bit of original + bcc NxtBitLp If it is a 0, do next bit + os9 F$STABX If it was a 1 (which means whole byte done), + leax 1,x Store finished byte and bump ptr +SkpBit lda #$FF Preload a finished byte + bra SkpBit2 Skip ahead + +StFulByt os9 F$STABX Store full byte + leax 1,x Bump ptr up 1 + IFNE H6309 + subw #8 Bump counter down by 8 +SkpBit2 cmpw #8 Is there at least 8 more (a full byte) to do? + ELSE + leay -8,y +SkpBit2 cmpy #$0008 + ENDC + bhi StFulByt More than 1, go do current + beq BitStEx Exactly 1 byte left, do final store & exit + +* Last byte: Not a full byte left loop +L085A lsra Bump out least sig. bit + IFNE H6309 + decw Dec the bit counter + ELSE + leay -1,y + ENDC + bne L085A Keep going until last one is shifted out + coma Invert byte to get proper result + sta ,s Preserve a sec + os9 F$LDABX Get byte for original map + ora ,s Merge with new mask +BitStEx os9 F$STABX Store finished byte into task + leas 1,s Eat the working copy of the mask +BitEx clrb No error & return + rts + +* Calculate address of first byte we want, and which bit in that byte, from +* a bit allocation map given the address of the map & the bit # we want to +* point to +* Entry: D=Bit # +* X=Ptr to bit mask table +* Exit: A=Mask to point to bit # within byte we are starting on +* X=Ptr in allocation map to first byte we are starting on +CalcBit pshs b,y preserve registers + IFNE H6309 + lsrd divide bit # by 8 to calculate byte # to start + lsrd allocating at + lsrd + addr d,x Offset that far into the map + ELSE + lsra + rorb + lsra + rorb + lsra + rorb + leax d,x + ENDC + puls b restore bit position LSB + leay <L0883,pc point to mask table + andb #7 round it down to nearest bit + lda b,y get bit mask + puls y,pc restore & return + +* Bit position table (NOTE that bit #'s are done by left to right) +L0883 fcb $80,$40,$20,$10,$08,$04,$02,$01 + + +************************************************** +* System Call: F$DelBit +* +* Function: Clears bits in an allocation bitmap +* +* Input: X = Address of allocation bitmap +* D = Number of first bit to clear +* Y = Bit count (number of bits to clear) +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FDelBit ldd R$D,u Get bit # to start with + ldx R$X,u Get addr. of bit allocation map + bsr CalcBit Point to starting bit + ldy <D.Proc Get current Task # + ldb P$Task,y get task # + bra L08A0 Do rest of 0 bits + +* F$DelBit entry point for system state +FSDelBit ldd R$D,u Get bit # to start with + ldx R$X,u Get addr. of bit allocation map + bsr CalcBit Point to starting bit + ldb <D.SysTsk Get system task # + +L08A0 equ * + IFNE H6309 + ldw R$Y,u Get # bits to clear + ELSE + ldy R$Y,u Get # bits to clear + ENDC + beq L08E0 None, return + coma Invert current bit mask + sta ,-s Preserve on stack + bpl L08BC If high bit clear, skip ahead + os9 F$LDABX Go get byte from user's map +L08AD anda ,s AND it with current mask + IFNE H6309 + decw Dec the bits left counter + ELSE + leay -1,y + ENDC + beq BitDone Done, store finished byte back in task's map + asr ,s Shift out lowest bit, leaving highest alone + bcs L08AD If it is a 1, do next bit + os9 F$STABX If it was a 0 (which means whole byte done), + leax 1,x store finished byte & inc. ptr +L08BC clra Preload a cleared byte + bra ChkFull skip ahead +L08BF os9 F$STABX Store full byte + leax 1,x Bump ptr up by 1 + IFNE H6309 + subw #8 Dec bits left counter by 8 +ChkFull cmpw #8 At least 1 full byte left? + ELSE + leay -8,y +ChkFull cmpy #8 + ENDC + bhi L08BF Yes, do a whole byte in 1 shot + beq BitDone Exactly 1, store byte & exit + coma < full byte left, invert bits +L08CF lsra Shift out rightmost bit + IFNE H6309 + decw Dec bits left counter + ELSE + leay -1,y + ENDC + bne L08CF Keep doing till done + sta ,s Save finished mask + os9 F$LDABX Get original byte from task + anda ,s Merge cleared bits with it +BitDone os9 F$STABX Store finished byte into task + leas 1,s Eat working copy of mask +L08E0 clrb Eat error & return + rts + + +************************************************** +* System Call: F$SchBit +* +* Function: Search bitmap for a free area +* +* Input: X = Address of allocation bitmap +* D = Starting bit number +* Y = Bit count (free bit block size) +* U = Address of end of allocation bitmap +* +* Output: D = Beginning bit number +* Y = Bit count +* +* Error: CC = C bit set; B = error code +* +FSchBit ldd R$D,u Get start bit # + ldx R$X,u Get addr. of allocation bit map + bsr CalcBit Point to starting bit + ldy <D.Proc Get task # + ldb P$Task,y + bra L08F8 skip ahead + +* F$SchBit entry point for system +FSSchBit ldd R$D,u Get start bit # + ldx R$X,u Get addr. of allocation bit map + lbsr CalcBit Point to starting bit + ldb <D.SysTsk Get task # +* Stack: 0,s : byte we are working on (from original map) +* 1,s : Mask of which bit in current byte to start on +* 2,s : Task number the allocation bit map is in +* 3,s : Largest block found so far +* 5,s : Starting bit # of requested (or closest) size found +* 7,s : Starting bit # of current block being checked (2 bytes) (NOW IN Y) + IFNE H6309 +L08F8 pshs cc,d,x,y Preserve task # & bit mask & reserve stack space + clrd Faster than 2 memory clears + ELSE +L08F8 pshs cc,d,x,y,u Preserve task # & bit mask & reserve stack space + clra + clrb + ENDC + std 3,s Preserve it + IFNE H6309 + ldw R$D,u get start bit # + tfr w,y save as current block starting bit # + ELSE + ldy R$D,u + sty 7,s + ENDC + bra Skipper skip ahead + +* New start point for search at current location +RstSrch equ * + IFNE H6309 + tfr w,y Preserve current block bit # start + ELSE + sty 7,s + ENDC +* Move to next bit position, and to next byte if current byte is done +MoveBit lsr 1,s Move to next bit position + bcc CheckBit If not the last one, check it + ror 1,s Move bit position marker to 1st bit again + leax 1,x Move byte ptr (in map) to next byte + +* Check if we are finished allocation map +Skipper cmpx R$U,u done entire map? + bhs BadNews yes, couldn't fit in 1 block, notify caller + ldb 2,s Get task number + os9 F$LDABX Get byte from bit allocation map + sta ,s Preserve in scratch area + +* Main checking +CheckBit equ * + IFNE H6309 + incw Increment current bit # + ELSE + leay 1,y + ENDC + lda ,s Get current byte + anda 1,s Mask out all but current bit position + bne RstSrch If bit not free, restart search from next bit + IFNE H6309 + tfr w,d Dupe current bit # into D + subr y,d Calculate size we have free so far + cmpd R$Y,u As big as user requested? + ELSE + tfr y,d + subd 7,s + cmpd R$Y,u + ENDC + bhs WereDone Yes, we are done + cmpd $03,s As big as the largest one we have found so far? + bls MoveBit No, move to next bit and keep going + std $03,s It is the largest, save current size + IFNE H6309 + sty $05,s Save as start bit # of largest block found so far + ELSE + ldd 7,s + std 5,s + ENDC + bra MoveBit Move to next bit and keep going + +* Couldn't find requested size block; tell user where the closest was found +* and how big it was +BadNews ldd $03,s Get size of largest block we found + std R$Y,u Put into callers Y register + comb Set carry to indicate we couldn't get full size + ldd 5,s Get starting bit # of largest block we found + bra BadSkip skip ahead +* Found one, tell user where it is +WereDone equ * + IFNE H6309 + tfr y,d Get start bit # of the block we found + ELSE + ldd 7,s + ENDC +BadSkip std R$D,u Put starting bit # of block into callers D register + IFNE H6309 + leas $07,s Eat our temporary stack area & return + ELSE + leas $09,s + ENDC + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fallimg.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,67 @@ +* F$AllImg entry point +* Entry: U=Register stack pointer +FAllImg ldd R$D,u get starting block # & # of blocks + ldx R$X,u get process descriptor pointer +* Entry point from F$SRqMem +* +* 6309 NOTE: IF W IS USED HERE, TRY TO PRESERVE IT AS F$SRQMEM WILL +* PROBABLY END UP USING IT +L09BE pshs d,x,y,u + lsla + leay P$DATImg,x + leay a,y + clra + tfr d,x + ldu <D.BlkMap + pshs d,x,y,u +L09CD ldd ,y++ + cmpd #DAT.Free + beq L09E2 + lda d,u + cmpa #RAMinUse + puls d + bne L09F7 + IFNE H6309 + decd + ELSE + subd #$0001 + ENDC + pshs d +L09E2 leax -1,x + bne L09CD + ldx ,s++ + beq L0A00 +L09EA lda ,u+ + bne L09F2 + leax -1,x + beq L0A00 +L09F2 cmpu <D.BlkMap+2 + bcs L09EA +L09F7 ldb #E$MemFul + leas 6,s + stb 1,s + comb + puls d,x,y,u,pc + +L0A00 puls x,y,u +L0A02 ldd ,y++ + cmpd #DAT.Free + bne L0A16 +L0A0A lda ,u+ + bne L0A0A + inc ,-u + tfr u,d + subd <D.BlkMap + std -2,y +L0A16 leax -1,x + bne L0A02 + ldx 2,s + IFNE H6309 + oim #ImgChg,P$State,x + ELSE + lda P$State,x + ora #ImgChg + sta P$State,x + ENDC + clrb + puls d,x,y,u,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fallprc.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,158 @@ +* F$AllPrc entry point +* Entry: U=Register stack pointer +FAllPrc pshs u preserve register stack pointer + bsr AllPrc try & allocate descriptor + bcs L02E8 can't do, return + ldx ,s get register stack pointer + stu R$U,x save pointer to new descriptor +L02E8 puls u,pc restore & return +* Allocate a process desciptor +* Entry: None +AllPrc ldx <D.PrcDBT get pointer to process descriptor block table +L02EC lda ,x+ get a process block # + bne L02EC used, keep looking + leax -1,x point to it again + tfr x,d move it to D + subd <D.PrcDBT subtract pointer to table (gives actual prc. ID) + tsta id valid? + beq L02FE yes, go on + comb set carry + ldb #E$PrcFul get error code + rts Return with error + +L02FE pshs b save process # + ldd #P$Size get size of descriptor + os9 F$SRqMem request the memory for it + puls a restore process # + bcs L032F exit if error from mem call + sta P$ID,u save ID to descriptor + tfr u,d + sta ,x save ID to process descriptor table + +* Clear out process descriptor through till stack + IFNE H6309 + leay <Null3,pc Point to 0 byte + leax 1,u + ldw #$0100 +Null3 equ *-1 + tfm y,x+ + ELSE + clra + leax P$PID,u + ldy #$80 +LChinese std ,x++ + leay -1,y + bne LChinese + ENDC + +*************************************************************************** +* OS-9 L2 Upgrade Enhancement: Stamp current date/time for start of process +* ldy <D.Proc get current process descriptor +* ldx <D.SysProc get system process descriptor +* stx <D.Proc make system process current +* leax P$DatBeg,u new proc desc creation date/time stamp +* os9 F$Time ignore any error... +* sty <D.Proc restore current proc desc address +*************************************************************************** + + lda #SysState set process to system state + sta P$State,u +* Empty out DAT image + ldb #DAT.BlCt # of double byte writes + ldx #DAT.Free Empty block marker + leay P$DATImg,u +L0329 stx ,y++ + decb done? + bne L0329 no, keep going + clrb clear carry +L032F rts return + +* F$DelPrc entry point +FDelPrc lda R$A,u get process # + bra L0386 delete it + +* F$Wait entry point +* Checks all children to see if any died (done through linked child process +* list through P$CID for 1st one & P$SID for rest) +* Will stick process into Wait Queue until either Waiting process receives +* signal or until child dies. Child dying does NOT send signal to parent +FWait ldx <D.Proc get current process + lda P$CID,x any children? + beq L0368 no, exit with error +L033A lbsr L0B2E get pointer to child process dsc. into Y + IFNE H6309 + tim #Dead,P$State,y Is child dead? + ELSE + lda P$State,y + bita #Dead + ENDC + bne L036C Yes, send message to parent + lda P$SID,y No, check for another child (thru sibling list) + bne L033A Yes there is another child, go see if it is dead +* NOTE: MAY WANT TO ADD IN CLRB, CHANGE TO STD R$A,u + sta R$A,u No child has died, clear out process # & status + sta R$B,u code in caller's A&B regs + pshs cc Preserve CC + orcc #IntMasks Shut off interrupts + lda <P$Signal,x Any signals pending? + beq L035D No, skip ahead +* No Child died, but received signal + deca Yes, is it a wakeup signal? + bne L035A no, wake it up with proper signal + sta <P$Signal,x Clear out signal code +L035A lbra L071B go wake it up (no signal will be sent) + +* No dead child & no signal...execute next F$Waiting process in line +L035D ldd <D.WProcQ get ptr to head of waiting process line + std P$Queue,x save as next process in line from current one + stx <D.WProcQ save curr. process as new head of waiting process line + puls cc restore interupts + lbra L0780 go activate next process in line + +L0368 comb Exit with No Children error + ldb #E$NoChld + rts + +* Child has died +* Entry: Y=Ptr to child process that died +* U=Ptr to caller's register stack +L036C lda P$ID,y Get process ID of dead child + ldb <P$Signal,y Get signal code that child received (if any) + std R$D,u Save in caller's D + leau ,y Point U to child process dsc. + leay P$CID-P$SID,x Bump Y up by 1 for 1st loop so P$SID below actually +* references P$CID + bra L037C skip ahead + +* Update linked list of sibling processes to exclude dead child +L0379 lbsr L0B2E get pointer to process +L037C lda P$SID,y Get Sibling ID (or Child ID on 1st run) + cmpa P$ID,u Same as Dying process ID? + bne L0379 No, go get ptr to Sibling process & do again + ldb P$SID,u Yes, wrapped to our own, get Sibling ID from child + stb P$SID,y Save as sibling process id # in other sibling + +L0386 pshs d,x,u preserve regs + cmpa WGlobal+G.AlPID Does dying process have an alarm set up? + bne L0393 no, go on + IFNE H6309 + clrd Faster than 2 memory clears + ELSE + clra + clrb + ENDC + std WGlobal+G.AlPID clear alarm ID & signal + +L0393 ldb ,s get dying process # back + ldx <D.PrcDBT get ptr to process descriptor block table + abx offset into table + lda ,x Get MSB of process dsc. ptr + beq L03AC If gone already, exit + clrb + stb ,x Clear out entry in block table + tfr d,x Move process dsc. ptr to X + os9 F$DelTsk Remove task # for this process + leau ,x Point U to start of Dead process dsc. + ldd #P$Size Size of a process dsc. + os9 F$SRtMem Deallocate process dsc. from system memory pool +L03AC puls d,x,u,pc Restore regs & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fallram.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,49 @@ +* F$AllRam entry point +* Entry: B=# blocks to allocate +* Exit: D=block # of start of contigously allocated blocks +FAllRam ldb R$B,u Get # blocks requested + pshs b,x,y Save regs + ldx <D.BlkMap Get ptr to start of block map +L0974 leay ,x Point Y to current block + ldb ,s Get # blocks requested +L0978 cmpx <D.BlkMap+2 Hit end of map yet? + bhs L0995 Yes, exit with No RAM error + lda ,x+ Get block marker + bne L0974 Already used, start over with next block up + decb Dec # blocks still needed + bne L0978 Still more, keep checking +* Entry: Y=ptr to start of memory found +* Note: Due to fact that block map always starts @ $200 (up to $2FF), we +* don't need to calc A +L0983 tfr y,d Copy start of requested block mem ptr to D (B) + lda ,s Get # blocks requested + stb ,s Save start block # +L098D inc ,y+ Flag blocks as used + deca (for all blocks allocated) + bne L098D Do until done + puls b Get start block # + clra (allow for D as per original calls) + std R$D,u Save for caller + puls x,y,pc Restore regs & return + +L0995 comb Exit with No RAM error + ldb #E$NoRam + stb ,s + puls b,x,y,pc + +* F$AlHRam entry point +* Entry: B=# blocks to allocate +* Exit: D=block # of start of contigously allocated blocks +FAlHRam ldb R$B,u Get # blocks to allocate + pshs b,x,y Preserve regs + ldx <D.BlkMap+2 Get ptr to end of block map +L09A9 ldb ,s Get # blocks requested +L09AB cmpx <D.BlkMap Are we at beginning of RAM yet? + bls L0995 Yes, exit with No RAM error + lda ,-x Get RAM block marker + bne L09A9 If not free, start checking next one down + decb Free block, dec # blocks left to find count + bne L09AB Still more needed, keep checking + tfr x,y Found enough contigous blocks, move ptr to Y + bra L0983 Go mark blocks as used, & return info to caller +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/falltsk.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,148 @@ +* F$AllTsk entry point +FAllTsk ldx R$X,u get pointer to process descriptor +L0C58 ldb P$Task,x already have a task #? + bne L0C64 yes, return + bsr L0CA6 find a free task + bcs L0C65 error, couldn't get one, return + stb P$Task,x save task # + bsr L0C79 load MMU with task +L0C64 clrb clear errors +L0C65 rts return + +* F$DelTsk entry point +FDelTsk ldx R$X,u +L0C68 ldb P$Task,x grab the current task number + beq L0C64 if system (or released), exit + clr P$Task,x force the task number to be zero + bra L0CC3 do a F$RelTsk + +TstImg equ * + IFNE H6309 + tim #ImgChg,P$State,x + ELSE + pshs a + lda P$State,x + bita #ImgChg + puls a + ENDC + beq L0C65 if not, exit now: don't clear carry, it's not needed + fcb $8C skip LDX, below + +* F$SetTsk entry point +FSetTsk ldx R$X,u get process descriptor pointer +L0C79 equ * + IFNE H6309 + aim #^ImgChg,P$State,x flag DAT image change in process descriptor + ELSE + lda P$State,x + anda #^ImgChg + sta P$State,x + ENDC + clr <D.Task1N task 1 DAT image has changed + andcc #^Carry clear carry + pshs cc,d,x,u preserve everything + ldb P$Task,x get task # + leau <P$DATImg,x point to DAT image + ldx <D.TskIPt get task image table pointer + lslb account for 2 bytes/entry + stu b,x save DAT image pointer in task table + cmpb #2 is it either system or GrfDrv? + bhi L0C9F no, return + ldx #$FFA0 update system DAT image + lbsr L0E93 go bash the hardware +L0C9F puls cc,d,x,u,pc + +* F$ResTsk entry point +FResTsk bsr L0CA6 + stb R$B,u +L0CA5 rts + +* Find a free task in task map +* Entry: None +* Exit : B=Task # +L0CA6 pshs x preserve X + ldb #$02 get starting task # (skip System/Grfdrv) + ldx <D.Tasks get task table pointer +L0CAC lda b,x task allocated? + beq L0CBA no, allocate it & return + incb move to next task + cmpb #$20 end of task list? + bne L0CAC no, keep looking + comb set carry for error + ldb #E$NoTask get error code + puls x,pc + +L0CBA stb b,x flag task used (1 cycle faster than inc) +* orb <D.SysTsk merge in system task # ??? always 0 + clra clear carry +L0CBF puls x,pc restore & return + +* F$RelTsk entry point +* no idea why B and X are saved. +FRelTsk ldb R$B,u Get task # to release +L0CC3 pshs b,x Preserve it & X +* ??? No idea why this stuff is done. D.SysTsk is ALWAYS 0. +* Even GrfDrv never changes it. +* ldb <D.SysTsk Get system task # +* comb Invert it +* andb ,s Mask with requested task + tstb check out B + beq L0CD0 If system task, don't bother deleting the task + ldx <D.Tasks Get task table ptr + clr b,x Clear out the task +L0CD0 puls b,x,pc Restore regs & return + +* Sleeping process update (Gets executed from clock) +* Could move this code into Clock, but what about the call to F$AProc (L0D11)? +* It probably will be OK... but have to check. +* Possible, move ALL software-clock code into OS9p2, and therefore +* have it auto-initialize? All hardware clocks would then be called +* just once a minute. +L0CD2 ldx <D.SProcQ Get sleeping process Queue ptr + beq L0CFD None (no one sleeping), so exit + IFNE H6309 + tim #TimSleep,P$State,x Is it a timed sleep? + ELSE + ldb P$State,x + bitb #TimSleep + ENDC + beq L0CFD No, exit: waiting for signal/interrupt + ldu P$SP,x Yes, get his stack pointer + ldd R$X,u Get his sleep tick count + IFNE H6309 + decd decrement sleep count + ELSE + subd #$0001 + ENDC + std R$X,u Save it back + bne L0CFD Still more ticks to go, so exit +* Process needs to wake up, update queue pointers +L0CE7 ldu P$Queue,x Get next process in Queue + bsr L0D11 activate it + leax ,u point to new process + beq L0CFB don't exist, go on + IFNE H6309 + tim #TimSleep,P$State,x is it in a timed sleep? + ELSE + ldb P$State,x + bitb #TimSleep + ENDC + beq L0CFB no, go update process table + ldu P$SP,x get it's stack pointer + ldd R$X,u any sleep time left? + beq L0CE7 no, go activate next process in queue +L0CFB stx <D.SProcQ Store new sleeping process pointer +L0CFD dec <D.Slice Any time remaining on process? + bne L0D0D Yes, exit + inc <D.Slice reset slice count + ldx <D.Proc Get current process pointer + beq L0D0D none, return + IFNE H6309 + oim #TimOut,P$State,x put him in a timeout state + ELSE + ldb P$State,x + orb #TimOut + stb P$State,x + ENDC +L0D0D clrb + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/faproc.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,34 @@ +************************************************** +* System Call: F$AProc +* +* Function: Insert process into active process queue +* +* Input: X = Address of process descriptor +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FAProc ldx R$X,u Get ptr to process to activate +L0D11 clrb + pshs cc,b,x,y,u + lda P$Prior,x Get process priority + sta P$Age,x Save it as age (How long it's been around) + orcc #IntMasks Shut down IRQ's + ldu #(D.AProcQ-P$Queue) Get ptr to active process queue + bra L0D29 Go through the chain +* Update active process queue +* X=Process to activate +* U=Current process in queue links +L0D1F inc P$Age,u update current process age + bne L0D25 wrap? + dec P$Age,u yes, reset it to max. +L0D25 cmpa P$Age,u match process ages?? + bhi L0D2B no, skip update +L0D29 leay ,u point Y to current process +L0D2B ldu P$Queue,u get pointer to next process in chain + bne L0D1F Still more in chain, keep going + ldd P$Queue,y + stx P$Queue,y save new process to chain + std P$Queue,x + puls cc,b,x,y,u,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fchain.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,269 @@ +************************************************** +* System Call: F$Chain +* +* Function: Starts a new child process and terminates the calling process. +* +* Input: X = Address of module or filename +* Y = Parameter area size (256 byte pages) +* U = Address of parameter area +* A = Language/Type code +* B = Optional data area size (256 byte pages) +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FChain pshs u preserve register stack pointer + lbsr AllPrc allocate a new process descriptor + bcc L03B7 do the chain if no error + puls u,pc return to caller with error + +* Copy Process Descriptor Data +L03B7 ldx <D.Proc get pointer to current process + pshs x,u save old & new descriptor pointers + leax P$SP,x point to source + leau P$SP,u point to destination + IFNE H6309 + ldw #$00fc get size (P$SP+$FC) + tfm x+,u+ move it + ELSE + ldy #$007E +L03C3 ldd ,x++ copy bytes + std ,u++ + leay -1,y + bne L03C3 + ENDC +L03CB ldu 2,s get new descriptor pointer + leau <P$DATImg,u + ldx ,s get old descriptor pointer + lda P$Task,x get task # + lsla 2 bytes per entry + ldx <D.TskIpt get task image table pointer + stu a,x save updated DAT image pointer for later +* Question: are the previous 7 lines necessary? The F$AllTsk call, below +* should take care of everything! + ldx <D.Proc get process descriptor + IFNE H6309 + clrd Faster than 2 memory clears + ELSE + clra + clrb + ENDC + stb P$Task,x old process has no task number + std <P$SWI,x clear out all sorts of signals and vectors + std <P$SWI2,x + std <P$SWI3,x + sta <P$Signal,x + std <P$SigVec,x + ldu <P$PModul,x + os9 F$UnLink unlink from the primary module + ldb P$PagCnt,x grab the page count + addb #$1F round up to the nearest block + lsrb + lsrb + lsrb + lsrb + lsrb get number of blocks used + lda #$08 + IFNE H6309 + subr b,a A=number of blocks unused + ELSE + pshs b + suba ,s+ + ENDC + leay <P$DATImg,x set up the initial DAT image + lslb + leay b,y go to the offset + ldu #DAT.Free mark the blocks as free +L040C stu ,y++ do all of them + deca + bne L040C + ldu 2,s get new process descriptor pointer + stu <D.Proc make it the new process + ldu 4,s + lbsr L04B1 link to new module & setup register stack + IFNE H6309 + bcs L04A1 + ELSE + lbcs L04A1 + ENDC + pshs d somehow D = memory size? Or parameter size? + os9 F$AllTsk allocate a new task number +* ignore errors here +* Hmmm.. the code above FORCES the new process to have the same DAT image ptr +* as the old process, not that it matters... + + fcb $24,$00 + ldu <D.Proc get nre process + lda P$Task,u new task number + ldb P$Task,x old task number + leau >(P$Stack-R$Size),x set up the stack for the new process + leax ,y + ldu R$X,u where to copy from + IFNE H6309 + cmpr x,u check From/To addresses + ELSE + pshs u src ptr + cmpx ,s++ dest ptr + ENDC + puls y size + bhi L0471 To < From: do F$Move + beq L0474 To == From, skip F$Move + +* To > From: do special copy + leay ,y any bytes to move? + beq L0474 no, skip ahead + IFNE H6309 + pshs x save address + addr y,x add size to FROM address + cmpr x,u is it + puls x + ELSE + pshs d,x + tfr y,d + leax d,x + pshs u + cmpx ,s++ + puls d,x + ENDC + bls L0471 end of FROM <= start of TO: do F$Move + +* The areas to copy overlap: do special move routine + pshs d,x,y,u save regs + IFNE H6309 + addr y,x go to the END of the area to copy FROM + addr y,u end of area to copy TO + ELSE + tfr y,d + leax d,x + leau d,y + ENDC + +* This all appears to be doing a copy where destination <= source, +* in the same address space. +L0457 ldb ,s grab ?? + leax -1,x back up one + os9 F$LDABX + exg x,u + ldb 1,s + leax -1,x back up another one + os9 F$STABX + exg x,u + leay -1,y + bne L0457 + + puls d,x,y,u restore regs + bra L0474 skip over F$Move + +L0471 os9 F$Move move data over? +L0474 lda <D.SysTsk get system task number + ldx ,s old process dsc ptr + ldu P$SP,x + leax >(P$Stack-R$Size),x + ldy #R$Size + os9 F$Move move the stack over + puls u,x restore new, old process dsc's + lda P$ID,u + lbsr L0386 check alarms + os9 F$DelTsk delete the old task + orcc #IntMasks + ldd <D.SysPrc + std <D.Proc + IFNE H6309 + aim #^SysState,P$State,x + ELSE + lda P$State,x + anda #^SysState + sta P$State,x + ENDC + os9 F$AProc activate the process + os9 F$NProc go to it + +* comes here on error with link to new module +L04A1 puls u,x + stx <D.Proc + pshs b + lda ,u + lbsr L0386 kill signals + puls b + os9 F$Exit exit from the process with error condition + +* Setup new process DAT image with module +L04B1 pshs d,x,y,u preserve everything + ldd <D.Proc get pointer to current process + pshs d save it + stx <D.Proc save pointer to new process + lda R$A,u get module type + ldx R$X,u get pointer to module name + ldy ,s get pointer to current process + leay P$DATImg,y point to DAT image + os9 F$SLink map it into new process DAT image + bcc L04D7 no error, keep going + ldd ,s restore to current process + std <D.Proc + ldu 4,s get pointer to new process + os9 F$Load try & load it + bcc L04D7 no error, keep going + leas 4,s purge stack + puls x,y,u,pc restore & return +* +L04D7 stu 2,s save pointer to module + pshs a,y save module type & entry point + ldu $0B,s restore register stack pointer + stx R$X,u save updated name pointer + ldx $07,s restore process pointer + stx <D.Proc make it current + ldd 5,s get pointer to new module + std P$PModul,x save it into process descriptor + puls a restore module type + cmpa #Prgrm+Objct regular module? + beq L04FB yes, go + cmpa #Systm+Objct system module? + beq L04FB +*--- these lines added to allow 6309 native mode modules to be executed + cmpa #Prgrm+Obj6309 regular module? + beq L04FB yes, go + cmpa #Systm+Obj6309 system module? + beq L04FB +*--- + ldb #E$NEMod return unknown module +L04F4 leas 2,s purge stack + stb 3,s save error + comb set carry + bra L053E return +* Setup up data memory +L04FB ldd #M$Mem get offset to module memory size + leay P$DATImg,x get pointer to DAT image + ldx P$PModul,x get pointer to module header + os9 F$LDDDXY get module memory size + cmpa R$B,u bigger or smaller than callers request? + bcc L050E bigger, use it instead + lda R$B,u get callers memory size instead + clrb clear LSB of mem size +L050E os9 F$Mem try & get the data memory + bcs L04F4 can't do it, exit with error + ldx 6,s restore process pointer + leay (P$Stack-R$Size),x point to new register stack + pshs d preserve memory size + subd R$Y,u take off size of paramater area + std R$X,y save pointer to parameter area + subd #R$Size take off size of register stack + std P$SP,x save new SP + ldd R$Y,u get parameter count + std R$A,y save it to new process + std 6,s save it for myself to + puls d,x restore top of mem & program entry point + std R$Y,y set top of mem pointer + ldd R$U,u get pointer to parameters + std 6,s + lda #Entire + sta R$CC,y save condition code + clra + sta R$DP,y save direct page + clrb + std R$U,y save data area start + stx R$PC,y save program entry point +L053E puls d restore process pointer + std <D.Proc save it as current + puls d,x,y,u,pc +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fclrblk.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,42 @@ +* F$ClrBlk entry point +FClrBlk ldb R$B,u + beq L0BE9 + ldd R$U,u + tstb + bne L0BAA + bita #$1F + bne L0BAA + ldx <D.Proc + lda P$SP,x + anda #$E0 + suba R$U,u + bcs L0BCE + lsra + lsra + lsra + lsra + lsra + cmpa R$B,u + bcs L0BAA +L0BCE + IFNE H6309 + oim #ImgChg,P$State,x + ELSE + lda P$State,x + ora #ImgChg + sta P$State,x + ENDC + lda R$U,u + lsra + lsra + lsra + lsra + leay P$DATImg,x + leay a,y + ldb R$B,u + ldx #DAT.Free +L0BE4 stx ,y++ + decb + bne L0BE4 +L0BE9 clrb + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fcmpnam.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,79 @@ +************************************************** +* System Call: F$CmpNam +* +* Function: Compare two names +* +* Input: X = Address of first name +* Y = Address of second name +* B = length of first name +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FCmpNam ldx <D.Proc get current process ptr + leay P$DATImg,x Point to the DAT image + ldx R$X,u Get pointer to string #1 + pshs y,x preserve 'em + bra L07CF + +* F$CmpNam entry point for system state +FSCmpNam ldx <D.Proc Get current proc. dsc. ptr + leay P$DATImg,x Point to it's DAT image + ldx R$X,u get pointer to string #1 + pshs x,y + ldy <D.SysDAT get pointer to system DAT +L07CF ldx R$Y,u get pointer to string #2 + pshs y,x Preserve them + ldd R$D,u get length + leax 4,s point to string #1 info packet + leay ,s point to string #2 info packet + bsr L07DE go compare 'em + leas 8,s purge stack + rts return + +* Compare 2 strings +* +* Input: D = Length of string #1 (only requires B) +* X = Ptr to string #1 info packet +* 0,X = DAT image pointer +* 2,X = Pointer to string +* Y = Ptr to string #2 info packet +* 0,Y = DAT image pointer +* 2,Y = Pointer to string +* U = Register stack ptr +L07DE pshs d,x,y,u preserve registers + tfr x,u U=ptr to string #1 packet + pulu x,y get DAT ptr to Y and string ptr to X + lbsr AdjBlk0 adjust X to use block 0 + pshu x,y put them back + ldu 4,s get pointer to string #2 packet + pulu x,y get DAT ptr to Y and string ptr to X + lbsr AdjBlk0 Adjust X to block 0 + bra L07F6 go compare the strings + +L07F2 ldu 4,s get pointer to string #2 packet + pulu x,y get DAT ptr to Y and string ptr to X +L07F6 lbsr LDAXY Map in the block & grab a byte from string + pshu x,y Put updated DAT & string ptr back + pshs a Save the character + ldu 3,s pointer to string #1 packet + pulu x,y get DAT ptr to Y and string ptr to X + lbsr LDAXY get byte from string #1 + pshu y,x put pointers back + eora ,s + tst ,s+ was it high bit? + bmi L0816 yes, check if last character in string #2 + decb + beq L0813 + anda #$DF match? + beq L07F2 yes, check next character +L0813 comb set carry + puls d,x,y,u,pc + +L0816 decb done whole string? + bne L0813 no, exit with no match + anda #$5F match? + bne L0813 yes, keep checking + clrb strings match, clear carry + puls d,x,y,u,pc restore & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fcpymem.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,122 @@ + IFNE H6309 + +* F$CpyMem entry point +* NOTE: It currently checks to see if the end of the buffer you are copying to +* will overflow past $FFFF, and exits if it does. Should this be changed to +* check if it overflows past the data area of a process, or at least into +* Vector page RAM & I/O ($FE00-$FFFF)? +FCpyMem ldd R$Y,u get byte count + beq L0A01 nothing there so nothing to move, return + addd R$U,u add it caller's buffer start ptr. + cmpa #$FE Is it going to overwrite Vector or I/O pages? + bhs L0A01 Yes, exit without error + leas -$10,s make a buffer for DAT image + leay ,s point to it + pshs y,u Preserve stack buffer ptr & register stack pointer + ldx <D.Proc Get caller's task # + ldf P$Task,x get task # of caller + leay P$DATImg,x Point to DAT image in callers's process dsc. + ldx R$D,u get caller's DAT image pointer + lde #$08 counter (for double byte moves) + ldu ,s get temp. stack buffer pointer + +* This loop copies the DAT image from the caller's process descriptor into +* a temporary buffer on the stack +L09C7 equ * + clrd Clear offset to 0 + bsr L0B02 Short cut OS9 F$LDDDXY + std ,u++ save it to buffer + leax 2,x Bump ptr + dece Decrement loop counter + bne L09C7 Keep doing until 16 bytes is done + + ldu 2,s Get back register stack pointer + lbsr L0CA6 Short cut OS9 F$ResTsk + bcs L09FB If error, deallocate our stack & exit with error + tfr b,e New temp task # into E + lslb Multiply by 2 for 2 byte entries + ldx <D.TskIPt Get ptr to task image table +* Make new temporary task use the memory blocks from the requested DAT image +* from the caller, to help do a 1 shot F$Move command, because in general +* the temporary DAT image is not associated with a task. + ldu ,s Get pointer to DAT image we just copied + stu b,x Point new task image table to our DAT image copy + ldu 2,s Get back data area pointer + tfr w,d Move temp & caller's task #'s into proper regs. + pshs a Save new task # + bsr L0B25 F$Move the memory into the caller's requested area +* BAD Bug! Well, maybe not. F$Move NEVER returns an error code +* but if it did, we'd skip the $RelTsk, and have an orphan task +* left over. +* bcs L09FB If error, purge stack & return with error code + puls b Get back new task # + lbsr L0CC3 Short cut OS9 F$RelTsk +L09FB leas <$14,s Purge our stack buffer & return + rts + +L0A01 clrb No error & exit + rts + + + ELSE + +*------------------------------------------------* +* F$CpyMem +*------------------------------------------------* +FCpyMem ldd R$Y,u byte count + beq L0A01 ..skip if none + addd R$U,u plus dest buff + bcs L0A01 + leas -$10,s + leay ,s + pshs a,b,y save buff end,img ptr + ldx <D.Proc + ldb P$Task,X + pshs b save caller task# + leay P$DATImg,x + ldx R$D,u X=caller DAT img ptr + ldb #8 + pshs b,u + ldu P$Task,s U=tempdat ptr + +L09C7 clra D=0000 + clrb + os9 F$LDDDXY move user DAT image + std ,u++ to sys tempDAT img + leax 2,x + dec ,s + bne L09C7 ..loop + + puls b,u + ldx R$X,u X=offset + ldu R$U,u U=dest buffer + ldy 3,s Y=tmpDAT + + puls b + bra L09E7 + +N09D6 leax $E000,x + leay 2,y + +*------------------------------------------------* +* Copy Loop: + +L09E7 cmpx #$2000 + bcc N09D6 + +L09EC os9 F$LDAXY get byte + leax 1,x + exg x,u + + os9 F$STABX store byte + leax 1,x plus one + cmpx ,s + exg x,u + bcs L09E7 + leas $14,s + +L0A01 clrb ok + rts end. + + ENDC +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fcrcmod.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,21 @@ +* F$CRCMod entry point - CHANGED 05/20/93 +* Entry : A = 0 Report current mode +* = 1 Shut CRC Checking off +* =>2 Turn CRC Checking on +* Exit : A = 0 CRC is off +* 1 CRC is on +* no error can be returned +* except if call not available +FCRCMod lda R$A,u do they want a report or a toggle? + beq CRCRep a report only + deca Check for OFF + bne GoCRCon No, must be on + fcb $8C --- skip 2 bytes, saves 3 bytes of memory +* sta <D.CRC Shut CRC flag off +* bra CRCRep2 Save in caller's A & return +GoCRCon lda #$1 CRC checking on + sta <D.CRC Turn CRC checking on +CRCRep lda <D.CRC get current CRC flag for return +CRCRep2 sta R$A,u save it to their register stack + clrb no error + rts and exit
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fdatlog.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,24 @@ +* F$DATLog entry point +FDATLog ldb R$B,u Get logical Block # + ldx R$X,u Get offset into block + bsr CmpLBlk Go modify X to be Logical address + stx R$X,u Save in callers X register + clrb No error & return + rts + +* Compute logical address given B=Logical Block # & X=offset into block +* Exits with B being logical block & X=logical address +CmpLBlk pshs b Preserve logical block # + tfr b,a Move log. block # to A + lsla Multiply logical block by 32 + lsla + lsla + lsla + lsla + clrb D=8k offset value + IFNE H6309 + addr d,x X=logical address in 64k workspace + ELSE + leax d,x + ENDC + puls b,pc Restore A, block # & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fdelimg.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,40 @@ +* F$DelImg entry point +FDelImg ldx R$X,u get process pointer + ldd R$D,u get start block & block count + leau <P$DATImg,x point to DAT image + lsla 2 bytes per block entry + leau a,u Point U to block entry +* Block count in B +L0B55 + IFNE H6309 + ldw ,u Get block # + addw <D.BlkMap Add it to map ptr + aim #^RAMinUse,0,w + ldw #DAT.Free get empty block marker + stw ,u++ save it to process descriptor + decb done? + bne L0B55 No, keep going + oim #ImgChg,P$State,x + ELSE + clra + tfr d,y + pshs x +L0BLoop ldd ,u + addd <D.BlkMap + tfr d,x + lda ,x + anda #^RAMinUse + sta ,x + ldd #DAT.Free + std ,u++ + leay -1,y + bne L0BLoop + + puls x + lda P$State,x + ora #ImgChg + sta P$State,x + ENDC + clrb + rts +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fdelram.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,28 @@ +* F$DelRAM entry point --- moved over from OS9p2 +FDelRAM ldb R$B,u # of blocks to de-allocate + beq DelRAM.2 if none, exit + ldd <D.BlkMap+2 get end of the block map + subd <D.BlkMap subtract out start of the block map + subd R$X,u take out starting block number + bls DelRAM.2 exit if the starting block is ># of blocks available + tsta check high byte of RAM # + bne DelRAM.0 if not zero, skip it + cmpb R$B,u check against size of the block + bhs DelRAM.0 if size is >RAM available + stb R$B,u save actual # of blocks deleted +DelRAM.0 ldx <D.BlkMap get start address of the block map + ldd R$X,u starting address of the RAM to de-allocate + leax d,x slower, but smaller than ADDR + ldb R$B,u get actual # of blocks to de-allocate +DelRAM.1 equ * + IFNE H6309 + aim #^RAMinUse,,x+ set to RAM not in use + ELSE + lda ,x + anda #^RAMinUse + sta ,x+ + ENDC + decb count down a block + bne DelRAM.1 continue +DelRAM.2 clrb and exit + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fexit.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,103 @@ +************************************************** +* System Call: F$Exit +* +* Function: Causes a process to cease execution and exit +* +* Input: B = Status code to be returned to parent process +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FExit ldx <D.Proc get current process pointer + bsr L05A5 close all the paths + ldb R$B,u get exit signal + stb <P$Signal,x and save in proc desc + leay P$PID,x + bra L0563 go find kids... + +L0551 clr P$SID,y clear child ID + lbsr L0B2E find its proc desc + clr 1,y clear sibling ID + IFNE H6309 + tim #Dead,P$State,y + ELSE + lda P$State,y get child's state + bita #Dead is it dead? + ENDC + beq L0563 ...no + lda P$ID,y else get its ID + lbsr L0386 and destroy its proc desc +L0563 lda P$SID,y get child ID + bne L0551 ...yes, loop + + leay ,x kid's proc desc + ldx #D.WProcQ-P$Queue + lds <D.SysStk use system stack + pshs cc save CC + orcc #IntMasks halt interrupts + lda P$PID,y get our parent ID + bne L0584 and wake him up + + puls cc restore CC + lda P$ID,y get our ID + lbsr L0386 give up our proc desc + bra L05A2 and start next active process + +* Search for Waiting Parent +L0580 cmpa P$ID,x is proc desc our parent's? + beq L0592 ...yes! + +L0584 leau ,x U is base desc + ldx P$Queue,x X is next waiter + bne L0580 see if parent + puls cc restore CC + lda #(SysState!Dead) set us to system state + sta P$State,y and mark us as dead + bra L05A2 so F$Wait will find us; next proc + +* Found Parent (X) +L0592 ldd P$Queue,x take parent out of wait queue + std P$Queue,u + puls cc restore CC + ldu P$SP,x get parent's stack register + ldu R$U,u + lbsr L036C get child's death signal to parent + os9 F$AProc move parent to active queue +L05A2 os9 F$NProc start next proc in active queue + +* Close Proc I/O Paths & Unlink Mem +* Entry: U=Register stack pointer +L05A5 pshs u preserve register stack pointer + ldb #NumPaths get maximum # of paths + leay P$Path,x point to path table +L05AC lda ,y+ path open? + beq L05B9 no, skip ahead + clr -1,y clear the path block # + pshs b preserve count + os9 I$Close close the path + puls b restore count +L05B9 decb done? + bne L05AC no, continue looking + +* Clean up memory process had + clra get starting block + ldb P$PagCnt,x get page count + beq L05CB none there, skip ahead + addb #$1F round it up + lsrb divide by 32 to get block count + lsrb + lsrb + lsrb + lsrb + os9 F$DelImg delete the ram & DAT image +* Unlink the module +L05CB ldd <D.Proc + pshs d + stx <D.Proc set bad proc + ldu P$PModul,x program pointer + os9 F$UnLink unlink aborted program + puls u,b,a + std <D.Proc reset parent proc + os9 F$DelTsk release X's task # + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/ffind64.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,213 @@ +************************************************** +* System Call: F$Find64 +* +* Function: Find a 64 byte memory block +* +* Input: X = Address of page table +* A = Block number +* +* Output: Y = Address of block +* +* Error: CC = C bit set; B = error code +* +* +FFind64 ldx R$X,u Get block tbl ptr + lda R$A,u get path block # +* Find a empty path block + beq L0A70 None, return error + clrb calculate address + IFNE H6309 + lsrd (Divide by 4) + lsrd + ELSE + lsra + rorb + lsra + rorb + ENDC + lda a,x is that block allocated? + tfr d,x Move addr to X + beq L0A70 no, return error + tst ,x this the page table? + bne L0A71 no, we can use this one +L0A70 coma set carry & return + rts +L0A71 stx R$Y,u save address of block + rts return + + +************************************************** +* System Call: F$All64 +* +* Function: Allocate a 64 byte memory block +* +* Input: X = Address of page table (0 if page table hasn't been allocated) +* +* Output: A = Block number +* X = Address of page table +* Y = Address of block +* +* Error: CC = C bit set; B = error code +* +* +FAll64 ldx R$X,u get base address of page table + bne L0A7F it's been allocated, skip ahead + bsr L0A89 allocate the page + bcs L0A88 error allocating, return + stx ,x save base address in page table + stx R$X,u save base address to caller's X +L0A7F bsr L0A9F find a empty spot in path table + bcs L0A88 couldn't find one, return error + sta R$A,u save block # + sty R$Y,u save address of block +L0A88 rts return + +* Allocate a new base page +* Exit: X=Ptr to newly allocated 256 byte page +L0A89 pshs u preserve register stack pointer + IFNE H6309 + ldq #$01000100 get block size (1 for SRqMem & 1 for TFM) + ELSE + ldd #$0100 + ENDC + os9 F$SRqMem request mem for it + leax ,u point to it + ldu ,s restore register stack pointer + stx ,s save pointer to new page on stack + bcs L0A9E error on allocate, return +* Clear freshly allocated page to 0's + IFNE H6309 + leay TFMNull,pc point to NULL byte + tfm y,x+ + ELSE + clrb +AllLoop clr ,x+ + decb + bne AllLoop + ENDC +L0A9E puls x,pc + + IFNE H6309 +TFMNull fcb 0 used to clear memory + ENDC + +* Search page table for a free 64 byte block +* Entry: X=Ptr to base page (the one with the 64 entry page index) +L0A9F pshs x,u preserve base page & register stack ptrs + clra Index entry #=0 +* Main search loop +L0AA2 pshs a Save which index entry we are checking + clrb Set position within page we are checking to 0 + lda a,x Is the current index entry used? + beq L0AB4 no, skip ahead + tfr d,y Yes, Move ptr to 256 byte block to Y + clra Clear offset for 64 byte blocks to 0 +L0AAC tst d,y Is this 64 byte block allocated? + beq L0AB6 No, skip ahead + addb #$40 Yes, point to next 64 byte block in page + bcc L0AAC If not done checking entire page, keep going + +* Index entry has a totally unused 256 byte page +L0AB4 orcc #Carry Set flag (didn't find one) +L0AB6 leay d,y + puls a Get which index entry we were checking + bcc L0AE1 If we found a blank entry, go allocate it + inca Didn't, move to next index entry + cmpa #64 Done entire index? + blo L0AA2 no, keep looking + + clra Yes, clear out to first entry +L0AC2 tst a,x Is this one used? + beq L0AD0 No, skip ahead + inca Increment index entry # + cmpa #64 Done entire index? + blo L0AC2 No, continue looking + + comb Done all of them, exit with Path table full error + ldb #E$PthFul + puls x,u,pc +* Found empty page +L0AD0 pshs x,a Preserve index ptr & index entry # + bsr L0A89 Allocate & clear out new 256 byte page + bcs L0AF0 If error,exit + leay ,x Point Y to start of new page + tfr x,d Also copy to D + tfr a,b Page # into B + puls x,a Get back index ptr & index entry # + stb a,x Save page # in proper index entry + clrb D=index entry #*256 + +* D = Block Address +L0AE1 equ * + IFNE H6309 + lsld ???Calculate 256 byte page #? + lsld + ELSE + aslb + rola + aslb + rola + ENDC + tfr y,u U=Ptr to start of new page + IFNE H6309 + ldw #$3f Clear out the 64 byte block we are using + leax TFMNull,pc + tfm x,u+ + ELSE + ldb #$3f +ClrIt clr ,u+ + decb + bne ClrIt + ENDC + sta ,y Save 256 byte page # as 1st byte of block + puls x,u,pc + +L0AF0 leas 3,s + puls x,u,pc + + +************************************************** +* System Call: F$Ret64 +* +* Function: Deallocate a 64 byte memory block +* +* Input: X = Address of page table +* A = Block number +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FRet64 lda R$A,u + ldx R$X,u + pshs u,y,x,d + clrb + tsta + beq L0B22 + IFNE H6309 + lsrd (Divide by 4) + lsrd + ELSE + lsra + rorb + lsra + rorb + ENDC + pshs a + lda a,x + beq L0B20 + tfr d,y + clr ,y + clrb + tfr d,u + clra +L0B10 tst d,u + bne L0B20 + addb #$40 + bne L0B10 + inca + os9 F$SRtMem + lda ,s + clr a,x +L0B20 clr ,s+ +L0B22 puls pc,u,y,x,d
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/ffmodul.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,132 @@ +* F$FModul entry point +FFModul pshs u preserve register stack pointer + lda R$A,u get module type + ldx R$X,u get pointer to name + ldy R$Y,u get pointer to DAT image of name (from caller) + bsr L068D go find it + puls y restore register stack pointer + std R$D,y save type & revision + stx R$X,y save updated name pointer + stu R$U,y save pointer to directory entry + rts return + +* Find module in module directory +* Entry: A=Module type +* X=Pointer to module name +* Y=DAT image pointer for module name +L068D equ * + IFNE H6309 + tfr 0,u init directory pointer to nothing + ELSE + ldu #$0000 + ENDC + pshs d,u preserve (Why B?) + bsr L0712 Go find 1st char of module name requested + cmpa #PDELIM Is it a '/'? + beq L070B yes, exit with error + lbsr L0741 parse the name to find the end & length + bcs L070E error (illegal name), exit + ldu <D.ModEnd get module directory end pointer + bra L0700 start looking for it + +* Main module directory search +* Entry: A=Module type +* B=Module name length +* X=Logical address of name in Caller's 64k space +* Y=DAT image of caller (for module name) +* U=Module directory Entry ptr (current module being checked) +L06A1 pshs d,x,y Preserve Mod type/nm len, Log. Addr, DAT Img ptr + pshs x,y Preserve Log. addr & DAT Img ptr + ldy MD$MPDAT,u Does the module have a DAT Image ptr? + beq L06F6 no, skip module + ldx MD$MPtr,u get module pointer + pshs x,y Save module ptr & DAT Img ptr of module + ldd #M$Name # bytes to go in to get module name ptr + lbsr L0B02 Go get the module name ptr + IFNE H6309 + addr d,x add it to module start + ELSE + leax d,x + ENDC + pshs x,y preserve module name ptr & DAT pointer + leax 8,s Point to addr of name we are searching for + ldb 13,s get name length + leay ,s point to module name name ptr within module DAT +* Stack: +* 0-1,s = Ptr to module name within Module DAT Img +* 2-3,s = Ptr to module's DAT Img +* 4-5,s = Ptr to module start +* 6-7,s = Ptr to module's DAT Img +* 8-9,s = Ptr to name we are looking for in caller's 64K space +* A-B,s = Ptr to caller's DAT Img +* C,s = Module type we are looking for (0=don't care) +* D,s = Length of module name +* E-F,s = Ptr to name we are looking for in caller's 64K space +* 10-11,s = Ptr to caller's DAT Img +* 12,s = Module type looking for +* 13,s = ??? (B from entry) +* 14-15,s = Module directory ptr (inited to 0) + lbsr L07DE compare the names + leas 4,s purge stack + puls y,x restore module pointer & DAT image + leas 4,s purge stack + bcs L06FE name didn't match, skip ahead + ldd #M$Type + lbsr L0B02 + sta ,s + stb $07,s + lda $06,s + beq L06ED + anda #TypeMask + beq L06E1 + eora ,s + anda #TypeMask + bne L06FE +L06E1 lda $06,s + anda #LangMask + beq L06ED + eora ,s + anda #LangMask + bne L06FE +L06ED puls y,x,d + abx + clrb + ldb 1,s + leas 4,s + rts + +L06F6 leas 4,s purge stack + ldd 8,s do we have a directory pointer? + bne L06FE yes, skip ahead + stu 8,s save directory entry pointer +L06FE puls d,x,y restore pointers +L0700 leau -MD$ESize,u move back 1 entry in module table + cmpu <D.ModDir at the beginning? + bhs L06A1 no, check entry + ldb #E$MNF get error code (module not found) + fcb $8C skip 2 bytes + +L070B ldb #E$BNam get error code + coma set carry for error +L070E stb 1,s save error code for caller + puls d,u,pc return + +* Skip spaces in name string & return first character of name +* Entry: X=Pointer to name +* Y=DAT image pointer +* Exit : A=First character of name +* B=DAT image block offset +* X=Logical address of name +L0712 pshs y preserve DAT image pointer +L0714 lbsr AdjBlk0 adjust pointer to offset for mapping in + lbsr L0AC8 map in block + leax 1,x + cmpa #C$SPAC space? + beq L0714 yes, eat it + leax -1,x move back to first character +L0720 pshs d,cc preserve char + tfr y,d copy DAT pointer to D + subd 3,s calculate DAT image offset + asrb divide it by 2 + lbsr CmpLBlk convert X to logical address in 64k map + puls cc,d,y,pc restore & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/ffork.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,144 @@ +************************************************** +* System Call: F$Fork +* +* Function: Starts a new child process +* +* Input: X = Address of module or filename +* Y = Parameter area size (256 byte pages) +* U = Address of parameter area +* A = Language/Type code +* B = Optional data area size (256 byte pages) +* +* Output: X = Updated past the name string +* A = Child's process ID +* +* Error: CC = C bit set; B = error code +* +FFork pshs u preserve register stack pointer + lbsr AllPrc setup a new process descriptor + bcc GotNPrc went ok, keep going + puls u,pc restore & return with error + +* Copy user # & priority +GotNPrc pshs u save pointer to new descriptor + ldx <D.Proc get current process pointer + IFNE H6309 + ldq P$User,x Get user # & priority from forking process + std P$User,u Save user # in new process + ste P$Prior,u Save priority in new process + ELSE + ldd P$User,x + std P$User,u + lda P$Prior,x + sta P$Prior,u + pshs x,u + ENDC +* Copy network I/O pointers to new descriptor + IFEQ Network-1 + pshs x,u preserve pointers to descriptors + leax >P$NIO,x point to current NIO pointers + leau >P$NIO,u point to buffer for new ones + IFNE H6309 + ldw #NefIOSiz get size + tfm x+,u+ move 'em + ELSE + ldb #NefIOSiz +L0250 lda ,x+ + sta ,u+ + decb + bne L0250 + ENDC + puls x,u restore pointers to descriptors + ENDC +* Copy I/O pointers to new descriptor + leax P$DIO,x + leau P$DIO,u + IFNE H6309 + ldw #DefIOSiz + tfm x+,u+ +* Copy Standard paths to new descriptor + lde #3 get # paths + ELSE + ldb #DefIOSiz +L0261 lda ,x+ + sta ,u+ + decb + bne L0261 + ldy #3 + ENDC + +* Duplicate 1st 3 paths +GetOPth lda ,x+ get a path # + beq SveNPth don't exist, go on + os9 I$Dup dupe it + bcc SveNPth no error, go on + clra clear it + +* As std in/out/err +SveNPth sta ,u+ save new path # + IFNE H6309 + dece done? + ELSE + leay -1,y + ENDC + bne GetOPth no, keep going +* Link to new module & setup task map + ldx ,s get pointer to new descriptor + ldu 2,s get pointer to register stack + lbsr L04B1 link to module & setup register stack + bcs L02CF exit if error + pshs d + os9 F$AllTsk allocate the task & setup MMU + bcs L02CF Error, skip ahead + +* Copy parameters to new process + lda P$PagCnt,x get memory page count + clrb + subd ,s calculate destination + tfr d,u set parameter destination pointer + ldb P$Task,x get source task # + ldx <D.Proc get destination task # + lda P$Task,x + leax ,y point to parameters + puls y restore parameter count + os9 F$Move move parameters to new process + +* Setup the new stack + ldx ,s get pointer to process descriptor + lda <D.SysTsk get task # + ldu P$SP,x get new stack pointer + leax >(P$Stack-R$Size),x point to register stack + ldy #R$Size get size of register stack + os9 F$Move move the register stack over + puls u,x + os9 F$DelTsk + ldy <D.Proc + lda P$ID,x + sta R$A,u + ldb P$CID,y + sta P$CID,y + lda P$ID,y + std P$PID,x + IFNE H6309 + aim #^SysState,P$State,x switch to non-system state + ELSE + lda P$State,x + anda #^SysState + sta P$State,x + ENDC +* Put date & time of creation into descriptor +* pshs x preserve process pointer +* leax P$DatBeg,x point to time buffer +* os9 F$Time put date/time into it +* puls x restore pointer + os9 F$AProc and start the process + rts return + +* Fork error goes here +L02CF puls x + pshs b save error + lbsr L05A5 close paths & unlink mem + lda P$ID,x get bad ID + lbsr L0386 delete proc desc & task # + comb set carry + puls pc,u,b pull error code & u & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/ffreehb.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,84 @@ +* F$FreeHB entry point (Called from F$MapBlk - called from SS.MpGPB) +FFreeHB ldb R$B,u Get # blocks requested + ldy R$Y,u Get DAT Img ptr + bsr L0A31 Go find free blocks in high part of DAT +L0A2C bcs L0A30 Couldn't find any, exit with error + sta R$A,u Save starting block # +L0A30 rts Return + +L0A31 tfr b,a Copy # blocks requested to A +* This gets called directly from within F$Link +L0A33 suba #$09 Invert within 8 + nega + pshs x,d Save X, block # & block count + ldd #$FFFF -1' +L0A56 pshs d + +* Move to next block - SHOULD OPTOMIZE WITH W +L0A58 clra # free blocks found so far=0 + ldb 2,s Get block # + addb ,s Add block increment (point to next block) + stb 2,s Save new block # to check + cmpb 1,s Same as block count? + bne L0A75 No, skip ahead + ldb #E$MemFul Preset error for 207 (Process mem full) + cmpy <D.SysDAT Is it the system process? + bne L0A6C No, exit with error 207 + ldb #E$NoRam System Mem full (237) +L0A6C stb 3,s Save error code + comb set carry + bra L0A82 Exit with error + +L0A71 tfr a,b Copy # blocks to B + addb 2,s Add to current start block # +L0A75 lslb Multiply block # by 2 + ldx b,y Get DAT marker for that block + cmpx #DAT.Free Empty block? + bne L0A58 No, move to next block + inca Bump up # blocks free counter + cmpa 3,s Have we got enough? + bne L0A71 No, keep looking +L0A82 leas 2,s Eat temporary stack + puls d,x,pc Restore reg, error code & return + +* F$FreeLB entry point (WHERE DOES THIS EVER GET CALLED FROM???) +FSFreeLB ldb R$B,u Get block count + ldy R$Y,u Get ptr to DAT Image + bsr L0A4B Go find block #'s + bra L0A2C Do error checking & exit (since never called, +* not worried about speed) + +L0A4B lda #$FF Value to start loop at block 0 + pshs x,d Preserve X,flag & block count +* lda #$01 # to add to go to next block (positive here) + nega -(-1)=+1 + subb #9 Drop block count to -8 to -1 (invert within 8) + negb Negate so it is a positive # again + bra L0A56 Go into main find loop + +* F$FreLB entry point +FFreeLB ldd R$D,u + ldx R$X,u + ldu R$U,u +L0A8C pshs d,x,y,u + leay <P$DATImg,x + lsla + leay a,y + IFNE H6309 + clra + lslb + tfr d,w + tfm u+,y+ + oim #ImgChg,P$State,x + ELSE +L0ALoop ldx ,u++ + stx ,y++ + decb + bne L0ALoop + ldx 2,s get proc desc ptr + lda P$State,x + ora #ImgChg + sta P$State,x + ENDC + clrb + puls d,x,y,u,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fgblkmp.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,14 @@ +* F$GBlkMp entry point +FGBlkMp ldd #DAT.BlSz # bytes per MMU block (8k) + std R$D,u Put into caller's D register + ldd <D.BlkMap+2 Get end of system block map ptr + subd <D.BlkMap Subtract start of system block map ptr + std R$Y,u Store size of system block map in caller's Y reg. + tfr d,y + lda <D.SysTsk Get system task # + ldx <D.Proc Get caller's task # + ldb P$Task,x get task # of caller + ldx <D.BlkMap Get start ptr of system block map +L0978 ldu R$X,u Get addr to put it that caller requested + os9 F$Move Move it into caller's space + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fgcmdir.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,95 @@ +* F$GCMDir entry point +* +* This system call is only used by OS9p1 to get rid of all the empty spaces +* in the module directory to keep it small & compact. +FGCMDir ldx <D.ModDir get pointer to module directory start + bra L0C1D skip ahead +L0C17 ldu MD$MPDAT,x DAT initialized? + beq L0C23 no it's empty skip ahead + leax MD$ESize,x move to next entry +L0C1D cmpx <D.ModEnd end of module directory? + bne L0C17 no, keep looking + bra L0C4B +* Move all entrys up 1 slot in directory +L0C23 tfr x,y move empty entry pointer to Y + bra L0C2B +L0C27 ldu MD$MPDAT,y + bne L0C34 +L0C2B leay MD$ESize,y + cmpy <D.ModEnd done complete directory? + bne L0C27 no, keep going + bra L0C49 +* Move entry up 1 slot in directory +L0C34 equ * + IFNE H6309 + ldw #MD$ESize + tfm y+,x+ + ELSE + ldu ,y++ + stu ,x++ + ldu ,y++ + stu ,x++ + ldu ,y++ + stu ,x++ + ldu ,y++ + stu ,x++ + ENDC +L0C44 cmpy <D.ModEnd done complete directory? + bne L0C27 no, keep going + +L0C49 stx <D.ModEnd save new module directory end pointer +* Shrink DAT table +L0C4B ldx <D.ModDir+2 get module directory DAT end pointer + bra L0C53 + +L0C4F ldu ,x + beq L0C5B +L0C53 leax -2,x Bump module ptr down by 2 + cmpx <D.ModDAT Hit beginning yet? + bne L0C4F No, keep checking + clrb Yes, return without error + rts + +L0C5B ldu -2,x + bne L0C53 + tfr x,y + bra L0C67 + +L0C63 ldu ,y + bne L0C70 +L0C67 leay -2,y +L0C69 cmpy <D.ModDAT + bcc L0C63 + bra L0C81 +L0C70 leay 2,y + ldu ,y + stu ,x +L0C76 ldu ,--y + stu ,--x + beq L0C87 + cmpy <D.ModDAT + bne L0C76 + +L0C81 stx <D.ModDAT + bsr L0C95 + clrb Yes, return without error + rts + +L0C87 leay 2,y + leax 2,x + bsr L0C95 + leay -4,y + leax -2,x + bra L0C69 + +* Update Module Dir Image Ptrs +L0C95 pshs u + ldu <D.ModDir + bra L0CA4 +L0C9B cmpy MD$MPDAT,u same DAT ptrs? + bne L0CA2 no, skip + stx MD$MPDAT,u else update ptrs +L0CA2 leau MD$ESize,u next entry +L0CA4 cmpu <D.ModEnd last entry? + bne L0C9B no + puls u,pc else yes... return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fgmoddr.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,24 @@ +* F$GModDr entry point +FGModDr ldd <D.ModDir+2 Get end ptr of module directory + subd <D.ModDir Calculate maximum size of module directory + tfr d,y Put max. size in Y + ldd <D.ModEnd Get real end ptr of module dir + subd <D.ModDir Calculate real size of module dir + ldx R$X,u Get requested buffer ptr to put it from caller + IFNE H6309 + addr d,x Calculate end addr. of directory after its copied + ELSE + leax d,x + ENDC + stx R$Y,u Preserve in caller's Y register + ldx <D.ModDir Get start ptr of module directory + stx R$U,u Preserve in caller's U register + + lda <D.SysTsk Get system task # + ldx <D.Proc Get current process task # + ldb P$Task,x + ldx <D.ModDir Get start ptr of module directory + bra L0978 --- saves 4 bytes, adds 3 cycles +*** ldu R$X,u Get caller's buffer ptr +*** os9 F$Move Copy module directory in caller's buffer +*** rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fgprdsc.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,12 @@ +* F$GPrDsc entry point +FGPrDsc ldx <D.Proc Get current process dsc. ptr. + ldb P$Task,x Get task number + lda R$A,u Get requested process ID # + os9 F$GProcP Get ptr to process to descriptor + bcs L0962 Error, exit with it + lda <D.SysTsk Get system task # + leax ,y Point X to the process descriptor + ldy #P$Size Y=Size of process descriptor (512 bytes) + ldu R$X,u Get requested place to put copy of process dsc. + os9 F$Move Move it into caller's space +L0962 rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fgprocp.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,25 @@ +* F$GProcP entry point +FGProcP lda R$A,u get process # + bsr L0B2E Get ptr to process descriptor + bcs L0B2D If error, exit with it + sty R$Y,u Save ptr in caller's Y +L0B2D rts Return + +* Entry: A=Process # +* Exit: Y=Ptr to process descriptor +* All others preserved +L0B2E pshs d,x Preserve regs + ldb ,s Get process # into B + beq L0B40 0, skip ahead + ldx <D.PrcDBT Get ptr to process descriptor block table + abx Point to specific process' entry + lda ,x Get MSB of process dsc. ptr + beq L0B40 None there, exit with error + clrb Clear LSB of process dsc. ptr (always fall on $200 + tfr d,y boundaries) & move ptr to Y + puls d,x,pc Restore regs & return + +L0B40 puls d,x Get regs back + comb Exit with Bad process ID error + ldb #E$BPrcID + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/ficpt.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,25 @@ +************************************************** +* System Call: F$Icpt +* +* Function: Sets the function to be called when a signal arrives. +* +* +* Input: X = Address of intercept routine +* U = Address of intercept routine data area +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FIcpt ldx <D.Proc get current process pointer + ldd R$X,u Get vector for signal trap handler + IFNE H6309 + ldw R$U,u Get data area ptr for signal trap handler + stq P$SigVec,x Save them in descriptor + ELSE + std P$SigVec,x + ldd R$U,u + std P$SigDat,x + ENDC + clrb clear errors + rts return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fid.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,19 @@ +************************************************** +* System Call: F$ID +* +* Function: Return's caller's process ID +* +* Input: None +* +* Output: A = Caller's process ID +* Y = User ID +* +* Error: CC = C bit set; B = error code +* +FID ldx <D.Proc get current process pointer + lda P$ID,x get ID + sta R$A,u save it + ldd P$User,x get user # + std R$Y,u save it + clrb clear error + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fld.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,71 @@ +* F$LDAXY entry point +FLDAXY ldx R$X,u Get offset within block (S/B $0000-$1FFF) + ldy R$Y,u Get ptr to DAT block entry + bsr L0AC8 Go get byte + sta R$A,u Save in caller's A reg. + rts + +* Entry: X=offset ($0000-$1fff) to get from block pointed to by Y (DAT entry +* format) +L0AC8 lda 1,y Get MMU block # to get data from + clrb Clear carry/setup for STB + pshs cc Preserve interrupt status/settings + orcc #IntMasks shut IRQ's off + sta >$FFA0 Map block into $0000-$1FFF + brn L0AC8 + lda ,x Get byte + stb >$FFA0 Map block 0 into $0000-$1FFF + fdb $21ED + puls pc,cc Get interrupt status/(or turn on) & return + +* Get 1st byte of LDDDXY - also used by many other routines +* Increments X on exit; adjusts X for within 8K block & Y (DAT img ptr) +LDAXY lda 1,y Get MMU block # + pshs b,cc + clrb + orcc #IntMasks Shut off interrupts + sta >$FFA0 Map in MMU block into slot 0 + lda ,x+ Get byte + stb >$FFA0 +* clr >$FFA0 Map in MMU block #0 into slot 0 +* andcc #^IntMasks + puls b,cc + bra AdjBlk0 + +L0AEA leax >-DAT.BlSz,x Bump offset ptr to start of block again + leay 2,y Bump source MMU block up to next on in DAT Image +AdjBlk0 cmpx #DAT.BlSz Going to wrap out of our block? + bhs L0AEA Yes, go adjust + rts No, return + +* F$LDDDXY entry point +FLDDDXY ldd R$D,u Get offset to offset within DAT Image + leau R$X,u Point U to Offset + pulu x,y Y=Offset within DAT Image, X=DAT Image ptr + bsr L0B02 Go get 2 bytes + std -(R$X+3),u Save into caller's X + clrb No error & return + rts +* Get 2 bytes for LDDDXY (also called by other routines) +* Should simply map in 2 blocks, and do a LDD (don't have to worry about wrap) +L0B02 pshs u,y,x Preserve regs + IFNE H6309 + addr d,x Point X to X+D + ELSE + leax d,x + ENDC + bsr AdjBlk0 Wrap address around for 1 block + ldu <D.SysDAT Get sys DAT Image ptr +* lda 1,u Get MMU block #0 + clra system block 0 =0 always + ldb 3,u Get MMU block #1 + tfr d,u make U=blocks to re-map in once done + lda 1,y Get MMU block #0 + ldb 3,y Get MMU block #1 + pshs cc Preserve int. status + orcc #IntMasks shut off int. + std >$FFA0 Map in both blocks + ldd ,x Get 2 bytes + stu >$FFA0 Map original blocks in +* tfr y,w Restore W + puls pc,u,y,x,cc Restore regs & return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fldabx.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,47 @@ +* F$LDABX entry point +FLDABX ldb R$B,u Get task # to get byte from + ldx R$X,u Get offset into task's DAT image to get byte from +*** bsr L0C40 Go get the byte into B +* Load a byte from another task +* Entry: B=Task # +* X=Pointer to data +* Exit : B=Byte from other task +L0C40 pshs cc,a,x,u + bsr L0BF5 + ldd a,u + orcc #IntMasks + stb >$FFA0 + ldb ,x + clr >$FFA0 + puls cc,a,x,u + + stb R$A,u Save into caller's A & return + clrb set to no errors + rts + +* Get pointer to task DAT image +* Entry: B=Task # +* Exit : U=Pointer to task image +*L0C09 ldu <D.TskIPt get pointer to task image table +* lslb multiply task # by 2 +* ldu b,u get pointer to task image (doesn't affect carry) +* rts restore & return + +* F$STABX entry point +FSTABX ldd R$D,u + ldx R$X,u +* Store a byte in another task +* Entry: A=Byte to store +* B=Task # + +* X=Pointer to data +L0C28 andcc #^Carry + pshs cc,d,x,u + bsr L0BF5 calculate offset into DAT image + ldd a,u get memory block + lda 1,s + orcc #IntMasks + stb >$FFA0 + sta ,x + clr >$FFA0 + puls cc,d,x,u,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/flink.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,148 @@ +* F$SLink entry point +* Entry: U=Register stack pointer +FSLink ldy R$Y,u get DAT image pointer of name + bra L0398 skip ahead + +* F$ELink entry point +* Entry: U=Register stack pointer +FELink pshs u preserve register stack pointer + ldb R$B,u get module type + ldx R$X,u get pointer to module directory entry + bra L03AF skip ahead + + +************************************************** +* System Call: F$Link +* +* Function: Link to a memory module +* +* Input: X = Address of module name +* A = Type/Language byte +* +* Output: X = Advanced past module name +* Y = Module entry point address +* U = Module header address +* A = Module type/language byte +* B = Module attributes/revision byte +* +* Error: CC = C bit set; B = error code +* +FLink ldx <D.Proc get pointer to DAT image + leay P$DATImg,x point to process DAT image +L0398 pshs u preserve register stack pointer + ldx R$X,u get pointer to path name + lda R$A,u get module type + lbsr L068D search module directory + bcs L041E not there, exit with error + leay ,u point to module directory entry + ldu ,s get register stack pointer + stx R$X,u save updated module name pointer + std R$D,u save type/language + leax ,y point to directory entry +L03AF bitb #ReEnt is it re-entrant? + bne L03BB yes, skip ahead + ldd MD$Link,x is module busy? + beq L03BB no, go link it + ldb #E$ModBsy return module busy error + bra L041E return +L03BB ldd MD$MPtr,x get module pointer + pshs d,x preserve that & directory pointer + ldy MD$MPDAT,x get module DAT image pointer + ldd MD$MBSiz,x get block size + addd #$1FFF round it up + tfr a,b + lsrb + lsrb + lsrb + lsrb + lsrb +* adda #$02 + lsra + inca instead of adda #2, above + lsra + lsra + lsra + lsra + pshs a + leau ,y point to module DAT image + bsr L0422 is it already linked in process space? + bcc L03EB yes, skip ahead + lda ,s + lbsr L0A33 find free low block in process DAT image + bcc L03E8 found some, skip ahead + leas 5,s purge stack + bra L041E return error + +L03E8 lbsr L0A8C copy memory blocks into process DAT image +L03EB ldb #P$Links point to memory block link counts + abx smaller and faster than leax P$Links,x + sta ,s Save block # on stack + lsla account for 2 bytes/entry + leau a,x Point to block # we want + ldd ,u Get link count for that block + IFNE H6309 + incd Bump up by 1 + ELSE + addd #$0001 + ENDC + beq L03FC If wraps to 0, leave at $FFFF + std ,u Otherwise, store new link count +L03FC ldu $03,s + ldd MD$Link,u + IFNE H6309 + incd + ELSE + addd #$0001 + ENDC + beq L0406 + std MD$Link,u +L0406 puls b,x,y,u + lbsr CmpLBlk + stx R$U,u + ldx MD$MPtr,y + ldy ,y + ldd #M$Exec get offset to execution address + lbsr L0B02 get execution offset + addd R$U,u add it to start of module + std R$Y,u set execution entry point + clrb No error & return + rts + +L041E orcc #Carry Error & return + puls u,pc + +L0422 ldx <D.Proc get pointer to current process + leay P$DATImg,x point to process DAT image + clra + pshs d,x,y + subb #DAT.BlCt + negb + lslb + leay b,y + IFNE H6309 +L0430 ldw ,s Get counter + ELSE +L0430 ldx ,s + ENDC + pshs u,y +L0434 ldd ,y++ + cmpd ,u++ + bne L0449 + IFNE H6309 + decw Dec counter + ELSE + leax -1,x + ENDC + bne L0434 If not done, keep going + puls d,u + subd 4,s + lsrb + stb ,s + clrb + puls d,x,y,pc Restore regs & return + +L0449 puls u,y + leay -2,y + cmpy 4,s + bcc L0430 + puls d,x,y,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fmapblk.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,36 @@ +* F$MapBlk entry point +FMapBlk lda R$B,u get # blocks + beq L0BAA can't map 0 blocks, return error + cmpa #DAT.BlCt within range of DAT image? + bhi L0BAA no, return error + leas -$10,s make a buffer to hold DAT image + ldx R$X,u get start block # + ldb #1 block increment value +* Change to W 05/19/93 - used W since one cycle faster per block + tfr s,w point to buffer +FMapBlk2 stx ,w++ save block # to buffer + abx Next block + deca done? + bne FMapBlk2 no, keep going + ldb R$B,u get block count again + ldx <D.Proc get process pointer + leay <P$DATImg,x point to DAT image + os9 F$FreeHB find the highest free block offset + bcs L0BA6 no room, return error + tfr d,w Preserve start block # & # of blocks + lsla Multiply start block # by 32 + lsla + lsla + lsla + lsla + clrb + std R$U,u save address of first block + tfr w,d Restore offset + leau ,s move DAT image into process descriptor + os9 F$SetImg Change process dsc to reflect new blocks +L0BA6 leas <$10,s Eat DAT image copy & return + rts + +L0BAA comb Illegal Block address error + ldb #E$IBA + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fmem.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,77 @@ +************************************************** +* System Call: F$Mem +* +* Function: Resize data memory area +* +* Input: D = Desired memory area (in bytes) +* +* Output: Y = Address of new memory area upper bound +* D = New memory area size in bytes +* +* Error: CC = C bit set; B = error code +* +FMem ldx <D.Proc get current process pointer + ldd R$D,u get requested memory size + beq L0638 he wants current size, return it + addd #$00FF round up to nearest page + bcc L05EE no overflow, skip ahead + ldb #E$MemFul get mem full error + rts return + +L05EE cmpa P$PagCnt,x match current page count? + beq L0638 yes, return it + pshs a save page count + bhs L0602 he's requesting more, skip ahead + deca subtract a page + ldb #($100-R$Size) get size of default stack - R$Size + cmpd P$SP,x shrinking it into stack? + bhs L0602 no, skip ahead + ldb #E$DelSP get error code (223) + bra L0627 return error +L0602 lda P$PagCnt,x get page count + adda #$1F round it up + lsra divide by 32 to get block count + lsra + lsra + lsra + lsra + ldb ,s + addb #$1F + bcc L0615 still have room, skip ahead + ldb #E$MemFul + bra L0627 +L0615 lsrb divide by 32 to get block count + lsrb + lsrb + lsrb + lsrb + IFNE H6309 + subr a,b same count? + ELSE + pshs b + suba ,s+ + ENDC + beq L0634 yes, save it + bcs L062C overflow, delete the ram we just got + os9 F$AllImg allocate the image in DAT + bcc L0634 no error, skip ahead +L0627 leas 1,s purge stack +L0629 orcc #Carry set carry for error + rts return + +L062C equ * + IFNE H6309 + addr b,a + ELSE + pshs a + addb ,s+ + ENDC + negb + os9 F$DelImg +L0634 puls a restore requested page count + sta P$PagCnt,x save it into process descriptor +L0638 lda P$PagCnt,x get page count + clrb clear LSB + std R$D,u save mem byte count to caller + std R$Y,u save memory upper limit to caller + rts return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fmove.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,195 @@ +* F$Move entry point +* Entry: U=Register stack pointer +FMove ldd R$D,u get source & destination task #'s +L0B25 ldy R$Y,u Get # bytes to move + beq L0A01 None, exit without error + ldx R$X,u get source pointer + ldu R$U,u get destination pointer + +L0B2C pshs d,x,y,u preserve it all + pshs d,y save task #'s & byte count + tfr a,b copy source task to B + lbsr L0BF5 calculate block offset of source + leay a,u point to block + pshs x,y save source pointer & DAT pointer of source + ldb 9,s get destination task # + ldx 14,s get destination pointer + lbsr L0BF5 calculate block offset + leay a,u point to block + pshs x,y save dest. pointer & DAT pointer to dest. +* try ldq #$20002000/ subr x,w / pshsw (+3), take out ldd (-3) + ldd #DAT.BlSz get block size + subd ,s take off offset + pshs d preserve + ldd #DAT.BlSz init offset in block + subd 6,s + pshs d save distance to end?? + ldx 8,s get source pointer + leax -$6000,x make X point to where we'll map block ($a000) + ldu 4,s get destination pointer + leau -$4000,u make U point to where we'll map block ($c000) + ldy <D.SysDAT Get ptr to system DAT image + lda 11,y Get MMU block #5 + ldb 13,y Get MMU block #6 + tfr d,y Move to Y since unused in loop below +* Main move loop +* Stack: 0,s=distance to end of source block +* 2,s=distance to end of destination block +* 4,s=pointer to destination +* 6,s=pointer to destination DAT image +* 8,s=pointer to source +* 10,s=pointer to source DAT image +* 12,s=task # of source +* 13,s=task # of destination +* 14,s=total byte count of move +* Registers: X=Source pointer +* U=Destination pointer +L0B6A equ * + IFNE H6309 + ldd [<6,s] [B]=Block # of source + ldw [<10,s] [A]=Block # of destination + tfr f,a +* Calculate move length for this pass + ldw 14,s get full byte count + cmpw ,s we gonna overlap source? + bls L0B82 no, skip ahead + ldw ,s get remaining bytes in source block +L0B82 cmpw 2,s we gonna overlap destination? + bls L0B89 no, skip ahead + ldw 2,s get remaining bytes in destination block +L0B89 cmpw #$0100 less than 128 bytes? + bls L0B92 yes, skip ahead + ldw #$0100 force to 128 bytes +L0B92 stw 12,s save count + orcc #IntMasks Shut off interrupts + std >$FFA5 map in the blocks + tfm x+,u+ Copy up to 128 bytes + sty >$FFA5 Restore system blocks 5&6 to normal + andcc #^IntMasks + ldd 14,s get full count + subd 12,s done? + beq L0BEF yes, return + std 14,s save updated count + ldd ,s get current offset in block + subd 12,s need to switch source block? + bne L0BD7 no, skip ahead + lda #$20 B=0 from 'bne' above + subr d,x reset source back to begining of block + inc 11,s add 2 to source DAT pointer + inc 11,s +L0BD7 std ,s save updated source offset in block + ldd 2,s get destination offset + subd 12,s need to switch destination block? + bne L0BEA no, skip ahead + lda #$20 B=0 from 'bne', above + subr d,u reset destination back to beginning of block + inc 7,s add 2 to destination DAT pointer + inc 7,s +L0BEA std 2,s save updated destination offset in block + bra L0B6A go do next block +* Block move done, return +L0BEF leas 16,s purge stack +L0BF2 clrb clear errors + puls d,x,y,u,pc return + ELSE +L0BXA pshs cc + ldd [<$07,s] + pshs b + ldd [<$0C,s] + pshs b + ldd <$11,s + cmpd $03,s + bls L0B82 + ldd $03,s +L0B82 cmpd $05,s + bls L0B89 + ldd $05,s +L0B89 cmpd #$0040 + bls L0B84 + ldd #$0040 +L0B84 std $0F,s + puls y + orcc #IntMasks + sty >$FFA5 + andb #$07 + beq L0B99 +L0B92 lda ,x+ + sta ,u+ + decb + bne L0B92 +L0B99 ldb $0E,s + lsrb + lsrb + lsrb + beq L0BBC + pshs b + exg x,u +L0BA4 pulu y,b,a + std ,x + sty $02,x + pulu y,b,a + std $04,x + sty $06,x + leax $08,x + dec ,s + bne L0BA4 + leas $01,s + exg x,u +L0BBC ldy <D.SysDAT + lda $0B,y + ldb $0D,y + std >$FFA5 + puls cc + ldd $0E,s + subd $0C,s + beq L0BEF + std $0E,s + ldd ,s + subd $0C,s + bne L0BD7 + ldd #DAT.BlSz + leax >-DAT.BlSz,x + inc $0B,s + inc $0B,s +L0BD7 std ,s + ldd $02,s + subd $0C,s + bne L0BEA + ldd #DAT.BlSz + leau >-DAT.BlSz,u + inc $07,s + inc $07,s +L0BEA std $02,s + lbra L0BXA +L0BEF leas <$10,s +L0BF2 clrb + puls pc,u,y,x,b,a + ENDC +L0BF3 tfr u,y save a copy of U for later +* Calculate offset within DAT image +* Entry: B=Task # +* X=Pointer to data +* Exit : A=Offset into DAT image +* X=Offset within block from original pointer +* Possible bug: No one ever checks if the DAT image, in fact, exists. +L0BF5 ldu <D.TskIPt get task image ptr table + lslb + ldu b,u get ptr to this task's DAT image + tfr x,d copy logical address to D + anda #%11100000 Keep only which 8K bank it's in + beq L0C07 Bank 0, no further calcs needed + clrb force it to start on an 8K boundary + IFNE H6309 + subr d,x now X=offset into the block + ELSE + pshs d + tfr x,d + subd ,s++ + tfr d,x + ENDC + lsra Calculate offset into DAT image to get proper + lsra 8K bank (remember that each entry in a DAT image + lsra is 2 bytes) + lsra +L0C07 rts +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fnproc.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,102 @@ +************************************************** +* System Call: F$NProc +* +* Function: Start the next process in the active queue +* +* Input: None +* +* Output: Control does not return to the caller +* +FNProc ldx <D.SysPrc get system process descriptor + stx <D.Proc save it as current + lds <D.SysStk get system stack pointer + andcc #^IntMasks re-enable IRQ's (to allow pending one through) + fcb $8C skip the next 2 bytes + +L0D91 cwai #^IntMasks re-enable IRQ's and wait for one +L0D93 orcc #IntMasks Shut off interrupts again + lda #Suspend get suspend suspend state flag + ldx #D.AProcQ-P$Queue For start of loop, setup to point to current process + +* Loop to find next active process that is not Suspended +L0D9A leay ,x Point y to previous link (process dsc. ptr) + ldx P$Queue,y Get process dsc. ptr for next active process + beq L0D91 None, allow any pending IRQ thru & try again + bita P$State,x There is one, is it Suspended? + bne L0D9A Yes, skip it & try next one + +* Found a process in line ready to be started + ldd P$Queue,x Get next process dsc. ptr in line after found one + std P$Queue,y Save the next one in line in previous' next ptr + stx <D.Proc Make new process dsc. the current one + lbsr L0C58 Go check or make a task # for the found process + bcs L0D83 Couldn't get one, go to next process in line + lda <D.TSlice Reload # ticks this process can run + sta <D.Slice Save as new tick counter for process + ldu P$SP,x get the process stack pointer + lda P$State,x get it's state + lbmi L0E29 If in System State, switch to system task (0) +L0DB9 bita #Condem Was it condemned by a deadly signal? + bne L0DFD Yes, go exit with Error=the signal code # + lbsr TstImg do a F$SetTsk if the ImgChg flag is set +L0DBD ldb <P$Signal,x any signals? + beq L0DF7 no, go on + decb is it a wake up signal? + beq L0DEF yes, go wake it up + leas -R$Size,s make a register buffer on stack + leau ,s point to it + lbsr L02CB copy the stack from process to our copy of it + lda <P$Signal,x get last signal + sta R$B,u save it to process' B + + ldd <P$SigVec,x any intercept trap? + beq L0DFD no, go force the process to F$Exit + std R$PC,u save vector to it's PC + ldd <P$SigDat,x get pointer to intercept data area + std R$U,u save it to it's U + ldd P$SP,x get it's stack pointer + subd #R$Size take off register stack + std P$SP,x save updated SP + lbsr L02DA Copy modified stack back overtop process' stack + leas R$Size,s purge temporary stack +L0DEF clr <P$Signal,x clear the signal + +* No signals go here +L0DF7 equ * + IFNE H6309 + oim #$01,<D.Quick + ELSE + ldb <D.Quick + orb #$01 + stb <D.Quick + ENDC +BackTo1 equ * +L0DF2 ldu <D.UsrSvc Get current User's system call service routine ptr + stu <D.XSWI2 Save as SWI2 service routine ptr + ldu <D.UsrIRQ Get IRQ entry point for user state + stu <D.XIRQ Save as IRQ service routine ptr + + ldb P$Task,x get task number + lslb 2 bytes per entry in D.TskIpt + ldy P$SP,x get stack pointer + lbsr L0E8D re-map the DAT image, if necessary + + ldb <D.Quick get quick return flag + bra L0E4C Go switch GIME over to new process & run + +* Process a signal (process had no signal trap) +L0DFD equ * + IFNE H6309 + oim #SysState,P$State,x Put process into system state + ELSE + ldb P$State,x + orb #SysState + stb P$State,x + ENDC + leas >P$Stack,x Point SP to process' stack + andcc #^IntMasks Turn interrupts on + ldb <P$Signal,x Get signal that process received + clr <P$Signal,x Clear out the one in process dsc. + os9 F$Exit Exit with signal # being error code + +L0E45 jmp [>D.Poll] Call IOMAN for IRQ polling
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fprsnam.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,97 @@ +************************************************** +* System Call: F$PrsNam +* +* Function: Parse a path name +* +* Input: X = Address of pathlist +* +* Output: X = Updated past optional "/" character +* Y = Address of last character of pathlist + 1 +* B = Length of pathlist +* +* Error: CC = C bit set; B = error code +* +* Modification to allow '-' in filenames by WG +* +FPrsNam ldx <D.Proc proc desc + leay <P$DATImg,x Y=DAT image ptr + ldx R$X,u X=name string + bsr L0741 get it and length + std R$D,u return length in D + bcs L073E ..err + stx R$X,u and X at name begin + abx plus len +L073E stx R$Y,u return Y=end of name ptr + rts end. + +* Parse name +L0741 pshs y save DAT image pointer + lbsr AdjBlk0 go find map block... + pshs x,y save X offset within block and Y block pointer + bsr GoGetAXY go get byte at X in block Y... + + cmpa #'. is the first character a period? + bne IsSlash no, do proper first character checking + lbsr L0AC8 do a LDAXY, without changing X or Y + bsr ChkFirst is the next character non-period? + lda #'. restore the period character the LDAXY destroyed + bcc Do.Loop if NON-period character, skip 1st char checks + +IsSlash cmpa #'/ is it a slash? + bne NotSlash no, go keep X offset and block Y... + bsr GetChar go get character... +NotSlash bsr ChkFirst go check if valid first character... + bcs NotValid not valid, go get next name start offset in X... +Do.Loop clrb initialize character counter +LastLoop incb add one character + tsta last character in name string? + bmi LastChar yes, go return valid... + bsr GoGetAXY go get next character... + bsr ChkValid go check if valid character... + bcc LastLoop valid, go check if last character... +LastChar andcc #^Carry + bra RtnValid + +GetChar stx 2,s save current offset over old offset + sty 4,s save current block pointer over old block pointer +GoGetAXY lbra LDAXY go get byte at X in block Y in A, & return + +NextLoop bsr GetChar go get character... +NotValid cmpa #', comma? + beq NextLoop yes, go get next character... + cmpa #C$SPAC space? + beq NextLoop yes, go get next character... + comb error, set Carry + ldb #E$BNam 'Bad Name' error +RtnValid puls x,y recover offset & pointer + bra L0720 go do a similar exit routine + +ChkFirst pshs a save character + anda #$7F drop msbit + bra ChkRst skip dash for first character check + +ChkValid pshs a save character + anda #$7F drop msbit + cmpa #'. period? + beq ValidChr yes, go return valid character... +ChkRest cmpa #'- is it a dash? + beq ValidChr yes, it's valid +ChkRst cmpa #'z greater than "z"? + bhi InvalidC yes, go return invalid character... + cmpa #'a greater than or equal to "a"? + bhs ValidChr yes, go return valid character... + cmpa #'_ underscore? + beq ValidChr yes, go return valid character... + cmpa #'Z greater than "Z"? + bhi InvalidC yes, go return invalid character... + cmpa #'A greater than or equal to "A"? + bhs ValidChr yes, go return valid character... + cmpa #'9 greater than "9"? + bhi InvalidC yes, go return invalid character... + cmpa #'0 greater than or equal to "0"? + bhs ValidChr yes, go return valid character... + cmpa #'$ dollar symbol? + beq ValidChr yes, go return valid character... +InvalidC coma invalid character, set carry +ValidChr puls a,pc +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/freboot.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,32 @@ +****************************************************** +* F$ReBoot entry point +* Currently disabled (doesn't work) +* Besides, there's no need for this code to be in system memory. +* A user-mode program can do this just as well. +* +* Entry A = 0 Cold ReBoot +* = 1 Quit to RSDOS +* +*ReBoot equ * +* orcc #Carry Set error flag +* rts Exit +* tst R$A,u Cold start (a=0) +* bne WarmBt no, attempt a warm boot +*WarmBt orcc #IntMasks +* ldb #CodeSize +* leax BootCode,pc +* tfr 0,y +*BootLoop lda ,x+ +* sta ,y+ +* decb +* bne BootLoop +* jmp >$0000 +*BootCode equ * +* lda >$ffa8 +* sta >$ffa0 +* clra +* sta >$ff90 +* sta >$ff91 +* jmp >$ed5f +*CodeSize equ *-BootCode +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsend.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,134 @@ +************************************************** +* System Call: F$Send +* +* Function: Send a signal to a process +* +* Input: A = Receiver's process ID +* B = Signal code +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FSend ldx <D.Proc get current process pointer + lda R$A,u get destination ID + bne L0652 it's ok, go on + inca add one +* Send signal to ALL process's +L0647 cmpa P$ID,x find myself? + beq L064D yes, skip it + bsr L0652 send the signal +L064D inca move to next process + bne L0647 go send it + clrb clear errors + rts return + +* X = process descriptor ptr of singal sender +* A = process ID to send signal to +* R$B = signal code +L0652 lbsr L0B2E get pointer to destination descriptor + pshs cc,a,y,u preserve registers + bcs L066A error, can't get pointer return + tst R$B,u kill signal? + bne L066D no, go on + ldd P$User,x get user # + beq L066D he's super user, go on + cmpd P$User,y does he own the process? + beq L066D yes, send the signal + ldb #E$BPrcID get bad process error + inc ,s set Carry in CC on stack +L066A puls cc,a,y,u,pc return + +* Y = process descriptor of process receiving signal +L066D orcc #IntMasks shut down IRQ's + ldb R$B,u get signal code + bne L067B not a kill signal, skip ahead + ldb #E$PrcAbt get error 228 + IFNE H6309 + oim #Condem,P$State,y condem process +L067B aim #^Suspend,P$State,y take process out of suspend state + ELSE + lda P$State,y + ora #Condem + sta P$State,y +L067B lda P$State,y + anda #^Suspend + sta P$State,y + ENDC + lda <P$Signal,y already have a pending signal? + beq L068F nope, go on + deca is it a wakeup signal? + beq L068F yes, skip ahead + inc ,s set carry on stack + ldb #E$USigP get pending signal error + puls cc,a,y,u,pc return + +* Update sleeping process queue +L068F stb P$Signal,y save signal code in descriptor + ldx #(D.SProcQ-P$Queue) get pointer to sleeping process queue + IFNE H6309 + clrd Faster than 2 memory clears + ELSE + clra + clrb + ENDC +L0697 leay ,x point Y to this process + ldx P$Queue,x get pointer to next process in chain + beq L06D3 last one, go check waiting list + ldu P$SP,x get process stack pointer + addd R$X,u add his sleep count + cmpx 2,s is it destination process? + bne L0697 no, skip to next process + pshs d save sleep count + IFNE H6309 + tim #TimSleep,P$State,x + ELSE + lda P$State,x + bita #TimSleep + ENDC + beq L06CF no, update queue + ldd ,s + beq L06CF + ldd R$X,u + IFNE H6309 + ldw ,s + stw R$X,u + ELSE + pshs d + ldd 2,s + std R$X,u + puls d + ENDC + ldu P$Queue,x + beq L06CF + std ,s + IFNE H6309 + tim #TimSleep,P$State,u + ELSE + lda P$State,u + bita #TimSleep + ENDC + beq L06CF + ldu P$SP,u + ldd ,s + addd R$X,u + std R$X,u +L06CF leas 2,s + bra L06E0 +L06D3 ldx #(D.WProcQ-P$Queue) +L06D6 leay ,x + ldx P$Queue,x + beq L06F4 + cmpx 2,s + bne L06D6 +L06E0 ldd P$Queue,x + std P$Queue,y + lda P$Signal,x + deca + bne L06F1 + sta P$Signal,x + lda ,s + tfr a,cc +L06F1 os9 F$AProc activate the process +L06F4 puls cc,a,y,u,pc restore & return +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsleep.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,112 @@ +************************************************** +* System Call: F$Sleep +* +* Function: Put the calling process to sleep +* +* Input: X = Sleep time in ticks (0 = forever) +* +* Output: X = Decremented by the number of ticks that the process slept +* +* Error: CC = C bit set; B = error code +* +FSleep pshs cc preserve interupt status + ldx <D.Proc Get current process pointer + +* F$Sleep bug fix. Check if we're in system state. If so return because you +* should never sleep in system state. + cmpx <D.SysPrc is it system process? + beq SkpSleep skip sleep call + orcc #IntMasks disable interupts + lda P$Signal,x get pending signal + beq L0722 none there, skip ahead + deca wakeup signal? + bne L0715 no, skip ahead + sta P$Signal,x clear pending signal so we can wake up process +L0715 + IFNE H6309 + aim #^Suspend,P$State,x + ELSE + ENDC +L071B puls cc + os9 F$AProc activate the process + bra L0780 +L0722 ldd R$X,u get callers X (contains sleep tick count) + beq L076D done, wake it up + IFNE H6309 + decd subtract 1 from tick count + ELSE + ENDC + std R$X,u save it back + beq L071B zero, wake up process + pshs x,y + ldx #(D.SProcQ-P$Queue) +L0732 std R$X,u + stx 2,s + ldx P$Queue,x + beq L074F + IFNE H6309 + tim #TimSleep,P$State,x + ELSE + ENDC + beq L074F + ldy P$SP,x get process stack pointer + ldd R$X,u + subd R$X,y + bcc L0732 + IFNE H6309 + negd + ELSE + nega + negb + ENDC + std R$X,y +L074F puls y,x + IFNE H6309 + oim #TimSleep,P$State,x + ELSE + ENDC + ldd P$Queue,y + stx P$Queue,y + std P$Queue,x + ldx R$X,u + bsr L0780 + stx R$X,u + ldx <D.Proc + IFNE H6309 + aim #^TimSleep,P$State,x + ELSE + ENDC +SkpSleep puls cc,pc + +L076D ldx #D.SProcQ-P$Queue +L0770 leay ,x + ldx P$Queue,x + bne L0770 + ldx <D.Proc + clra + clrb + stx P$Queue,y + std P$Queue,x + puls cc + +L0780 pshs dp,x,y,u,pc +L0782 leax <L079C,pc + stx 7,s + ldx <D.Proc + ldb P$Task,x This is related to the 'one-byte hack' + cmpb <D.SysTsk that stops OS9p1 from doing an F$AllTsk on + beq L0792 _every_ system call. + os9 F$DelTsk +L0792 ldd P$SP,x + IFNE H6309 + pshsw + ENDC + pshs cc,d + sts P$SP,x + os9 F$NProc + +L079C pshs x + ldx <D.Proc + std P$SP,x + clrb + puls x,pc
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsprior.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,28 @@ +************************************************** +* System Call: F$SPrior +* +* Function: Set a process' priority +* +* Input: A = Process ID +* B = Priority (0 = lowest, 255 = highest) +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FSPrior lda R$A,u get process # + lbsr L0B2E get pointer to it + bcs L07C0 error, return + ldx <D.Proc get current process + ldd P$User,x get user # + beq L07B7 super user, go set priority + cmpd P$User,y user #'s match? + bne L07BD no, return error +L07B7 lda R$B,u get new priority + sta P$Prior,y set it + clrb clear errors + rts return +L07BD comb set carry for error + ldb #E$BPrcID +L07C0 rts +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsrqmem.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,304 @@ +************************************************** +* System Call: F$SRqMem +* +* Function: Request memory +* +* Input: D = Byte count +* +* Output: U = Address of allocated memory area +* +* Error: CC = C bit set; B = error code +* +* It also updates 8K DAT blocks-if it finds an empty block, it re-does the 32 +* entries in the SMAP table to indicate that they are free +* +FSRqMem ldd R$D,u get size requested + addd #$00FF round it up to nearest 256 byte page + clrb Just keep # of pages (and start 8K block #) + std R$D,u save rounded version back to user + ldy <D.SysMem Get ptr to SMAP table + leay $ED,y + +* leay $20,y Skip Block 0 (always reserved for system) +* Change to pshs a,b:use 1,s for block # to check, and ,s for TFM spot +* incb Skip block 0 (always reserved for system) + pshs d Reserve a byte & put 0 byte on stack + +* This loop updates the SMAP table if anything can be marked as unused +*L082F ldx <D.SysDAT get pointer to system DAT block list +* lslb adjust block offset for 2 bytes/entry +* ldd b,x get block type/# from system DAT +* cmpd #DAT.Free Unused block? +* beq L0847 yes, mark it free in SMAP table +* ldx <D.BlkMap No, get ptr to MMAP table +* lda d,x Get block marker for 2 meg mem map +* cmpa #RAMinUse Is it in use (not free, ROM or used by module)? +* bne L0848 No, mark it as type it is in SMAP table +* leay $20,y Yes, move to next block in pages +* bra L084F move to next block & try again + +*L0847 clra Byte to fill system page map with (0=Not in use) +*L0848 sta ,s Put it on stack +* ldw #$0020 Get size of 8K block in pages +* tfm s,y+ Mark entire block's worth of pages with A +*L084F inc 1,s Bump up to next block to check +* ldb 1,s Get it +* cmpb #8 Done whole 64k system space? +* blo L082F no, keep checking +* Now we can actually attempt to allocate the system RAM requested +* NOTE: Opt for Coco/TC9 OS9 ONLY: skip last 17 pages with leay -17,y since +* they are: Kernal (REL/BOOT/OS9P1 - 15 pages), vector RAM & I/O (2 pages) +* (Already permanently marked @ L01D2) +* At the start, Y is pointing to the end of the SMAP table+1 + ldx <D.SysMem Get start of table ptr + ldb #$20 skip block 0: it's always full + abx same size, but faster than leax $20,x +* leay -17,y Skip Kernal, Vector RAM & I/O (Can't be free) +L0857 ldb R$A,u Get # 256 byte pages requested +* Loop (from end of system mem map) to look for # continuous pages requested +L0859 equ * + IFNE H6309 +* TODO: Verify order of comparison + cmpr x,y We still have any system RAM left to try? + ELSE + pshs y + cmpx ,s++ + ENDC + bhi L0863 Yes, continue + comb Exit with No System RAM Error + ldb #E$NoRam + bra L0894 Eat stack & exit + +L0863 lda ,-y Get page marker (starting @ end of SMAP) + bne L0857 Used, try next lower page + decb Found 1 page, dec # pages we need to allocate + bne L0859 Still more pages needed, check if we can get more + sty ,s Found free contigous pages, save SMAP entry ptr + lda 1,s Get LSB of ptr + lsra Divide by 32 (Calculate start 8K block #) + lsra + lsra + lsra + lsra + ldb 1,s Get LSB of ptr again + andb #%00011111 Keep only within 8K block offset + addb R$A,u Add # pages requested + addb #$1F Round up to nearest 8K block + lsrb Divide by 32 (Calculate end 8K block #) + lsrb + lsrb + lsrb + lsrb + ldx <D.SysPrc Get ptr to system proc. dsc. + lbsr L09BE Allocate an image with our start/end block #'s + bcs L0894 Couldn't, exit with error + ldb R$A,u Get # pages requested + lda #RAMinUse Get SMAP in use flag +L088A sta ,y+ Mark all the pages requested as In Use + decb + bne L088A + lda 1,s Get MSB of ptr to start of newly allocated Sys RAM + std R$U,u Save for caller + clrb No error +L0894 puls u,pc Eat stack (U is changed after it exits) & return + + +************************************************** +* System Call: F$SRtMem +* +* Function: Return memory +* +* Input: U = Address of memory to return +* D = Number of bytes to return +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FSRtMem ldd R$D,u get # pages to free up + beq L08F2 nothing to free, return without error + addd #$00FF round it up to nearest page + ldb R$U+1,u get LSB of address + beq L08A6 it's a even page, skip ahead + comb set carry + ldb #E$BPAddr get error code + rts return + +L08A6 ldb R$U,u get MSB of page address + beq L08F2 not a legal page, return without error + ldx <D.SysMem get pointer to system memory map + abx set pointer into map +L08AD equ * + IFNE H6309 + aim #^RAMinUse,,x+ + ELSE + ldb ,x + andb #^RAMinUse + stb ,x+ + ENDC + deca + bne L08AD +* Scan DAT image to find memory blocks to free up + ldx <D.SysDAT get pointer to system DAT image + IFNE H6309 + lde #8 get # blocks to check + ELSE + ldy #DAT.BlCt + ENDC +L08BC ldd ,x get block image + cmpd #DAT.Free is it already free? + beq L08EC yes, skip to next one + ldu <D.BlkMap get pointer to MMU block map + lda d,u get allocation flag for this block: 16-bit offset + cmpa #RAMinUse being used? + bne L08EC no, move to next block + tfr x,d + subd <D.SysDAT + lslb + lslb + lslb + lslb + ldu <D.SysMem get pointer to system map + IFNE H6309 + addr d,u +* Check if we can remove the entire memory block from system map + ldf #16 get # pages per block/2 +L08DA ldd ,u++ Either of these 2 pages allocated? + ELSE + leau d,u + ldb #32 +L08DA lda ,u+ Either of these 2 pages allocated? + ENDC + bne L08EC yes, can't free block, skip to next one + IFNE H6309 + decf checked all pages? + ELSE + decb + ENDC + bne L08DA no, keep looking + ldd ,x get block # into B: could be >$80 + ldu <D.BlkMap point to allocation table + IFNE H6309 + sta d,u clear the block using 16-bit offset + ELSE + clr d,u + ENDC + ldd #DAT.Free get free block marker + std ,x save it into DAT image +L08EC leax 2,x move to next DAT block + IFNE H6309 + dece done? + ELSE + leay -1,y + ENDC + bne L08BC no, keep checking +L08F2 clrb clear errors +L08F3 rts return + +* Optimize F$Boot for size, as it's only called once... +* F$Boot entry point +FBoot lda #'t tried to boot + jsr <D.BtBug + coma Set boot flag + lda <D.Boot we booted once before? + bne L08F3 Yes, return + inc <D.Boot Set boot flag + ldx <D.Init Get ptr to init module if it exists + beq L0908 it doesn't, point to boot name + ldd <BootStr,x Get offset to text + beq L0908 Doesn't exist, get hard coded text + leax d,x Adjust X to point to boot module + bra L090C Try & link to module + +boot fcs /Boot/ + +L0908 leax <boot,pcr +* Link to module and execute +L090C lda #Systm+Objct + os9 F$Link + bcs L08F3 + lda #'b calling boot + jsr <D.BtBug + jsr ,y load boot file + bcs L08F3 + std <D.BtSz save boot file size + stx <D.BtPtr save start pointer of bootfile + lda #'b boot returns OK + jsr <D.BtBug + +* added for IOMan system memory extentions + ldd M$Name,x grab the name offset + ldd d,x find the first 2 bytes of the first module + cmpd #$4E69 'Ni' ? (NitrOS9 module?) + bne not.ext no, not system memory extensions + ldd M$Exec,x grab the execution ptr + jmp d,x and go execute the system memory extension module + +not.ext ldd <D.BtSz + bsr I.VBlock internal verify block routine + ldx <D.SysDAT get system DAT pointer + ldb $0D,x get highest allocated block number + incb allocate block 0, too + ldx <D.BlkMap point to the memory block map + lbra L01DF and go mark the blocks as used. + +FVBlock ldd R$D,u size of block to verify + ldx R$X,u start address to verify + +I.VBlock leau d,x point to end of bootfile + tfr x,d + anda #$E0 + clrb + pshs d,u + lsra + lsra + lsra + lsra + ldy <D.SysDAT get pointer to system DAT + leay a,y offset to bootfile +L092D ldd M$ID,x get module ID + cmpd #M$ID12 legal ID? + bne L0954 no, keep looking + ldd M$Name,x find name offset pointer + pshs x + leax d,x + +name.prt lda ,x+ get first character of the name + jsr <D.BtBug print it out + bpl name.prt + lda #C$SPAC a space + jsr <D.BtBug + + puls x + IFNE H6309 + ldd ,s offset into block + subr d,x make X=offset into block + ELSE + tfr x,d + subd ,s + tfr d,x + ENDC + tfr y,d + os9 F$VModul + IFNE H6309 + ldw ,s + leax w,x + ELSE + pshs b + ldd 1,s + leax d,x + puls b + ENDC + bcc L094E + cmpb #E$KwnMod + bne L0954 +L094E ldd M$Size,x + leax d,x + fcb $8C skip 2 bytes + +L0954 leax 1,x move to next byte +L0956 cmpx 2,s gone thru whole bootfile? + bcs L092D no, keep looking + leas 4,s purge stack + clrb + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fssvc.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,28 @@ +************************************************** +* System Call: F$SSVC +* +* Function: Allocate a 64 byte memory block +* +* Input: Y = Address of service request init table +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FSSvc ldy R$Y,u get pointer to table + bra L037F start moving +* Main move loop +L036D clra clear MSB of table offset + lslb multiply function # by 2 to get offset into table + tfr d,u copy it to U + ldd ,y++ get vector to function handler + leax d,y offset X from current Y + ldd <D.SysDis get system dispatch table pointer + stx d,u save vector into place + bcs L037F it was a privliged call, skip ahead + ldd <D.UsrDis get user displat table pointer + stx d,u save vector into place +L037F ldb ,y+ get callcode + cmpb #$80 done? + bne L036D no, keep going + rts return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsswi.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,26 @@ +************************************************** +* System Call: F$SSWI +* +* Function: Sets the SWI vector specified for the calling process. +* +* Input: B = SWI vector (1-3) to modify +* U = Address of new SWI vector for process +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FSSWI ldx <D.Proc get current process + ldb R$A,u get type code + decb adjust for offset + cmpb #3 legal value? + bcc BadSWI no, return error + lslb account for 2 bytes entry + addb #P$SWI go to start of P$SWI pointers + ldu R$X,u get address + stu b,x save to descriptor + rts return + +BadSWI comb + ldb #E$ISWI + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fstime.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,43 @@ +************************************************** +* System Call: F$STime +* +* Function: Set system time +* +* Input: X = Address of time packet: +* +* Offset 0 = Year +* Offset 1 = Month +* Offset 2 = Day +* Offset 3 = Hour +* Offset 4 = Minute +* Offset 5 = Second +* +* Output: System time/date set +* +* Error: CC = C bit set; B = error code +* +FSTime ldx R$X,u Get address that user wants time packet +*** tfr dp,a Set MSB of D to direct page +*** ldb #D.Time Offset to Time packet in direct page +*** tfr d,u Point U to it + ldu #D.Time --- DP=0 always + ldy <D.Proc Get ptr to process that called us + lda P$Task,y Get task # from process + ldb <D.SysTsk Get task # of system process + ldy #6 6 byte packet to move + os9 F$Move Go move it + ldx <D.Proc Get ptr to process that called us + pshs x Preserve it + ldx <D.SysPrc Get ptr to system process + stx <D.Proc Save as current process + lda #$C1 Link to Clock module + leax L07E3,pc + os9 F$Link + puls x Get back ptr to user's process + stx <D.Proc Make it the active process again + bcs L0816 If error in Link, exit with error code + jmp ,y Jump into Clock +L0816 rts + +L07E3 fcs /Clock/ +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fsuser.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,6 @@ +* F$User entry point +FSUser ldx <D.Proc get current process dsc ptr + ldd R$Y,u get requested user number + std P$User,x save new user # in process descriptor + clrb no error + rts and return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/funlink.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,190 @@ +************************************************** +* System Call: F$UnLink +* +* Function: Unlink a module +* +* Input: U = Address of module header +* +* Output: None +* +* Error: CC = C bit set; B = error code +* +FUnLink pshs d,u preserve register stack pointer and make a buffer + ldd R$U,u get pointer to module header + tfr d,x copy it to X + lsra divide MSB by 32 to get DAT block offset + lsra + lsra + lsra + lsra + sta ,s save DAT block offset + lbeq L01D0 zero, can't use so exit + ldu <D.Proc get pointer to current process + leay P$DATImg,u point Y to it's DAT image + lsla account for 2 bytes/entry + ldd a,y get block # + ldu <D.BlkMap get pointer to system block map + IFNE H6309 + tim #ModBlock,d,u Is memory block a module type? + ELSE + ldb d,u + bitb #ModBlock + ENDC + beq L01D0 no, exit without error + leau (P$Links-P$DATImg),y point to block link counts + bra L0161 go unlink block + +L015D dec ,s we done? + beq L01D0 yes, go on +L0161 ldb ,s get current offset + lslb account for 2 bytes entry + ldd b,u get block link count + beq L015D already zero, get next one + lda ,s get block offset + lsla find offset into 64k map by multiplying by 32 + lsla + lsla + lsla + lsla + clrb + nega + IFNE H6309 + addr d,x + ELSE + leax d,x + ENDC + ldb ,s get block offset + lslb account for 2 bytes/entry + ldd b,y get block # + ldu <D.ModDir get module directory pointer + bra L0185 go look for it + +* Main module directory search routine +L017C leau MD$ESize,u move to next module entry + cmpu <D.ModEnd done entire directory? + bhs L01D0 Yes, exit +L0185 cmpx MD$MPtr,u is module pointer the same? + bne L017C no, keep looking + cmpd [MD$MPDAT,u] DAT match? + bne L017C no, keep looking +* Module is found decrement link count +* NOTE: COULD WE USE D? +* L0198 - Safe, destroys D immediately +* Fall through- safe, destroys D immediately +* L01B5 - Seems to be safe + ldd MD$Link,u get module link count + beq L0198 it's zero, go unlink it + IFNE H6309 + decd decrement link count + ELSE + subd #$0001 + ENDC + std MD$Link,u save it back + bne L01B5 go on +* Module link count is zero check if he's unlinking a I/O module +L0198 ldx 2,s get pointer to register stack + ldx R$U,x get pointer to module + ldd #M$Type get offset to module type + os9 F$LDDDXY get module type + cmpa #FlMgr is it a I/O module? + blo L01B3 no, don't process for I/O + os9 F$IODel device still being used by somebody else? + bcc L01B3 no, go on + ldd MD$Link,u put the link count back to where it was + IFNE H6309 + incd + ELSE + addd #$0001 + ENDC + std MD$Link,u + bra L01D1 return error +* Clear module from memory +L01B3 bsr DelMod delete module from memory & module dir +L01B5 ldb ,s get block + lslb account for 2 bytes/entry + leay b,y point to block + ldd (P$Links-P$DATImg),y get block link count + IFNE H6309 + decd decrement it + ELSE + subd #$0001 + ENDC + std (P$Links-P$DATImg),y save new link count + bne L01D0 not zero, return to user +* Clear module blocks in process DAT image + ldd MD$MBSiz,u get block size + bsr L0226 calculate # blocks to delete + ldx #DAT.Free get DAT free marker +L01CB stx ,y++ save it in DAT image + deca done? + bne L01CB no, keep going +L01D0 clrb clear errors +L01D1 leas 2,s purge local data + puls u,pc restore & return + +* Delete module from module directory & from memory +* Entry: U=Module directory entry pointer to delete +* Exit : None +DelMod ldx <D.BlkMap get pointer to memory block map + ldd [MD$MPDAT,u] get pointer to module DAT image + lda d,x is block type ROM? + bmi L0225 yes can't delete it, return + ldx <D.ModDir get pointer to module directory +L01DF ldd [MD$MPDAT,x] get offset to DAT + cmpd [MD$MPDAT,u] match what we're looking for? + bne L01EA no, keep looking + ldd MD$Link,x get module link count + bne L0225 not zero, return +L01EA leax MD$ESize,x move to next module + cmpx <D.ModEnd at the end? + bcs L01DF no, keep going + ldx <D.BlkMap get pointer to block map + ldd MD$MBSiz,u get memory block size + bsr L0226 calculate # blocks to clear + IFNE H6309 + pshs u Preserve U (faster than original Y below) + clrb Setup for faster block in use clears + ldu MD$MPDAT,u get pointer to module DAT image +L01FB ldw ,u++ Get first block + stb -2,u clear it in DAT image + stb -1,u + addr x,w point to block in block map + aim #^(ModBlock!RAMinUse),,w + deca + bne L01FB + puls u Restore module ptr + ELSE + pshs y save y + ldy MD$MPDAT,u module image ptr +L01FB pshs a,x save #blocks, ptr + ldd ,y get block number + clr ,y+ clear the image + clr ,y+ + leax d,x point to blkmap entry + ldb ,x + andb #^(RAMinUse+ModBlock) free block + stb ,x + puls a,x + deca last block done? + bne L01FB ..no, loop + puls y + ENDC + ldx <D.ModDir get module directory pointer + ldd MD$MPDAT,u get module DAT pointer +L0216 cmpd MD$MPDAT,x match? + bne L021F no, keep looking + clr MD$MPDAT,x clear module DAT image pointer + clr MD$MPDAT+1,x +L021F leax MD$ESize,x point to next module entry + cmpx <D.ModEnd at the end? + blo L0216 no, keep looking +L0225 rts return + +L0226 addd #$1FFF round up to nearest block + lsra calculate block # within 64k workspace + lsra + lsra + lsra + lsra + rts +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/funload.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,61 @@ +* F$UnLoad entry point +FUnLoad pshs u preserve register stack pointer + lda R$A,u get module type + ldx <D.Proc get current process pointer + leay P$DATImg,x point to DAT image + ldx R$X,u get pointer to name + os9 F$FModul find it in module directory + puls y restore register stack pointer + bcs L0A4F couldn't find it, return error + stx R$X,y save update name pointer + IFNE H6309 + ldw MD$Link,u get link count + beq L0A21 already 0 check if it's a I/O module + decw subtract 1 + stw MD$Link,u save it back + ELSE + ldx MD$Link,u get module link count + beq L0A21 branch if zero + leax -1,x else decrement + stx MD$Link,u + ENDC + bne L0A4E not zero, don't remove from memory, return + +* Link count is zero, check if module can be removed from memory +L0A21 cmpa #FlMgr is it a I/O module? + blo L0A4B no, remove module from memory + +* Special handling for I/O module deletion + clra + ldx [MD$MPDAT,u] get 1st 2 blocks in DAT image of module + ldy <D.SysDAT get pointer to system DAT image +L0A2B adda #2 + cmpa #DAT.ImSz done entire DAT? + bcc L0A4B yes, delete the module from memory + cmpx a,y find block? + bne L0A2B no, keep looking + lsla multiply by 16 to calculate the offset + lsla + lsla + lsla + clrb + addd MD$MPtr,u add in the pointer + tfr d,x copy it to X + os9 F$IODel delete the device from memory + bcc L0A4B no error, skip ahead + + IFNE H6309 + ldw MD$Link,u put link count back + incw + stw MD$Link,u + ELSE + ldx MD$Link,u put link count back + leax 1,x + stx MD$Link,u + ENDC + rts Return with error + +* Delete module from memory +L0A4B lbsr DelMod Delete module from memory +L0A4E clrb clear errors +L0A4F rts return
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/fvmodul.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,445 @@ +************************************************** +* System Call: F$VModul +* +* Function: Verify a module +* +* Input: X = Address of module to verify +* +* Output: U = Address of module directory entry +* +* Error: CC = C bit set; B = error code +* +FVModul pshs u preserve register stack pointer + ldx R$X,u get block offset + ldy R$D,u get DAT image pointer + bsr L0463 validate it + ldx ,s get register stack pointer + stu R$U,x save address of module directory entry + puls u,pc restore & return + +* Validate module - shortcut for calls within OS9p1 go here (ex. OS9Boot) +* Entry: X=Module block offset +* Y=Module DAT image pointer +L0463 pshs x,y save block offset & DAT Image ptr + lbsr L0586 Go check module ID & header parity + bcs L0495 Error, exit + ldd #M$Type Get offset to module type + lbsr L0B02 get it + andb #LangMask Just keep language mask + pshs d Preserve ??? & language + ldd #M$Name get offset to module name + lbsr L0B02 + leax d,x Point X to module name + puls a Restore type/language + lbsr L068D + puls a + bcs L0497 + IFNE H6309 + andb #$0F + subr a,b + ELSE + pshs a + andb #$0F + subb ,s+ + ENDC + blo L0497 If wrapped, skip ahead + ldb #E$KwnMod + fcb $8C skip 2 bytes +L0491 ldb #E$DirFul +L0493 orcc #Carry +L0495 puls x,y,pc + +L0497 ldx ,s + lbsr L0524 + bcs L0491 + sty ,u + stx MD$MPtr,u + IFNE H6309 + clrd + ELSE + clra + clrb + ENDC + std MD$Link,u + ldd #M$Size Get offset to size of module + lbsr L0B02 + IFNE H6309 + addr x,d Add it to module ptr + ELSE + pshs x + addd ,s++ + ENDC + std MD$MBSiz,u + ldy [MD$MPDAT,u] get pointer to module DAT + ldx <D.ModDir get module directory pointer + pshs u save module pointer + fcb $8C skip 2 bytes + +L04BC leax MD$ESize,x move to next entry +L04BE cmpx <D.ModEnd + bcc L04CD + cmpx ,s match? + beq L04BC no, keep looking + cmpy [MD$MPDAT,x] DAT match? + bne L04BC no, keep looking + bsr L04F2 + +L04CD puls u + ldx <D.BlkMap Get ptr to block map + ldd MD$MBSiz,u Get size of module + addd #$1FFF Round up to nearest 8K block + lsra Divide by 32 + lsra + lsra + lsra + lsra + ldy MD$MPDAT,u + + IFNE H6309 + tfr a,e +L04DE ldd ,y++ + oim #ModBlock,d,x + dece + ELSE + pshs a,x save block size, blkmap +L04DE ldd ,y++ D = image block # + leax d,x X = blkmap ptr + ldb ,x get block marker + orb #ModBlock set module in block + stb ,x marker + puls x,a + deca count-- + ENDC + bne L04DE no, keep going + + clrb clear carry + puls x,y,pc return + +L04F2 pshs d,x,y,u + ldx ,x + + IFNE H6309 + tfr x,w Dupe to faster index register + clrd +L04FA ldy ,w + beq L0503 + std ,w++ + bra L04FA +L0503 ldy 2,s + ELSE + pshs x + clra D=0000 + clrb +L04FA ldy ,x last entry? + beq L0503 ..yes + std ,x++ no, clear + bra L04FA and loop +L0503 puls x + ldy 2,s + ENDC + + ldu MD$MPDAT,u + puls d + +L050C cmpx MD$MPDAT,y + bne L051B + stu MD$MPDAT,y + cmpd MD$MBSiz,y + bcc L0519 + ldd MD$MBSiz,y +L0519 std MD$MBSiz,y +L051B leay MD$ESize,y + cmpy <D.ModEnd + bne L050C + puls x,y,u,pc + +L0524 pshs x,y,u + ldd #M$Size + lbsr L0B02 + addd ,s + addd #$1FFF + lsra + lsra + lsra + lsra + lsra + tfr a,b + pshs b +* incb + comb one byte shorter than incb;lslg;negb + lslb +* negb + sex + bsr L054E + bcc L054C + os9 F$GCMDir get rid of empty slots in module directory + IFNE H6309 + tfr 0,u + ELSE + ldu #$0000 + ENDC + stu $05,s + bsr L054E +L054C puls b,x,y,u,pc + +L054E ldx <D.ModDAT + leax d,x + cmpx <D.ModEnd + bcs L0583 + ldu 7,s + bne L056E + IFEQ H6309 + pshs x + ENDC + ldy <D.ModEnd + leay MD$ESize,y + IFNE H6309 +* TODO: Verify order of comparison + cmpr x,y + ELSE + cmpy ,s++ + ENDC + bhi L0583 + sty <D.ModEnd + leay -MD$ESize,y + sty $07,s +L056E stx <D.ModDAT + IFNE H6309 + ldd $05,s Get source ptr + stx $05,s + ldf 2,s + clre + rolw + tfm d+,x+ + stw ,x Save 0 + ELSE + ldy 5,s + ldb 2,s B=block count + stx 5,s return dir datimg ptr +L0577 ldu ,y++ copy images + stu ,x++ to new mod dat entry + decb + bne L0577 + clr ,x zero flag + clr 1,x + ENDC + rts + +* Default interrupt handling routine on first booting OS9p1 +L0583 orcc #Carry + rts + +* Check module ID & calculate module header parity & CRC +* Entry: X=Block offset of module +* Y=DAT image pointer of module +L0586 pshs x,y save block offset & DAT pointer + IFNE H6309 + clrd + ELSE + clra + clrb + ENDC + lbsr L0B02 get module ID + cmpd #M$ID12 legal module? + beq L0597 yes, calculate header parity + ldb #E$BMID get bad module ID error + bra L05F3 return error +* Calculate module header parity +L0597 leax 2,x point to start location of header calc + lbsr AdjBlk0 adjust it for block 0 + IFNE H6309 + ldw #($4A*256+M$Revs) Get initial value & count (7 bytes of header) +L05A2 lbsr LDAXY get a byte from module + eorr a,e add it into running parity + decf done full header? + bne L05A2 no, keep going + ince valid parity? + ELSE + leas -1,s make var + ldb #$07 seven bytes + lda #$4A header crc +L05A2 sta ,s save crc + lbsr LDAXY get next byte + eora ,s do crc + decb more? + bne L05A2 ..loop + leas 1,s drop var + inca $FF+1 = 00 + ENDC + beq L05B5 yes, skip ahead + ldb #E$BMHP get module header parity error + bra L05F3 return with error +L05B5 puls x,y restore module pointer & DAT pointer +* this checks if the module CRC checking is on or off + lda <D.CRC is CRC checking on? + bne L05BA yes - go check it + IFNE H6309 + clrd no, clear out + ELSE + clra + clrb + ENDC + rts and return +* Begin checking Module CRC +* Entry: X=Module pointer +* Y=DAT image pointer of module +L05BA ldd #M$Size get offset to module size + lbsr L0B02 get module size + IFNE H6309 + tfr d,w move length to W + pshs y,x preserve [X]=Buffer pointer,[Y]=DAT pointer + ELSE + pshs y,x,b,a preserve [X]=Buffer pointer,[Y]=DAT pointer + ENDC + ldd #$FFFF initial CRC value of $FFFFFF + pshs d set up local 24 bit variable + pshs b + lbsr AdjBlk0 adjust module pointer into block 0 for mapping + leau ,s point to CRC accumulator +* Loop: W=# bytes left to use in CRC calc +L05CB equ * + IFNE H6309 + tstf on 256 byte boundary? + ELSE + tstb + ENDC + bne L05D8 no, keep going + pshs x give up some time to system + ldx #1 + os9 F$Sleep + puls x restore module pointer +L05D8 lbsr LDAXY get a byte from module into A + bsr CRCCalc add it to running CRC + IFNE H6309 + decw Dec # bytes left to calculate CRC with + ELSE + ldd 3,s + subd #$0001 + std 3,s + ENDC + bne L05CB Still more, continue + IFNE H6309 + puls b,x yes, restore CRC + ELSE + puls b,x,y yes, restore CRC + ENDC + cmpb #CRCCon1 CRC MSB match constant? + bne L05F1 no, exit with error + cmpx #CRCCon23 LSW match constant? + beq L05F5 yes, skip ahead +L05F1 ldb #E$BMCRC Bad Module CRC error +L05F3 orcc #Carry Set up for error +L05F5 puls x,y,pc exit + +* Calculate 24 bit CRC +* Entry: A=Byte to add to CRC +* U=Pointer to 24 bit CRC accumulator +* +* Future reference note: Do not use W unless preserved, contains module +* byte counts from routines that come here!! +CRCCalc eora ,u + pshs a + ldd 1,u + std ,u + clra + ldb ,s + IFNE H6309 + lsld + ELSE + aslb + rola + ENDC + eora 1,u + std 1,u + clrb + lda ,s + IFNE H6309 + lsrd + lsrd + eord 1,u + ELSE + lsra + rorb + lsra + rorb + eora 1,u + eorb 2,u + ENDC + std 1,u + lda ,s + lsla + eora ,s + sta ,s + lsla + lsla + eora ,s + sta ,s + lsla + lsla + lsla + lsla + eora ,s+ + bpl L0635 + IFNE H6309 + eim #$80,,u + eim #$21,2,u + ELSE + ldd #$8021 + eora ,u + sta ,u + eorb 2,u + stb 2,u + ENDC +L0635 rts + + +************************************************** +* System Call: F$CRC +* +* Function: Compute CRC +* +* Input: X = Address to start computation +* Y = Byte count +* U = Address of 3 byte CRC accumulator +* +* Output: CRC accumulator is updated +* +* Error: CC = C bit set; B = error code +* +FCRC ldd R$Y,u get # bytes to do + beq L0677 nothing there, so nothing to do, return + ldx R$X,u get caller's buffer pointer + pshs d,x save # bytes & buffer pointer + leas -3,s allocate a 3 byte buffer + ldx <D.Proc point to current process descriptor + lda P$Task,x get its task number + ldb <D.SysTsk get the system task number + ldx R$U,u point to user's 24 bit CRC accumulator + ldy #3 number of bytes to move + leau ,s point to our temp buffer + pshs d,x,y save [D]=task #'s,[X]=Buff,[Y]=3 + lbsr L0B2C move CRC accumulator to temp buffer + ldx <D.Proc point to current process descriptor + leay <P$DATImg,x point to its DAT image + ldx 11,s restore the buffer pointer + lbsr AdjBlk0 make callers buffer visible + IFNE H6309 + ldw 9,s get byte count + ENDC +L065D lbsr LDAXY get byte from callers buffer + bsr CRCCalc add it to CRC + IFNE H6309 + decw done? + ELSE + ldd 9,s + subd #$0001 + std 9,s + ENDC + bne L065D no, keep going + puls d,x,y restore pointers + exg a,b swap around the task numbers + exg x,u and the pointers + lbsr L0B2C move accumulator back to user + leas 7,s clean up stack +L0677 clrb no error + rts
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/krn.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,946 @@ +******************************************************************** +* OS9p1 - NitrOS-9 kernel +* +* $Id$ +* +* Ed. Comments Who YY/MM/DD +* ------------------------------------------------------------------ +* 19r6 Assembles to the os9p1 module that works on BGP 02/08/21 +* my NitrOS-9 system +* 19r7 Added check for CRC feature bit in init module BGP 02/09/26 + + nam OS9p1 + ttl NitrOS-9 kernel + + IFP1 + use defsfile + ENDC + +* defines for customizations +Revision set 7 module revision +Edition set 19 module Edition +Where equ $F000 absolute address of where OS9p1 starts in memory + + mod eom,MName,Systm,ReEnt+Revision,OS9P1,0 + +MName fcs /OS9p1/ + fcb Edition + +* FILL - all unused bytes are now here + fcc /0123456789ABCDEF/ + fcc /0123456789ABCDEF/ + fcc /0123456789ABCDEF/ + fcc /01234567/ + +* Might as well have this here as just past the end of OS9p1... +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 OS9p1 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 * +* 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 +* Don't add any code here: See L0065, below. +* Interrupt service routine +L0271 jmp [<-(D.SWI3-D.XSWI3),x] (-$10) (Jmp to 2ndary vector) + +* Let's start by initializing system page +OS9P1 equ * + IFNE H6309 + ldq #$01001f00 Start address to clear & # bytes to clear + leay <OS9P1+2,pc Point to a 0 + tfm y,d+ + ELSE + ldx #$100 + ldy #8192-$100 + clra + clrb +L001C std ,x++ + leay -2,y + bne L001C + inca + inca + ENDC +* Setup system direct page variables + std <D.CCStk Set pointer to top of global memory to $2000 + lda #$01 set task user table to $0100 + 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 beggining of global memory to $1000 +* 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 + +* Initialize interrupt vector tables + leay <DisTable,pcr point to table of absoulte 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 + +* 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 + +* leau <L0271,pc point to vector + tfr y,u move the pointer to a faster register +L0065 stu ,x++ Set all IRQ vectors to go to L0271 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 >L0316,pc Setup System service routine entry vector + stx <D.SysSvc + stx <D.XSWI2 + leax >L0E12,pc Setup system IRQ service vector + stx <D.SysIRQ + stx <D.XIRQ + leax >L0E45,pc Setup in system IRQ service vector + stx <D.SvcIRQ + leax >L0583,pc Setup interrupt polling vector + stx <D.Poll ORCC #$01;RTS + leax >L0E44,pc Setup alternate IRQ vector: pts to an RTS + stx <D.AltIRQ + + lda #'1 --- in OS9p1 + jsr <D.BtBug --- + + leax >L0E7D,pc Setup change to task 1 vector + stx <D.Flip1 +* Setup System calls + leay >L0200,pc + lbsr L037F +* Initialize system process descriptor + 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 +* 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) + 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 + +* 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 + std <D.BlkMap+2 save block map end pointer + ELSE + ldd #$0008 +L0111 rolb + lsla + stb >$FFA5 + pshs a + lda #$01 + sta >-$6000,x + cmpa ,x + beq L0112 + puls a + bra L0111 +L0112 stb <D.MemSz + pshs x + addd ,s++ + std <D.BlkMap+2 + ENDC +* [D] at this point will contain 1 of the following: +* $0010 - 128k +* $0020 - 256k +* $0040 - 512k +* $0080 - 1024k +* $0100 - 2048k + 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 #$12 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 +* Save pointer to init module and execute os9p2 +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 <os9p2,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 os9p2 +* Mark kernel in system memory map as used memory (256 byte blocks) +L01D2 ldx <D.SysMem Get system mem ptr + ldd #NotRAM*256+$ED $ED00 is the 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 +L0E44 rts return + +* Link module pointed to by X +link lda #Systm Attempt to link system module + os9 F$Link + rts + +init fcs 'Init' +os9p2 fcs 'OS9p2' + +* Service vector call pointers +L0200 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 Now here in OS9P1 + fdb FCpyMem-*-2 + ENDC + fcb F$Move+SysState + fdb FMove-*-2 + fcb F$AllRam + fdb FAllRam-*-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$AlHRam+SysState + fdb FAlHRam-*-2 + fcb F$VBlock+SysState + fdb FVBlock-*-2 + fcb F$DelRAM + fdb FDelRAM-*-2 + fcb $80 + +* SWI3 vector entry +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 + +* SWI2 vector entry +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 + pshs d + 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 + + leau R$Size-1,s point to last byte of destination register stack + leay -1,y point to caller's register stack in $FEE1 + IFNE H6309 + ldw #R$Size size of the register stack + tfm y-,u- + ELSE + ldb #R$Size +Loop3 lda ,y- + sta ,u- + decb + bne Loop3 + puls d + ENDC + andcc #^IntMasks + leau ,s needed because the TFM is u-, not -u (post, not pre) +* 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 +* 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 + +* 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 + +* add ldu P$SP,x, etc... +AllClr inc <D.QCnt + IFNE H6309 + aim #$1F,<D.QCnt + beq DoFull ever 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 + 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 + +* 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 +* 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 + +* Process software interupts from system state +* Entry: U=Register stack pointer +L0316 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 + +* 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 +* Execute I/O system calls + 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 ,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 ,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 + + use fallram.asm + + use fdelram.asm + + use fallimg.asm + + use ffreehb.asm + + use fdatlog.asm + + use fld.asm + + use fcpymem.asm + + 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 +* 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 + +* 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 +L0E12 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 + +* 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 +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 + +* 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 +L0E7D 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 + +* 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 + +* 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 + clr >DAT.Task go to map type 1 + IFNE H6309 + tfr 0,dp set DP to zero + ELSE + clra + 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, +* ... and adds 14 cycles to each SWI(2,3) call from grfdrv... not a problem. +* 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 + +* 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 + +* 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 +* 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,$45,$72,$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 +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/krnp2.asm Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,396 @@ +******************************************************************** +* OS9p2 - NitrOS-9 Kernel Part II +* +* $Id$ +* +* Copyright (c) 1982 Microware Corporation +* +* Modified for 6309 Native mode by: +* +* Bill Nobel, L. Curtis Boyle & Wes Gale - Gale Force Enterprises +* +* Ed. Comments Who YY/MM/DD +* ------------------------------------------------------------------ +* +* 17.2 08/02/92 - Active in 6309 Native mode, No apparent bugs (BN) +* - Optimized F$Fork (BN) +* - Optimized F$Chain (BN) +* 18.4 92/12/15 - Cut initial memory allocation routine - unnecessary +* 18.5 93/01/18 - Fixed bug in F$Sleep (LCB) +* - Optimized F$All64 to use tfm (BN) +* NitrOS9 V1.09 - Move & optomized F$CpyMem to OS9P1 +* V1.10 93/05/23 - Slight opt to UnLink +* V1.11 93/07/26 - Slight opt in F$Icpt +* - Slight opt in F$Wait alarm clearing +* - Slight opt to speed up path table full errors +* - Changed LBEQ to BEQ in F$Unlink +* V1.16 93/09/03 - Moved F$SUser to OS9P1 (WG) +* 93/09/08 - Moved F$SUser back to OS9P2 for room in OS9P1 (LCB) +* 93/09/10 - F$Find64 (L0A50) - Took out BSR to L0A5C, merged routine +* in (only called from here), and took out PSHS/PULS D +* Also modified error structure a bit to shorten it +* 93/10/06 - Added conditional assembly to skip Network I/O ptrs since +* Coco network never released by Tandy/Microware (in F$Fork) +* - @ GotNProc (in F$Fork), saved 1 byte/cycle when inheriting +* User # & priority +* - Changed routine @ L01FB to use U instead of Y (slightly +* smaller & slightly faster), and also used CLRB with STB +* instead of CLR for clearing DAT block #'s (F$UnLink) +* 93/12/17 - Moved F$CRCMod code here to give some room in OS9P1 +* 94/05/15 - Attempted opts in Unlink: Changed usage of W to D @ L0185 +* and L0198 and L01B5, also optomized L017C to eliminate a +* branch (speeds up module dir search by 3 cycles/module +* checked) +* - Changed BRA L032F @ L02EC (AllProc error) to RTS +* - Changed BRA L0629 @ L05DF to RTS +* - Changed L066A & L067B from BRA L06F4 to PULS CC,A,Y,U,PC +* (F$Send errors) +* - Changed L0A2B from BRA L0A4F to RTS (F$UnLoad error) +* - Changed L0C53 & L0C81 BRA L0C93 to CLRB/RTS (F$GCMDir) +* -- Alan DeKok +* 94/10/28 - added boot debug calls +* - Changed code at ~L0D47 to allow F$Fork/F$Chain of Obj6309 +* 94/10/30 - Added error checking on F$Fork of CC3Go +* - Minor mods to F$SSWI call +* - Minor mods to F$STime +* - Changed F$GModDr to BRA to similar code in F$GBlkMp +* + + nam OS9p2 + ttl NitrOS-9 Kernel Part II + +** If Network I/O ptrs are disabled, F$Fork runs 72 cycles faster +Network equ 0 Set to 1 to enable network I/O ptrs + + ifp1 + use defsfile + endc + +TC9 set false "true" use TC-9 6309 trap vector +Edition equ 18 +Revision equ 5 +*DAT.Free equ $333E --- remove this def later + + mod eom,MName,Systm,ReEnt+Revision,OS9P2,$0100 + +MName fcs /OS9p2/ + fcb Edition + + ifeq TC9-1 +* Entry: None +* Exit : Process killed & register dump produced for user +Trap bitmd #%01000000 illegal instruction? + bne BadIns yes, go process + bitmd #%10000000 division by 0? + bne Div0 yes, go process + jmp [<D.XSWI] act as if nothing happened + +* Process illegal instruction trap +BadIns bsr SetProc move the register stack here + + + + + + ldb #18 get error code for F$Exit + bra TrapDone +* Process division by 0 trap +Div0 bsr SetProc move the register stack + + + + + ldb #45 get error code for F$Exit + +* Return to system after the trap +* Entry: B=Error code +* U=Pointer to register stack +TrapDone stb R$B,u save the error code to register stack for F$Exit + lbra FExit enter F$Exit directly + +* Set process to system state & copy register stack for trap processing +SetProc ldd <D.SysSvc set system call processor to system side + std <D.XSWI2 + ldd <D.SysIRQ do the same thing for IRQ's + std <D.XIRQ + ldx <D.Proc get current process pointer + IFNE H6309 + oim #SysState,P$State,x mark process as system state + ELSE + 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 + andcc #^IntMasks force interrupts back on + leau ,s point to destination register stack + ldb P$Task,x get task # of destination + ldx P$SP,x get the user/system stack pointer + pshs b preserve task for a moment + tfr x,d copy it for easier calcs + bita #%11100000 offset above block 0? + beq done yes, no calc needed get out + anda #%00011111 make it a offset within a block + tfr d,x copy new offset + lsra make A an offset into DAT image + lsra + lsra + lsra +done puls b restore task # + leax -$6000,x make it a pointer to where I'll map the block + tfr u,y + pshs cc,u preserve IRQ status & dest pointer + ldu <D.TskIPt + lslb adjust task # to fit table + ldu b,u get the DAT image pointer + leau a,u point to the blocks needed + lda 1,u get 1st block + ldb 3,u get a second in case of overlap + orcc #IntMasks shut IRQ's down + std >$FFA5 map in the blocks + IFNE H6309 + ldw #R$Size get size of register stack + tfm x+,y+ move 'em to process descriptor + ELSE + ldb #R$Size +Uday lda ,x+ + sta ,y+ + decb + bne Uday + ENDC + ldx <D.SysDAT get the system DAT image pointer + lda $0B,x get the original blocks + ldb $0D,x + std >$FFA5 map 'em back in + puls cc,u,pc restore IRQ's, register stack pointer & return + endc + +OS9P2 lda #'2 into OS9p2 + jsr <D.BtBug + + leay SvcTab,pc install system calls + os9 F$SSvc + ifeq TC9-1 + leax Trap,pc + stx <D.SWI + endc +* Change to default directory +L003A ldu <D.Init get init module pointer + ldd SysStr,u get pointer to system device name (usually '/dd') + beq L004F don't exist, open std device + leax d,u point to name + + lda #'x tried chd'ing + jsr <D.BtBug + + lda #(EXEC.+READ.) get file mode + os9 I$ChgDir change to it + bcc L004F went ok, go on + os9 F$Boot try & load boot file + bcc L003A go try again +L004F ldu <D.Init get pointer to init + ldd <StdStr,u point to default device (usually '/term') + beq L0077 don't exist go do OS9P3 + leax d,u point to it + + lda #'o tried opening output window + jsr <D.BtBug + + lda #UPDAT. get file mode + os9 I$Open open path to it + bcc L0066 went ok, save path # + os9 F$Boot try & re-boot + bcc L004F go try again + bra L009B crash machine +L0066 ldx <D.Proc get current process pointer + sta <P$Path,x save stdin path + os9 I$Dup dupe it + sta <P$Path+1,x save stdout path + os9 I$Dup dupe it again + sta <P$Path+2,x save stderr path +L0077 leax <L0096,pc point to 'OS9P3' + lda #Systm get type + os9 F$Link try & link + bcs L0083 not there, go on + jsr ,y execute it +* Execute module listed in Init module +L0083 ldu <D.Init get init module pointer + ldd InitStr,u get offset to name of first module + leax d,u point to it + + lda #'C tried to to CC3Go + jsr <D.BtBug + + lda #Objct get module type + clrb get mem size + IFNE H6309 + tfr 0,y Get parameter size + ELSE + ldy #$0000 + ENDC + os9 F$Fork fork it + bcc L0093 if no error, go execute it + jmp <D.Crash otherwise crash the system +L0093 os9 F$NProc let it take over + +L0096 fcs /OS9p3/ + +L009B jmp <D.Crash + +svctab fcb F$UnLink + fdb FUnLink-*-2 + fcb F$Fork + fdb FFork-*-2 + fcb F$Wait + fdb FWait-*-2 + fcb F$Chain + fdb FChain-*-2 + fcb F$Exit + fdb FExit-*-2 + fcb F$Mem + fdb FMem-*-2 + fcb F$Send + fdb FSend-*-2 + fcb F$Icpt + fdb FIcpt-*-2 + fcb F$Sleep + fdb FSleep-*-2 + fcb F$SPrior + fdb FSPrior-*-2 + fcb F$ID + fdb FID-*-2 + fcb F$SSWI + fdb FSSWI-*-2 + fcb F$STime + fdb FSTime-*-2 + fcb F$SchBit + fdb FSchBit-*-2 + fcb F$SchBit+$80 + fdb FSSchBit-*-2 + fcb F$AllBit + fdb FAllBit-*-2 + fcb F$AllBit+$80 + fdb FSAllBit-*-2 + fcb F$DelBit + fdb FDelBit-*-2 + fcb F$DelBit+$80 + fdb FSDelBit-*-2 + fcb F$GPrDsc + fdb FGPrDsc-*-2 + fcb F$GBlkMp + fdb FGBlkMp-*-2 + fcb F$GModDr + fdb FGModDr-*-2 + fcb F$SUser Added back here for room in OS9p1 + fdb FSUser-*-2 + fcb F$UnLoad + fdb FUnLoad-*-2 + fcb F$Find64+$80 + fdb FFind64-*-2 + fcb F$All64+$80 + fdb FAll64-*-2 + fcb F$Ret64+$80 + fdb FRet64-*-2 + fcb F$GProcP+$80 + fdb FGProcP-*-2 + fcb F$DelImg+$80 + fdb FDelImg-*-2 + fcb F$AllPrc+$80 + fdb FAllPrc-*-2 + fcb F$DelPrc+$80 + fdb FDelPrc-*-2 + fcb F$MapBlk + fdb FMapBlk-*-2 + fcb F$ClrBlk + fdb FClrBlk-*-2 + fcb F$GCMDir+$80 + fdb FGCMDir-*-2 + fcb F$CRCMod new system call to change module CRC calcs on/off + fdb FCRCMod-*-2 + fcb $7f + fdb GetIOMan-*-2 + fcb $80 + + use fcrcmod.asm + +* Link & execute IOMan +* Entry: None +* Exit : I/O handling installed & ready for use +GetIOMan pshs d,x,y,u preserve regs + bsr LnkIOMan link to ioman + bcc GotIOMan no errors, go on + os9 F$Boot re-load boot file + bcs IOManErr error loading, return + bsr LnkIOMan link to ioman + bcs IOManErr error, save it & return +GotIOMan jsr ,y execute IOMan's init routine + puls d,x,y,u restore registers + jmp [IOEntry,y] Execute I/O vector + +IOManErr stb 1,s save error if any + puls d,x,y,u,pc restore & return + +* Link to IOMan +* Entry: None +* Exit : U=Pointer to IOMan module header +* Y=Pointer to IOMan entry point +LnkIOMan leax <IOMan,pc point to name + lda #(Systm+Objct) get type + os9 F$Link link it + rts return + +IOMan fcs /IOMan/ + + use funlink.asm + + use ffork.asm + + use fallprc.asm + + use fchain.asm + + use fexit.asm + + use fmem.asm + + use fsend.asm + + use ficpt.asm + + use fsleep.asm + + use fsprior.asm + + use fid.asm + + use fsswi.asm + + use fstime.asm + + use fallbit.asm + + use fgprdsc.asm + + use fgblkmp.asm + + use fgmoddr.asm + + use fsuser.asm + + use funload.asm + + use ffind64.asm + + use fgprocp.asm + + use fdelimg.asm + + use fmapblk.asm + + use fclrblk.asm + + use fgcmdir.asm + + emod +eom equ * + end +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/level2/modules/kernel/makefile Tue Apr 22 19:35:48 2003 +0000 @@ -0,0 +1,38 @@ +include ../../../Makefile.rules + +vpath %.asm $(LEVEL2)/MODULES/KERNEL + +DEPENDS = ./Makefile +ADDOPTS = -e + +OS9P1 = os9p1 +OS9P2 = os9p2 +SYSCALLS = fallimg.asm fallram.asm falltsk.asm faproc.asm fcmpnam.asm \ + fcpymem.asm fdatlog.asm fdelram.asm ffmodul.asm ffreehb.asm \ + fld.asm fldabx.asm flink.asm fmove.asm fnproc.asm fprsnam.asm \ + freboot.asm fsrqmem.asm fssvc.asm fvmodul.asm \ + fallbit.asm fallprc.asm fchain.asm fclrblk.asm fcrcmod.asm \ + fdelimg.asm fexit.asm ffind64.asm ffork.asm fgblkmp.asm \ + fgcmdir.asm fgmoddr.asm fgprdsc.asm fgprocp.asm ficpt.asm \ + fid.asm fmapblk.asm fmem.asm fsend.asm fsleep.asm fsprior.asm \ + fsswi.asm fstime.asm fsuser.asm funlink.asm funload.asm + +ALLOBJS = $(OS9P1) $(OS9P2) + +all: $(ALLOBJS) + +$(OS9P1): os9p1.asm $(SYSCALLS) + +$(OS9P2): os9p2.asm $(SYSCALLS) + +clean: + $(RM) $(ALLOBJS) + +showobjs: + @$(ECHO) $(ALLOBJS) + +showcopyobjs: + @$(ECHO) $(COPYOBJS) + +identify: + $(IDENT_SHORT) $(ALLOBJS)