diff --git a/applecorn.po b/applecorn.po index e181cd7..d40b221 100644 Binary files a/applecorn.po and b/applecorn.po differ diff --git a/auxmem.bytwrd.s b/auxmem.bytwrd.s index f2a39c2..7733727 100644 --- a/auxmem.bytwrd.s +++ b/auxmem.bytwrd.s @@ -14,7 +14,7 @@ ************************* * OSBYTE DISPATCH TABLE * ************************* -BYTWRDADDR DW BYTE00XX ; OSBYTE 0 - Machine host +BYTWRDADDR DW BYTE00 ; OSBYTE 0 - Machine host - INIT.s DW BYTE01 ; OSBYTE 1 - User flag DW BYTE02 ; OSBYTE 2 - OSRDCH source DW BYTE03 ; OSBYTE 3 - OSWRCH dest @@ -248,14 +248,14 @@ WORD00 IF MAXLEN-OSTEXT-2 BPL :WORD00LP2 INY ; Initial line length = zero ELSE - LDA (OSCTRL),Y ; Copy control block - STA OSTEXT,Y ; 0,1 => text - INY ; 2 = MAXLEN - CPY #$05 ; 3 = MINCHAR - BCC WORD00 ; 4 = MAXCHAR - LDY #$00 ; Initial line length = zero + LDY #$04 ; Copy control block +:WORD00LP3 LDA (OSCTRL),Y ; 0,1 => text + STA OSTEXT,Y ; 2 = MAXLEN + DEY ; 3 = MINCHAR + BPL :WORD00LP3 ; 4 = MAXCHAR + INY ; Initial line length = zero FIN -* STY FXLINES ; Reset line counter +* STY FXLINES ; Reset line counter CLI BEQ :WORD00LP ; Enter main loop @@ -467,38 +467,3 @@ OSWORDM ASC 'OSWORD($' DB $00 OSBM2 ASC ').' DB $00 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/auxmem.chario.s b/auxmem.chario.s index 698aa3d..c553c16 100644 --- a/auxmem.chario.s +++ b/auxmem.chario.s @@ -26,10 +26,8 @@ * 09-Sep-2021 Moved keyboard OSBYTEs to here. * 12-Sep-2021 COPY calls new VDU entry point. * 15-Sep-2021 INKEY(0) tests once and returns immediately. +* TO DO: CHKESC should go through translations before testing. -* TO DO: move these to VDU -* OLDCHAR EQU OSKBD1 ; *TEMP* ; character under cursor -* COPYCHAR EQU OSKBD2 ; *TEMP* ; character under copy cursor FLASHER EQU BYTEVARBASE+176 ; VSync counter for flashing cursor FXEXEC EQU BYTEVARBASE+198 @@ -56,6 +54,7 @@ WRCHHND PHA PHX PHY * TO DO Check any output redirections +* PHA JSR OUTCHAR * TO DO Check any printer output @@ -444,33 +443,3 @@ BYTE7DOK RTS BYTE76 LDX #$00 ; Update LEDs and return X=SHIFT RTS ; Not possible with Apple - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/auxmem.hostfs.s b/auxmem.hostfs.s index 2b26e04..092ece2 100644 --- a/auxmem.hostfs.s +++ b/auxmem.hostfs.s @@ -16,88 +16,79 @@ * 23-Oct-2021 Uses single dispatch to mainmem FILE handler. * 24-Oct-2021 Tidied FSC handler. Optimised CATALOG, CAT shows access. * *EX can use two columns. *OPT stored. +* 29-Oct-2021 Bad *command->Bad command, bad *RUN->File not found. +* Optimised RENAME, COPY, CHDIR, DRIVE. FREE allowed. * $B0-$BF Temporary filing system workspace * $C0-$CF Persistant filing system workspace -FSXREG EQU $C0 -FSYREG EQU $C1 -FSAREG EQU $C2 -FSZPC3 EQU $C3 -FSCTRL EQU FSXREG -FSPTR1 EQU $C4 -FSPTR2 EQU $C6 -FSNUM EQU $C8 -FSZPCC EQU $CC -FSCMDLINE EQU $CE +FSXREG EQU $C0 +FSYREG EQU $C1 +FSAREG EQU $C2 +FSZPC3 EQU $C3 +FSCTRL EQU FSXREG +FSPTR1 EQU $C4 +FSPTR2 EQU $C6 +FSNUM EQU $C8 +FSZPCC EQU $CC +FSCMDLINE EQU $CE * OSFIND - open/close a file for byte access -FINDHND PHX - PHY - PHA - CMP #$00 ; A=$00 = close - BEQ :CLOSE - PHA - JSR PARSNAME ; Copy filename->MOSFILE - PLA ; Recover options - >>> XF2MAIN,OFILE -:CLOSE -* >>> WRTMAIN -* STY MOSFILE ; Write file number -* >>> WRTAUX - >>> XF2MAIN,CFILE ; Pass A,Y to main code - -OSFINDRET >>> ENTAUX - JSR CHKERROR ; Check if error returned - PLY ; Value of A on entry - BNE :S1 ; It wasn't close - TYA ; Preserve A for close -:S1 PLY - PLX - RTS +FINDHND PHX + PHY + PHA + CMP #$00 ; A=$00 = close + BEQ :CLOSE + PHA + JSR PARSNAME ; Copy filename->MOSFILE + PLA ; Recover options + >>> XF2MAIN,OFILE +:CLOSE >>> XF2MAIN,CFILE ; Pass A,Y to main code +OSFINDRET >>> ENTAUX + JSR CHKERROR ; Check if error returned + PLY ; Value of A on entry + BNE :S1 ; It wasn't close + TYA ; Preserve A for close +:S1 PLY + PLX + RTS * OSGBPB - Get/Put a block of bytes to/from an open file -GBPBHND LDA #OSGBPBM - JMP PRSTR -OSGBPBM ASC 'OSGBPB.' - DB $00 +GBPBHND LDA #OSGBPBM + JMP PRSTR +OSGBPBM ASC 'OSGBPB.' + DB $00 * OSBPUT - write one byte to an open file -BPUTHND PHX - PHY - PHA ; Stash char to write -* >>> WRTMAIN -* STY MOSFILE ; File reference number -* >>> WRTAUX - >>> XF2MAIN,FILEPUT ; Pass A,Y to main code -OSBPUTRET >>> ENTAUX - JSR CHKERROR - CLC ; Means no error - PLA - PLY - PLX - RTS +BPUTHND PHX + PHY + PHA ; Stash char to write + >>> XF2MAIN,FILEPUT ; Pass A,Y to main code +OSBPUTRET >>> ENTAUX + JSR CHKERROR + CLC ; Means no error + PLA + PLY + PLX + RTS * OSBGET - read one byte from an open file -BGETHND PHX - PHY -* >>> WRTMAIN -* STY MOSFILE ; File ref number -* >>> WRTAUX - >>> XF2MAIN,FILEGET ; Pass A,Y to main code -OSBGETRET >>> ENTAUX - CPY #$01 - BCC :EXIT ; If no error, return CC - LDA #$FE - CPY #$4C - BEQ :EXIT ; If at EOF, return CS - TYA - JSR CHKERROR -:EXIT PLY - PLX - RTS +BGETHND PHX + PHY + >>> XF2MAIN,FILEGET ; Pass A,Y to main code +OSBGETRET >>> ENTAUX + CPY #$01 + BCC :EXIT ; If no error, return CC + LDA #$FE + CPY #$4C + BEQ :EXIT ; If at EOF, return CS + TYA + JSR CHKERROR +:EXIT PLY + PLX + RTS * OSARGS - adjust file arguments * On entry, A=action @@ -117,88 +108,74 @@ OSBGETRET >>> ENTAUX * control block updated for 'read' calls * control block preserved otherwise * -ARGSHND PHX - PHY - PHA - CPY #$00 - BNE :HASFILE - CMP #$00 ; Y=0,A=0 => current file sys - BNE :S1 - PLA - LDA #105 ; 105=AppleFS filing system - PLY - PLX - RTS +ARGSHND PHX + PHY + PHA + CPY #$00 + BNE :HASFILE + CMP #$00 ; Y=0,A=0 => current file sys + BNE :S1 + PLA + LDA #105 ; 105=AppleFS filing system + PLY + PLX + RTS -:S1 CMP #$01 ; Y=0,A=1 => addr of CLI - BNE :S2 - LDA FSCMDLINE+0 - STA $00,X - LDA FSCMDLINE+1 - STA $01,X - LDA #$FF - STA $02,X - STA $03,X - JMP OSARGSDONE ; Implemented +:S1 CMP #$01 ; Y=0,A=1 => addr of CLI + BNE :S2 + LDA FSCMDLINE+0 + STA $00,X + LDA FSCMDLINE+1 + STA $01,X + LDA #$FF + STA $02,X + STA $03,X + JMP OSARGSDONE ; Implemented -:S2 CMP #$FF ; Y=0,A=FF => flush all files - BNE :IEXIT -* >>> WRTMAIN -* STZ MOSFILE ; Zero means flush all -* >>> WRTAUX - JMP :FLUSH -:IEXIT JMP :EXIT ; Exit preserved +:S2 CMP #$FF ; Y=0,A=FF => flush all files + BNE :IEXIT + JMP :FLUSH +:IEXIT JMP :EXIT ; Exit preserved -:HASFILE -* >>> WRTMAIN -* STY MOSFILE ; File ref num -* STX MOSFILE+1 ; Pointer to ZP control block -* >>> WRTAUX - CMP #$00 ; Y!=0,A=0 => read seq ptr - BNE :S3 -* >>> WRTMAIN -* STZ MOSFILE+2 ; 0 means get pos -* >>> WRTAUX - TXA - >>> XF2MAIN,TELL ; A=ZP, Y=channel +:HASFILE CMP #$00 ; Y!=0,A=0 => read seq ptr + BNE :S3 + TXA + >>> XF2MAIN,TELL ; A=ZP, Y=channel -:S3 CMP #$01 ; Y!=0,A=1 => write seq ptr - BNE :S4 - >>> WRTMAIN - STY GMARKPL+1 ; Write to MLI control block - LDA $00,X - STA GMARKPL+2 - LDA $01,X - STA GMARKPL+3 - LDA $02,X - STA GMARKPL+4 - >>> WRTAUX - >>> XF2MAIN,SEEK ; A=???, Y=channel +:S3 CMP #$01 ; Y!=0,A=1 => write seq ptr + BNE :S4 + >>> WRTMAIN + STY GMARKPL+1 ; Write to MLI control block + LDA $00,X + STA GMARKPL+2 + LDA $01,X + STA GMARKPL+3 + LDA $02,X + STA GMARKPL+4 + >>> WRTAUX + >>> XF2MAIN,SEEK ; A=???, Y=channel -:S4 CMP #$02 ; Y!=0,A=2 => read file len - BNE :S5 -* >>> WRTMAIN -* STA MOSFILE+2 ; Non-zero means get len -* >>> WRTAUX - TXA - >>> XF2MAIN,SIZE ; A=ZP, Y=channel +:S4 CMP #$02 ; Y!=0,A=2 => read file len + BNE :S5 + TXA + >>> XF2MAIN,SIZE ; A=ZP, Y=channel -:S5 CMP #$FF ; Y!=0,A=FF => flush file - BNE :EXIT -:FLUSH >>> XF2MAIN,FLUSH +:S5 CMP #$FF ; Y!=0,A=FF => flush file + BNE :EXIT +:FLUSH >>> XF2MAIN,FLUSH -:EXIT PLA ; Unimplemented - PLY - PLX - RTS +:EXIT PLA ; Unimplemented + PLY + PLX + RTS -OSARGSRET >>> ENTAUX - JSR CHKERROR -OSARGSDONE PLA - LDA #0 ; Implemented - PLY - PLX - RTS +OSARGSRET >>> ENTAUX + JSR CHKERROR +OSARGSDONE PLA + LDA #0 ; Implemented + PLY + PLX + RTS * OSFILE - perform actions on entire files/objects @@ -211,72 +188,50 @@ OSARGSDONE PLA * XY preserved * control block updated * -OSFILEMIN EQU $FF ; $FF=LOAD -OSFILEMAX EQU $08 ; $08=MKDIR +OSFILEMIN EQU $FF ; $FF=LOAD +OSFILEMAX EQU $08 ; $08=MKDIR -FILEHND PHX - PHY - PHA - CLC - ADC #256-OSFILEMIN - CMP #OSFILEMAX+257-OSFILEMIN ; NB: LtoR evaluation - BCS FILEIGNORE +FILEHND PHX + PHY + PHA + CLC + ADC #256-OSFILEMIN + CMP #OSFILEMAX+257-OSFILEMIN ; NB: LtoR evaluation + BCS FILEIGNORE - STX FSCTRL+0 ; FSCTRL=>control block - STY FSCTRL+1 - LDA (FSCTRL) ; XY=>filename - TAX - LDY #$01 - LDA (FSCTRL),Y - TAY - JSR PARSNAME ; Copy filename->MOSFILE + STX FSCTRL+0 ; FSCTRL=>control block + STY FSCTRL+1 + LDA (FSCTRL) ; XY=>filename + TAX + LDY #$01 + LDA (FSCTRL),Y + TAY + JSR PARSNAME ; Copy filename->MOSFILE - LDY #$11 - >>> WRTMAIN -:L1 LDA (FSCTRL),Y ; Copy control block to auxmem - STA FILEBLK,Y - DEY - BPL :L1 - >>> WRTAUX - PLA ; Get action back - >>> XF2MAIN,CALLFILE - -* BEQ :SAVE ; A=00 -> SAVE -* CMP #$FF -* BEQ :LOAD ; A=FF -> LOAD -* CMP #$06 -* BEQ :DELETE ; A=06 -> DELETE -* BCC :JMPINFO ; A=01-05 -> INFO -* CMP #$08 -* BEQ :MKDIR ; A=08 -> MKDIR -* -* PLY ; Not implemented, return unchanged -* PLX -* RTS -* -*:JMPINFO JMP :INFO -*:SAVE >>> XF2MAIN,SAVEFILE -*:LOAD >>> XF2MAIN,LOADFILE -*:DELETE >>> XF2MAIN,DELFILE -*:INFO >>> XF2MAIN,INFOFILE -*:MKDIR >>> XF2MAIN,MAKEDIR + LDY #$11 + >>> WRTMAIN +:L1 LDA (FSCTRL),Y ; Copy control block to auxmem + STA FILEBLK,Y + DEY + BPL :L1 + >>> WRTAUX + PLA ; Get action back + >>> XF2MAIN,CALLFILE * On return here, A<$20 return to caller, A>$1F ProDOS error -OSFILERET >>> ENTAUX - JSR CHKERROR ; Check if error returned - PHA - LDY #$11 ; Copy updated control block back -:L3 -* LDA AUXBLK,Y ; Mainmem left it in AUXBLK - LDA OSFILECB,Y ; Mainmem left it in OSFILECB - STA (FSCTRL),Y - DEY - BPL :L3 +OSFILERET >>> ENTAUX + JSR CHKERROR ; Check if error returned + PHA + LDY #$11 ; Copy updated control block back +:L3 LDA OSFILECB,Y ; Mainmem left it in OSFILECB + STA (FSCTRL),Y + DEY + BPL :L3 -FILEIGNORE PLA ; Returned object type - PLY ; No error, return to caller - PLX - RTS +FILEIGNORE PLA ; Returned object type + PLY ; No error, return to caller + PLX + RTS * FSC Command Table @@ -284,51 +239,51 @@ FILEIGNORE PLA ; Returned object type * These are commands specific to the filing system that can't be * called via OSFILE, OSFSC, etc. * -FSCCOMMAND ASC 'CHDIR' - DB $80 - DW FSCCHDIR-1 ; Change directory, LPTR=>params - ASC 'CD' - DB $80 - DW FSCCHDIR-1 ; Change directory, LPTR=>params - ASC 'DIR' - DB $80 - DW FSCCHDIR-1 ; Change directory, LPTR=>params - ASC 'DRIVE' - DB $80 - DW FSCDRIVE-1 ; Select drive, LPTR=>params - ASC 'FREE' - DB $80 - DW FSCFREE-1 ; FREE , LPTR=>params - ASC 'ACCESS' - DB $80 - DW FSCACCESS-1 ; ACCESS , LPTR=>params - ASC 'TITLE' - DB $80 - DW FSCTITLE-1 ; TITLE () , LPTR=>params - ASC 'DESTROY' - DB $80 - DW FSCDESTROY-1 ; DESTROY <objlist>, LPTR=>params - ASC 'COPY' - DB $80 - DW FSCCOPY-1 ; COPY <source> <dest>, LPTR=>params +FSCCOMMAND ASC 'CHDIR' + DB $80 + DW FSCCHDIR-1 ; Change directory, LPTR=>params + ASC 'CD' + DB $80 + DW FSCCHDIR-1 ; Change directory, LPTR=>params + ASC 'DIR' + DB $80 + DW FSCCHDIR-1 ; Change directory, LPTR=>params + ASC 'DRIVE' + DB $80 + DW FSCDRIVE-1 ; Select drive, LPTR=>params + ASC 'FREE' + DB $80 + DW FSCFREE-1 ; FREE <drive>, LPTR=>params + ASC 'ACCESS' + DB $80 + DW FSCACCESS-1 ; ACCESS <objlist> <access>, LPTR=>params + ASC 'TITLE' + DB $80 + DW FSCTITLE-1 ; TITLE (<drive>) <title>, LPTR=>params + ASC 'DESTROY' + DB $80 + DW FSCDESTROY-1 ; DESTROY <objlist>, LPTR=>params + ASC 'COPY' + DB $80 + DW FSCCOPY-1 ; COPY <source> <dest>, LPTR=>params * - DB $FF ; Terminator + DB $FF ; Terminator * FSC Dispatch Table ******************** -FSCDISPATCH DW FSCOPT-1 ; A=0 - *OPT - DW CHKEOF-1 ; A=1 - Read EOF - DW FSCRUN-1 ; A=2 - */filename - DW FSC03-1 ; A=3 - *command - DW FSCRUN-1 ; A=4 - *RUN - DW FSCCAT-1 ; A=5 - *CAT - DW FSCUKN-1 ; A=6 - DW FSCUKN-1 ; A=7 - DW FSCUKN-1 ; A=8 - DW FSCCAT-1 ; A=9 - *EX - DW FSCCAT-1 ; A=10 - *INFO - DW FSCUKN-1 ; A=11 - DW FSCRENAME-1 ; A=12 - *RENAME +FSCDISPATCH DW FSCOPT-1 ; A=0 - *OPT + DW CHKEOF-1 ; A=1 - Read EOF + DW FSCRUN-1 ; A=2 - */filename + DW FSC03-1 ; A=3 - *command + DW FSCRUN-1 ; A=4 - *RUN + DW FSCCAT-1 ; A=5 - *CAT + DW FSCUKN-1 ; A=6 + DW FSCUKN-1 ; A=7 + DW FSCUKN-1 ; A=8 + DW FSCCAT-1 ; A=9 - *EX + DW FSCCAT-1 ; A=10 - *INFO + DW FSCUKN-1 ; A=11 + DW FSCRENAME-1 ; A=12 - *RENAME * OSFSC - miscellanous file system calls ***************************************** @@ -338,756 +293,616 @@ FSCDISPATCH DW FSCOPT-1 ; A=0 - *OPT * A=0 if implemented * X,Y=any return values * -FSCHND CMP #13 - BCS FSCUKN - STA FSAREG - STX FSXREG - STY FSYREG - ASL A - TAX - LDA FSCDISPATCH+1,X - PHA - LDA FSCDISPATCH+0,X - PHA - LDX FSXREG - LDA FSAREG - RTS - -* CMP #$00 -* BEQ FSOPT ; A=0 - *OPT -* CMP #$01 -* BEQ CHKEOF ; A=1 - Read EOF -* CMP #$02 -* BEQ FSCRUN ; A=2 - */filename -* CMP #$03 -* BEQ FSC03 ; A=3 - *command -* CMP #$04 -* BEQ FSCRUN ; A=4 - *RUN -* CMP #$05 -* BEQ JMPCAT ; A=5 - *CAT -* CMP #$09 -* BEQ JMPCAT ; A=9 - *EX -* CMP #$0A -* BEQ JMPCAT ; A=10 - *INFO -* CMP #$0C -* BEQ FSCREN ; A=12 - *RENAME +FSCHND CMP #13 + BCS FSCUKN + STA FSAREG + STX FSXREG + STY FSYREG + ASL A + TAX + LDA FSCDISPATCH+1,X + PHA + LDA FSCDISPATCH+0,X + PHA +FSCNULL LDA FSAREG + LDY FSYREG + LDX FSXREG ; Set EQ/NE from X + RTS * OSFSC 00 - *OPT function -FSCOPT TXA - BEQ :OPT0 - LDA FSFLAG2 - AND :OPTMSK-1,X - EOR :OPTSET-0,Y - AND :OPTMSK-1,X - EOR :OPTSET-0,Y -:OPT0 STA FSFLAG2 -:OPTNULL RTS -:OPTMSK DB $3F,$CF,$F3,$FC -:OPTSET DB $00,$55,$AA,$FF +* Entered with A=$00 and EQ/NE from X +FSCOPT BEQ :OPT0 + LDA FSFLAG2 + AND :OPTMSK-1,X + EOR :OPTSET-0,Y + AND :OPTMSK-1,X + EOR :OPTSET-0,Y +:OPT0 STA FSFLAG2 +:OPTNULL RTS +:OPTMSK DB $3F,$CF,$F3,$FC +:OPTSET DB $00,$55,$AA,$FF -*FSCDRIVE JMP DRIVE -* -*FSCFREE JMP FREE -* -*FSCACCESS JMP ACCESS -* -*FSCDESTROY JMP DESTROY -* -*JMPCAT JMP FSCCAT - -FSCUKN PHA - LDA #<OSFSCM - LDY #>OSFSCM - JSR PRSTR - PLA -FSCNULL RTS -OSFSCM ASC 'OSFSC.' - DB $00 +FSCUKN + DO DEBUG + PHA + LDA #<OSFSCM + LDY #>OSFSCM + JSR PRSTR + PLA + FIN +FSCRET RTS + DO DEBUG +OSFSCM ASC 'OSFSC.' + DB $00 + FIN * OSFSC 01 - Read EOF function * X=File ref number * -CHKEOF -* >>> WRTMAIN -* STX MOSFILE ; File reference number -* >>> WRTAUX - TXA ; A=channel - >>> XF2MAIN,FILEEOF -CHKEOFRET >>> ENTAUX - TAX ; Return code -> X - TYA ; Y=any ProDOS error - JMP CHKERROR +CHKEOF TXA ; A=channel + >>> XF2MAIN,FILEEOF +CHKEOFRET >>> ENTAUX + TAX ; Return code -> X + TYA ; Y=any ProDOS error + JMP CHKERROR * OSFSC 03 - *command, fall back to *RUN command * XY=>command line * -FSC03 JSR XYtoLPTR - LDX #<FSCCOMMAND - LDY #>FSCCOMMAND - JSR CLILOOKUP - BEQ FSCNULL ; Matched, return - JSR LPTRtoXY ; Fall through to *RUN +FSC03 JSR XYtoLPTR + LDX #<FSCCOMMAND + LDY #>FSCCOMMAND + JSR CLILOOKUP + BEQ FSCRET ; Matched, return + JSR LPTRtoXY ; Fall through to *RUN + LDA #$FE ; Will become A=$05 -* OSFSC 04 - *RUN filename +* OSFSC 02 - */filename, OSFSC 04 - *RUN filename * XY=>pathname * -FSCRUN STX OSFILECB ; Pointer to filename - STY OSFILECB+1 - JSR XYtoLPTR -FSCRUNLP LDA (OSLPTR),Y ; Look for command line - INY - CMP #'!' - BCS FSCRUNLP - DEY - JSR SKIPSPC - JSR LPTRtoXY - STX FSCMDLINE+0 ; Set CMDLINE=>command line - STY FSCMDLINE+1 ; Collected by OSARGS 1,0 - LDA #$FF ; OSFILE load flag - STA OSFILECB+6 ; Use file's address - LDX #<OSFILECB ; Pointer to control block - LDY #>OSFILECB - JSR OSFILE - JSR :CALL - LDA #$00 ; A=0 on return - RTS -:CALL LDA #$01 ; A=1 - entering code - SEC ; Not from RESET - JMP (OSFILECB+6) ; Jump to EXEC addr - -* FSCREN JMP RENAME -* -* FSCCHDIR JMP CHDIR +FSCRUN PHA + STX OSFILECB+0 ; Pointer to filename + STY OSFILECB+1 + JSR XYtoLPTR +FSCRUNLP LDA (OSLPTR),Y ; Look for command line + INY + CMP #'!' + BCS FSCRUNLP + DEY + JSR SKIPSPC + JSR LPTRtoXY + STX FSCMDLINE+0 ; Set CMDLINE=>command line + STY FSCMDLINE+1 ; Collected by OSARGS 1,0 + PLA + EOR #$FB ; Convert $FE->$05, $02/$04->$Fx + BMI :FSCRUN2 ; *RUN, go direct to LOAD + JSR :FSCCALL ; Do an initial INFO + DEC A ; $01->$00 + BEQ :FSCRUN2 ; A file, load and run it + JMP FSCNULL ; Not a file, return all preserved +:FSCRUN2 LDA #$FF ; A=LOAD + STA OSFILECB+6 ; Use file's address + JSR :FSCCALL ; LOAD the file + JSR :CALLCODE ; Call the loaded code + LDA #$00 ; A=0 on return + RTS +:FSCCALL LDX #<OSFILECB ; Pointer to control block + LDY #>OSFILECB + JMP OSFILE +:CALLCODE LDA #$01 ; A=1 - entering code + SEC ; Not from RESET + JMP (OSFILECB+6) ; Jump to EXEC addr * Display catalog entries and info * A=5 *CAT, A=9 *EX, A=10 *INFO * XY=>pathname * -FSCCAT EOR #$06 - CLC - ROR A ; 01100000=*CAT - ROR A ; 11100000=*EX - ROR A ; 10000000=*INFO - ROR A ; b7=long info - STA FSAREG ; b6=multiple items - JSR PARSNAME ; Copy filename->MOSFILE - LDA FSAREG ; Get ARG back - >>> XF2MAIN,CATALOG -STARCATRET >>> ENTAUX - JSR CHKERROR ; See if error occurred - JSR FORCENL - LDA #0 ; 0=OK - RTS +FSCCAT EOR #$06 + CLC + ROR A ; 01100000=*CAT + ROR A ; 11100000=*EX + ROR A ; 10000000=*INFO + ROR A ; b7=long info + STA FSAREG ; b6=multiple items + JSR PARSNAME ; Copy filename->MOSFILE + LDA FSAREG ; Get ARG back + >>> XF2MAIN,CATALOG +STARCATRET >>> ENTAUX + JSR CHKERROR ; See if error occurred + JSR FORCENL + LDA #0 ; 0=OK + RTS * Print one block of a catalog. Called by CATALOG * Block is in AUXBLK -PRONEBLK >>> ENTAUX -* - LDA #<AUXBLK+4 ; FSPTR1=>first entry - STA FSPTR1+0 - LDA #>AUXBLK+4 - STA FSPTR1+1 - LDA #13 ; Max 13 entries per block - STA FSNUM -:CATLP LDY #$00 - LDA (FSPTR1),Y ; Get storage type - CMP #$E0 -* PHP - BCC :NOTKEY ; Not a key block - -* LDA AUXBLK+4 ; Get storage type -* AND #$E0 ; Mask 3 MSBs -* CMP #$E0 -* BNE :NOTKEY ; Not a key block +PRONEBLK >>> ENTAUX + LDA #<AUXBLK+4 ; FSPTR1=>first entry + STA FSPTR1+0 + LDA #>AUXBLK+4 + STA FSPTR1+1 + LDA #13 ; Max 13 entries per block + STA FSNUM +:CATLP LDY #$00 + LDA (FSPTR1),Y ; Get storage type + CMP #$E0 + BCC :NOTKEY ; Not a key block * Print directory name - LDA #<:DIRM - LDY #>:DIRM - JSR PRSTR - SEC -:NOTKEY -* LDA #$00 -*:L1 PHA -* PHP - JSR PRONEENT ; CC=entry, CS=header -* PLP -* BCC :L1X -* JSR OSNEWL -*:L1X - CLC ; Step to next entry - LDA FSPTR1+0 - ADC #$27 - STA FSPTR1+0 - LDA FSPTR1+1 - ADC #$00 - STA FSPTR1+1 - DEC FSNUM - BNE :CATLP ; Loop for all entries - -* PLA -* INC -* CMP #13 ; Number of dirents in block -* CLC -* BNE :L1 - - >>> XF2MAIN,CATALOGRET -:DIRM ASC 'Directory: ' - DB $00 + LDA #<:DIRM + LDY #>:DIRM + JSR PRSTR + SEC +:NOTKEY JSR PRONEENT ; CC=entry, CS=header + CLC ; Step to next entry + LDA FSPTR1+0 + ADC #$27 + STA FSPTR1+0 + LDA FSPTR1+1 + ADC #$00 + STA FSPTR1+1 + DEC FSNUM + BNE :CATLP ; Loop for all entries + >>> XF2MAIN,CATALOGRET +:DIRM ASC 'Directory: ' + DB $00 * Print a single directory entry * On entry: A = dirent index in AUXBLK * CC=entry, CS=header -PRONEENT -* PHP -* TAX -* LDA #<AUXBLK+4 ; Skip pointers -* STA ZP3 -* LDA #>AUXBLK+4 -* STA ZP3+1 -*:L1 CPX #$00 -* BEQ :S1 -* CLC -* LDA #$27 ; Size of dirent -* ADC ZP3 -* STA ZP3 -* LDA #$00 -* ADC ZP3+1 -* STA ZP3+1 -* DEX -* BRA :L1 -:S1 LDY #$00 ; Characters printed - LDA (FSPTR1),Y - AND #$0F ; Len of filename - BEQ :CATEXIT ; Inactive entry - PHP - TAX +PRONEENT LDY #$00 ; Characters printed + LDA (FSPTR1),Y + AND #$0F ; Len of filename + BEQ NULLENT ; Inactive entry + PHP + TAX +:L2 INY + LDA (FSPTR1),Y + JSR OSWRCH ; Print filename + DEX + BNE :L2 +:S2 PLP + BCS :EXITHDR ; Header entry, no info + JSR PRSPACES ; Pad after filename + BIT FSAREG + BMI :CATINFO ; Display object info + JMP PRACCESS +:EXITHDR JMP OSNEWL -:L2 INY - LDA (FSPTR1),Y - JSR OSWRCH ; Print filename - DEX - BNE :L2 +* Print object catalog info +:CATINFO LDY #$21 + LDX #3 + LDA #0 + JSR PRADDR0 + LDA #'+' + JSR OSWRCH + LDY #$17 + JSR PRADDR + JSR PRSPACE + JSR PRACCESS + BIT FSFLAG2 + BMI CATLONG ; *OPT 1,2 - detailed EX display + LDY #$0A +PRSPACES JSR PRSPACE + INY + CPY #$10 + BCC PRSPACES +NULLENT RTS -* LDY #$01 -*:L2 CPX #$00 -* BEQ :S2 -* LDA (FSPTR1),Y -* JSR OSWRCH -* DEX -* INY -* BRA :L2 +* Print extended catalog info +CATLONG LDY #$21 + JSR PRDATETIME + LDY #$18 + JSR PRDATETIME + JMP OSNEWL +PRDATETIME JSR PRSPACE + JSR PRSPACE + LDA (FSPTR1),Y + PHA + AND #$1F + JSR PRDECSLH ; Day + INY + LDA (FSPTR1),Y + ASL A + PLA + ROL A + ROL A + ROL A + ROL A + AND #$0F + JSR PRDECSLH ; Month + LDA (FSPTR1),Y + PHA + CMP #80 + LDA #$19 + BCS :CENTURY + LDA #$20 +:CENTURY JSR PRHEX ; Century + PLA + LSR A + JSR PRDEC ; Year + JSR PRSPACE + INY + INY + LDA (FSPTR1),Y + JSR PRDEC ; Hour + LDA #$3A + JSR OSWRCH + DEY + LDA (FSPTR1),Y ; Minute +PRDEC TAX + LDA #$99 + SED +:PRDECLP CLC + ADC #$01 + DEX + BPL :PRDECLP + CLD + JMP PRHEX +PRDECSLH JSR PRDEC + LDA #'/' + JMP OSWRCH -:S2 PLP - BCS :EXITHDR ; Header entry, no info - JSR PRSPACES +* Print object access string +PRACCESS LDX #$04 ; Offset to chars + LDY #$1E + LDA (FSPTR1),Y + PHA + LDY #$00 ; Chars printed + LDA (FSPTR1),Y + CMP #$D0 + JSR :PRACCCHR ; 'D' + PLA + CPY #$01 ; Has 'D' been printed? + PHP + PHA + EOR #$C0 + CMP #$40 + JSR :PRACCCHR ; 'L' + PLA + PLP + BCS :PRACCDONE ; Dir, skip 'WR' + ROR A + PHP + ROR A + JSR :PRACCCHR ; 'W' + PLP + JSR :PRACCCHR ; 'R' +:PRACCDONE LDA #$20 +:PRACCLP JSR :PRSPACE + CPY #$04 + BCC :PRACCLP +:PRSKIP RTS +:PRACCCHR DEX + BCC :PRSKIP + LDA ACCESSCHRS,X +:PRSPACE INY + JMP OSWRCH +ACCESSCHRS ASC 'RWLD' -* LDA #$20 -* BIT FSAREG -* BPL :S2LP -* INY -* INY -* INY -* INY -*:S2LP JSR OSWRCH -* INY -* CPY #$10 -* BCC :S2LP - - BIT FSAREG - BMI :CATINFO ; Display object info - JMP PRACCESS -:EXITHDR JMP OSNEWL - PLP -:CATEXIT RTS - -* BPL :EXIT -:CATINFO LDY #$21 - LDX #3 - LDA #0 - JSR PRADDR0 - LDA #'+' - JSR OSWRCH - LDY #$17 - JSR PRADDR - JSR PRSPACE - JSR PRACCESS - BIT FSFLAG2 - BVS CATLONG - LDY #$0A -PRSPACES JSR PRSPACE - INY - CPY #$10 - BCC PRSPACES - RTS - -CATLONG LDY #$21 - JSR PRDATETIME - LDY #$18 - JSR PRDATETIME - JMP OSNEWL -PRDATETIME JSR PRSPACE - JSR PRSPACE - LDA (FSPTR1),Y - PHA - AND #$1F - JSR PRDECSLH ; Day - INY - LDA (FSPTR1),Y - ASL A - PLA - ROL A - ROL A - ROL A - ROL A - AND #$0F - JSR PRDECSLH ; Month - LDA (FSPTR1),Y - PHA - CMP #80 - LDA #$19 - BCS :CENTURY - LDA #$20 -:CENTURY JSR PRHEX ; Century - PLA - LSR A - JSR PRDEC ; Year - JSR PRSPACE - INY - INY - LDA (FSPTR1),Y - JSR PRDEC ; Hour - LDA #$3A - JSR OSWRCH - DEY - LDA (FSPTR1),Y ; Minute -PRDEC TAX - LDA #$99 - SED -:PRDECLP CLC - ADC #$01 - DEX - BPL :PRDECLP - CLD - JMP PRHEX -PRDECSLH JSR PRDEC - LDA #'/' - JMP OSWRCH - -* LDY #$00 -* LDA (FSPTR1),Y -* AND #$F0 -* CMP #$D0 -* BNE :NOTDIR -* LDA #'D' -* JSR OSWRCH -* JSR PRLOCK -* JMP OSNEWL -*:NOTDIR JSR PRLOCK -* LDA (FSPTR1),Y -* LSR A -* PHP -* AND #1 -* BEQ :NOWR -* LDA #'W' -* JSR OSWRCH -*:NOWR PLP -* BCC :NOWR -* LDA #'R' -* JSR OSWRCH -*:NORD -* JSR PRSPACE -* LDY #$22 -* LDX #2 -* JSR PRADDRLP -:EXITHDR JMP OSNEWL - -PRACCESS LDX #$04 ; Offset to chars - LDY #$1E - LDA (FSPTR1),Y - PHA - LDY #$00 ; Chars printed - LDA (FSPTR1),Y - CMP #$D0 - JSR :PRACCCHR ; 'D' - PLA - CPY #$01 ; Has 'D' been printed? - PHP - PHA - EOR #$C0 - CMP #$40 - JSR :PRACCCHR ; 'L' - PLA - PLP - BCS :PRACCDONE ; Dir, skip 'WR' - ROR A - PHP - ROR A - JSR :PRACCCHR ; 'W' - PLP - JSR :PRACCCHR ; 'R' -:PRACCDONE LDA #$20 -:PRACCLP JSR :PRSPACE - CPY #$04 - BCC :PRACCLP -:PRSKIP RTS -:PRACCCHR DEX - BCC :PRSKIP - LDA ACCESSCHRS,X -:PRSPACE INY - JMP OSWRCH -ACCESSCHRS ASC 'RWLD' - - -*PRLOCK LDY #$1E -* LDA (FSPTR1),Y -* CMP #$40 -* BCS PRADDROK -* LDA #'L' -* JMP OSWRCH - -PRADDR LDX #3 -PRADDRLP LDA (FSPTR1),Y -PRADDR0 JSR OUTHEX - DEY - DEX - BNE PRADDRLP -PRADDROK RTS -PRSPACE LDA #' ' -PRCHAR JMP OSWRCH +* Print object addresses +PRADDR LDX #3 +PRADDRLP LDA (FSPTR1),Y +PRADDR0 JSR OUTHEX + DEY + DEX + BNE PRADDRLP +PRADDROK RTS +PRSPACE LDA #' ' +PRCHAR JMP OSWRCH * OSFSC $0C - RENAME function -* XY=>pathname -FSCRENAME -RENAME JSR PARSNAME ; Copy Arg1->MOSFILE - CMP #$00 ; Length of arg1 - BEQ :SYNTAX - JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 - CMP #$00 ; Length of arg2 - BEQ :SYNTAX - >>> XF2MAIN,RENFILE -:SYNTAX BRK - DB $DC - ASC 'Syntax: RENAME <objspec> <objspec>' - BRK +* XY=>pathnames +* +FSCRENAME JSR PARSNAME ; Copy Arg1->MOSFILE + BEQ :SYNTAX ; No <oldname> + JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 + BEQ :SYNTAX ; No <newname> + >>> XF2MAIN,RENFILE +:SYNTAX BRK + DB $DC + ASC 'Syntax: RENAME <oldspec> <newspec>' + BRK +* ProDOS returns $40 (Bad filename) for bad renames. +* Not easy to seperate out, so leave as Bad filename error. RENRET - >>> ENTAUX - JSR CHKERROR - LDA #$00 - RTS +COPYRET +CHDIRRET >>> ENTAUX + JMP CHKERROR * Handle *COPY command * LPTR=>parameters string * -FSCCOPY JSR PARSLPTR -* COPY JSR PARSNAME ; Copy Arg1->MOSFILE - CMP #$00 ; Length of arg1 - BEQ :SYNTAX - JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 - CMP #$00 ; Length of arg2 - BEQ :SYNTAX - >>> XF2MAIN,COPYFILE -:SYNTAX BRK - DB $DC - ASC 'Syntax: COPY <listspec> <*objspec*>' - BRK -COPYRET - >>> ENTAUX - JSR CHKERROR - LDA #$00 - RTS +FSCCOPY JSR PARSLPTR ; Copy Arg1->MOSFILE + BEQ :SYNTAX ; No <source> + JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 + BEQ :SYNTAX ; No <dest> + >>> XF2MAIN,COPYFILE ; Do the heavy lifting +:SYNTAX BRK + DB $DC + ASC 'Syntax: COPY <sourcespec> <destspec>' + BRK * Handle *DIR/*CHDIR/*CD (directory change) command * LPTR=>parameters string * -FSCCHDIR JSR PARSLPTR -* CHDIR JSR PARSNAME ; Copy filename->MOSFILE - CMP #$00 ; Filename length - BNE :HASPARM - BRK - DB $DC - ASC 'Syntax: DIR <*objspec*>' - BRK -:HASPARM >>> XF2MAIN,SETPFX +FSCCHDIR JSR PARSLPTR ; Copy filename->MOSFILE + BEQ ERRCHDIR ; No <dir> +FSCCHDIR2 >>> XF2MAIN,SETPFX +ERRCHDIR BRK + DB $DC + ASC 'Syntax: DIR <dir>' + BRK -* Handle *DRIVE command, which is similar +* Handle *DRIVE command, which is similar to CHDIR * LPTR=>parameters string * -FSCDRIVE -DRIVE LDA (OSLPTR),Y ; First char - CMP #$3A ; Colon - BNE :ERR - JSR PARSLPTR ; Copy arg->MOSFILE - CMP #$03 ; Check 3 char arg - BEQ :HASPARM -:ERR BRK - DB $DC - ASC 'Syntax: DRIVE <drv> (eg: DRIVE :61)' - BRK -:HASPARM >>> XF2MAIN,SETPFX - -CHDIRRET - >>> ENTAUX - JSR CHKERROR - CMP #$00 - BEQ :EXIT - BRK - DB $CE ; Bad directory - ASC 'Bad dir' - BRK -:EXIT RTS +FSCDRIVE LDA (OSLPTR),Y ; First char + CMP #$3A ; Colon + BNE :SYNTAX + JSR PARSLPTR ; Copy arg->MOSFILE + CMP #$03 ; Check 3 char arg + BEQ FSCCHDIR2 ; Pass on as CHDIR +:SYNTAX BRK + DB $DC + ASC 'Syntax: DRIVE <drv> (eg: DRIVE :61)' + BRK * Handle *FREE command * LPTR=>parameters string +* Also allows *FREE<cr> for current drive * FSCFREE -FREE LDA (OSLPTR),Y ; First char - CMP #$3A ; Colon - BNE :ERR - JSR PARSLPTR ; Copy arg->MOSFILE - CMP #$03 ; Check 3 char arg - BEQ :HASPARM -:ERR BRK - DB $DC - ASC 'Syntax: FREE <drv> (eg: FREE :61)' - BRK -:HASPARM >>> XF2MAIN,DRVINFO +* LDA (OSLPTR),Y ; First char +* CMP #$3A ; Colon +* BNE :ERR + JSR PARSLPTR ; Copy arg->MOSFILE + BEQ :HASPARM ; *FREE <cr> + CMP #$03 ; Check 3 char arg + BEQ :HASPARM +:ERR BRK + DB $DC + ASC 'Syntax: FREE (<drv>) (eg: FREE :61)' + BRK +:HASPARM >>> XF2MAIN,DRVINFO FREERET - >>> ENTAUX - JSR CHKERROR - CMP #$00 - BEQ :NOERR - BRK - DB $CE ; Bad directory - ASC 'Bad dir' - BRK -:NOERR SEC - LDA AUXBLK+2 ; LSB of total blks - SBC AUXBLK+0 ; LSB of blocks used - TAX - LDA AUXBLK+3 ; MSB of total blks - SBC AUXBLK+1 ; MSB of blocks used - TAY - LDA #$00 ; *TO DO* b16-b23 of free + >>> ENTAUX + JSR CHKERROR + CMP #$00 + BEQ :NOERR + BRK + DB $CE ; Bad directory + ASC 'Bad dir' + BRK - JSR :FREEDEC ; Print 'AAYYXX blocks aaayyyxxx bytes ' - LDX #<:FREE - LDY #>:FREE - JSR OUTSTR ; Print 'free'<nl> - LDX AUXBLK+0 ; Blocks used - LDY AUXBLK+1 - LDA #$00 ; *TO DO* b16-b23 of used - JSR :FREEDEC ; Print 'AAYYXX blocks aaayyyxxx bytes ' - LDX #<:USED - LDY #>:USED - JMP OUTSTR ; Print 'used'<nl> +* Disk size is two-byte 512-byte block count +* Maximum disk size is $FFFF blocks = 1FFFF00 bytes = 33554176 bytes = 32M-512 +:NOERR SEC + LDA AUXBLK+2 ; LSB of total blocks + SBC AUXBLK+0 ; LSB of blocks used + TAX ; X=b0-b7 of blocks free + LDA AUXBLK+3 ; MSB of total blocks + SBC AUXBLK+1 ; MSB of blocks used + TAY ; Y=b8-b15 of blocks free + LDA #$00 ; A=b16-b23 of blocks free + JSR :FREEDEC ; Print 'AAYYXX blocks aaayyyxxx bytes ' + LDX #<:FREE + LDY #>:FREE + JSR OUTSTR ; Print 'free'<nl> -:FREEDEC STX FSNUM+1 - STY FSNUM+2 - STA FSNUM+3 -* What's the maximum number of blocks? + LDX AUXBLK+0 ; X=b0-b7 of blocks used + LDY AUXBLK+1 ; Y=b8-b15 of blocks used + LDA #$00 ; A=b16-b23 of blocks used + JSR :FREEDEC ; Print 'AAYYXX blocks aaayyyxxx bytes ' + LDX #<:USED + LDY #>:USED + JMP OUTSTR ; Print 'used'<nl> + +:FREEDEC STX FSNUM+1 + STY FSNUM+2 + STA FSNUM+3 * JSR PRHEX ; Blocks b16-b23 in hex - JSR PR2HEX ; Blocks b0-b15 in hex - LDX #<:BLOCKS - LDY #>:BLOCKS - JSR OUTSTR ; ' blocks ' - STZ FSNUM+0 ; FSNUM=blocks*512 - ASL FSNUM+1 - ROL FSNUM+2 - ROL FSNUM+3 - LDX #FSNUM ; X=>number to print - LDY #8 ; Y=pad up to 8 digits - JSR PRINTDEC ; Print it in decimal - LDX #<:BYTES - LDY #>:BYTES - JMP OUTSTR ; ' bytes ' -:BLOCKS ASC ' blocks ' - DB 0 -:BYTES ASC ' bytes ' - DB 0 -:FREE ASC 'free' - DB 13,0 -:USED ASC 'used' - DB 13,0 + JSR PR2HEX ; Blocks b0-b15 in hex + LDX #<:BLOCKS + LDY #>:BLOCKS + JSR OUTSTR ; ' blocks ' + STZ FSNUM+0 ; FSNUM=blocks*512 + ASL FSNUM+1 + ROL FSNUM+2 + ROL FSNUM+3 + LDX #FSNUM ; X=>number to print + LDY #8 ; Y=pad up to 8 digits + JSR PRINTDEC ; Print it in decimal + LDX #<:BYTES + LDY #>:BYTES + JMP OUTSTR ; ' bytes ' +:BLOCKS ASC ' blocks ' + DB 0 +:BYTES ASC ' bytes ' + DB 0 +:FREE ASC 'free' + DB 13,0 +:USED ASC 'used' + DB 13,0 * Handle *ACCESS command * LPTR=>parameters string * -FSCACCESS -ACCESS JSR PARSLPTR ; Copy filename->MOSFILE - CMP #$00 ; Filename length - BEQ :SYNTAX - JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 - >>> XF2MAIN,SETPERM -:SYNTAX BRK - DB $DC - ASC 'Syntax: ACCESS <listspec> <L|W|R>' - BRK +ACCESS +FSCACCESS JSR PARSLPTR ; Copy filename->MOSFILE + CMP #$00 ; Filename length + BEQ :SYNTAX + JSR PARSLPTR2 ; Copy Arg2->MOSFILE2 + >>> XF2MAIN,SETPERM +:SYNTAX BRK + DB $DC + ASC 'Syntax: ACCESS <listspec> <L|W|R>' + BRK -ACCRET >>> ENTAUX - JSR CHKERROR - LDA #$00 - RTS +ACCRET >>> ENTAUX + JSR CHKERROR + LDA #$00 + RTS * Handle *DESTROY command * LPTR=>parameters string * FSCDESTROY -DESTROY JSR PARSLPTR ; Copy filename->MOSFILE - CMP #$00 ; Filename length - BEQ :SYNTAX - >>> XF2MAIN,MULTIDEL -:SYNTAX BRK - DB $DC - ASC 'Syntax: DESTROY <listspec>' - BRK +DESTROY JSR PARSLPTR ; Copy filename->MOSFILE + CMP #$00 ; Filename length + BEQ :SYNTAX + >>> XF2MAIN,MULTIDEL +:SYNTAX BRK + DB $DC + ASC 'Syntax: DESTROY <listspec>' + BRK -DESTRET >>> ENTAUX - JSR CHKERROR - LDA #$00 - RTS +DESTRET >>> ENTAUX + JSR CHKERROR + LDA #$00 + RTS * Handle *TITLE command * LPTR=>parameters string * Syntax: *TITLE (<drive>) <title> * -FSCTITLE RTS +FSCTITLE RTS * Parse filename pointed to by XY * Write filename to MOSFILE in main memory * Returns length in A with EQ/NE set -PARSNAME JSR XYtoLPTR -PARSLPTR CLC ; Means parsing a filename - JSR GSINIT ; Init general string handling - PHP - SEI ; Disable IRQs - LDX #$00 ; Length -:L1 JSR GSREAD ; Handle next char - BCS :DONE - STA $C004 ; Write to main mem - STA MOSFILE+1,X - STA $C005 ; Write to aux mem - INX - BNE :L1 -:DONE STA $C004 ; Write to main mem - STX MOSFILE ; Length byte (Pascal) - STA $C005 ; Back to aux - PLP ; IRQs back as they were - TXA ; Return len in A - RTS +PARSNAME JSR XYtoLPTR +PARSLPTR CLC ; Means parsing a filename + JSR GSINIT ; Init general string handling + PHP + SEI ; Disable IRQs + LDX #$00 ; Length +:L1 JSR GSREAD ; Handle next char + BCS :DONE + STA $C004 ; Write to main mem + STA MOSFILE+1,X + STA $C005 ; Write to aux mem + INX + BNE :L1 +:DONE STA $C004 ; Write to main mem + STX MOSFILE ; Length byte (Pascal) + STA $C005 ; Back to aux + PLP ; IRQs back as they were + TXA ; Return len in A + RTS * Parse filename pointed to by (OSLPTR),Y * Write filename to MOSFILE2 in main memory * Returns length in A with EQ/NE set -PARSNAME2 JSR XYtoLPTR -PARSLPTR2 CLC ; Means parsing a filename - JSR GSINIT ; Init gen string handling - PHP - SEI ; Disable IRQs - LDX #$00 ; Length -:L1 JSR GSREAD ; Handle next char - BCS :DONE - STA $C004 ; Write to main mem - STA MOSFILE2+1,X - STA $C005 ; Write to aux mem - INX - BNE :L1 -:DONE STA $C004 ; Write to main mem - STX MOSFILE2 ; Length byte (Pascal) - STA $C005 ; Back to aux - PLP ; IRQs back as they were - TXA ; Return len in A -NOTERROR RTS +PARSNAME2 JSR XYtoLPTR +PARSLPTR2 CLC ; Means parsing a filename + JSR GSINIT ; Init gen string handling + PHP + SEI ; Disable IRQs + LDX #$00 ; Length +:L1 JSR GSREAD ; Handle next char + BCS :DONE + STA $C004 ; Write to main mem + STA MOSFILE2+1,X + STA $C005 ; Write to aux mem + INX + BNE :L1 +:DONE STA $C004 ; Write to main mem + STX MOSFILE2 ; Length byte (Pascal) + STA $C005 ; Back to aux + PLP ; IRQs back as they were + TXA ; Return len in A +NOTERROR RTS -ERRNOTFND LDA #$46 ; File not found +ERRNOTFND LDA #$46 ; File not found * Check returned code for return code or error code * A<$20 - return to user, A>$1F - generate error * -CHKERROR CMP #$20 - BCC NOTERROR +CHKERROR CMP #$20 + BCC NOTERROR MKERROR * IF FALSE - BIT $E0 - BPL MKERROR1 ; *DEBUG* - PHA - LDX #15 -MKERRLP LDA ERRMSG,X - STA $100,X - DEX - BPL MKERRLP - PLA - PHA - LSR A - LSR A - LSR A - LSR A - JSR ERRHEX - STA $108 - PLA - JSR ERRHEX - STA $109 - JMP $100 -ERRHEX AND #15 - CMP #10 - BCC ERRHEX1 - ADC #6 -ERRHEX1 ADC #48 - RTS -ERRMSG BRK - DB $FF - ASC 'ERR: $00' - BRK + BIT $E0 + BPL MKERROR1 ; *DEBUG* + PHA + LDX #15 +MKERRLP LDA ERRMSG,X + STA $100,X + DEX + BPL MKERRLP + PLA + PHA + LSR A + LSR A + LSR A + LSR A + JSR ERRHEX + STA $108 + PLA + JSR ERRHEX + STA $109 + JMP $100 +ERRHEX AND #15 + CMP #10 + BCC ERRHEX1 + ADC #6 +ERRHEX1 ADC #48 + RTS +ERRMSG BRK + DB $FF + ASC 'ERR: $00' + BRK * FIN * Translate ProDOS error code into BBC error -MKERROR1 CMP #$40 - BCS MKERROR2 - ORA #$30 ; <$40 -> $30-$3F -MKERROR2 SEC - SBC #$38 - CMP #$28 - BCC MKERROR3 ; $28-$30, $40-$5F - LDA #$27 ; Otherwise I/O error -MKERROR3 ASL A - TAX - LDA MKERROR4+1,X - PHA - LDA MKERROR4+0,X - PHA - PHP - RTI -MKERROR4 DW ERROR28,ERROR27,ERROR27,ERROR2B,ERROR27,ERROR27,ERROR2E,ERROR27 - DW ERROR40,ERROR41,ERROR42,ERROR43,ERROR44,ERROR45,ERROR46,ERROR47 - DW ERROR48,ERROR49,ERROR4A,ERROR4B,ERROR4C,ERROR4D,ERROR4E,ERROR4F - DW ERROR50,ERROR51,ERROR52,ERROR53,ERROR54,ERROR55,ERROR56,ERROR57 - DW ERROR27,ERROR27,ERROR5A,ERROR5B,ERROR27,ERROR5D,ERROR5E,ERROR27 +MKERROR1 CMP #$40 + BCS MKERROR2 + ORA #$30 ; <$40 -> $30-$3F +MKERROR2 SEC + SBC #$38 + CMP #$28 + BCC MKERROR3 ; $28-$30, $40-$5F + LDA #$27 ; Otherwise I/O error +MKERROR3 ASL A + TAX + LDA MKERROR4+1,X + PHA + LDA MKERROR4+0,X + PHA + PHP + RTI +MKERROR4 DW ERROR28,ERROR27,ERROR27,ERROR2B,ERROR2C,ERROR27,ERROR2E,ERROR27 + DW ERROR40,ERROR41,ERROR42,ERROR43,ERROR44,ERROR45,ERROR46,ERROR47 + DW ERROR48,ERROR49,ERROR4A,ERROR4B,ERROR4C,ERROR4D,ERROR4E,ERROR4F + DW ERROR50,ERROR51,ERROR52,ERROR53,ERROR54,ERROR55,ERROR56,ERROR57 + DW ERROR27,ERROR27,ERROR5A,ERROR27,ERROR27,ERROR27,ERROR5E,ERROR27 * $27 - I/O error (disk not formatted) * $28 - No device con'd (drive not present) Disk not present * $29 -(GSOS Driver is busy) * $2A - * $2B - Disk write protected. Disk write protected -* $2C -(GSOS bad byte count) +* $2C - Bad byte count - file too long File too long * $2D -(GSOS bad block number) * $2E - Disk switched Disk changed * $2F - Device is offline (drive empty/absent) * $40 - Invalid pathname syntax. Bad filename -* $41 -(Duplicate filename. split from $47) Is a directory) +* $41 -(Duplicate filename. split from $47) Is a directory * $42 - File Control Block table full. Too many open * $43 - Invalid reference number. Channel not open * $44 - Path not found. (Dir not found) File not found @@ -1107,86 +922,80 @@ MKERROR4 DW ERROR28,ERROR27,ERROR27,ERROR2B,ERROR27,ERROR27,ERROR2E,ERROR * $52 - Not a ProDOS disk. Disk not recognised * $53 - Invalid parameter. Invalid parameter * $54 -(Dir not empty when deleting, cf $4E) DEL: Dir not empty -* $55 - Volume Control Block table full. +* $55 - Volume Control Block table full. (Too many disks mounted) * $56 - Bad buffer address. * $57 - Duplicate volume. -* $58 - Bad volume bitmap. +* $58 - Bad volume bitmap/Not block device. * $59 -(GSOS File level out of range) * $5A - Bit map disk address is impossible. Sector not found * $5B -(GSOS Bad ChangePath pathname) * $5C -(GSOS Not executable file) -* $5D -(GSOS OS/FS not found) (EOF during load or save) Data lost -* $5E -(Couldn't open to save) Can't save +* $5D -(GSOS OS/FS not found) +* $5E -(Destination filename has wildcards) Wildcards * $5F -(GSOS Too many applications) * $60+ - (GSOS) * AcornOS ProDOS -ERROR28 DW $D200 - ASC 'Disk not present' ; $28 - No device detected/connected -ERROR2B DW $C900 - ASC 'Disk write protected' ; $2B - Disk write protected -ERROR2E DW $C800 - ASC 'Disk changed' ; $2E - Disk switched -ERROR40 DW $CC00 - ASC 'Bad filename' ; $40 - Invalid pathname syntax -ERROR41 DW $C400 - ASC 'Is a directory' ; $41 - Duplicate filename (split from $47) -ERROR42 DW $C000 - ASC 'Too many open' ; $42 - File Control Block table full -ERROR43 DW $DE00 - ASC 'Channel not open' ; $43 - Invalid reference number -ERROR44 ; $44 - Path not found -ERROR46 DW $D600 - ASC 'File not found' ; $46 - File not found -ERROR45 DW $D600 - ASC 'Disk not found' ; $45 - Volume directory not found -ERROR47 DW $C400 - ASC 'File exists' ; $47 - Duplicate filename (see also $41) -ERROR48 DW $C600 - ASC 'Disk full' ; $48 - Overrun error -ERROR49 DW $B300 - ASC 'Directory full' ; $49 - Volume directory full -ERROR4A ; $4A - Incompatible file format -ERROR4B ; $4B - Unsupported storage_type -ERROR52 DW $C800 - ASC 'Disk not recognised' ; $52 - Not a ProDOS disk -ERROR4C DW $DF00 - ASC 'End of file' ; $4C - End of file has been encountered -ERROR4D DW $C100 - ASC 'Not open for update' ; $4D - Position out of range -ERROR4E DW $BD00 - ASC 'Insufficient access' ; $4E - Access error (see also $4F) -ERROR4F DW $C300 - ASC 'Entry locked' ; $4F - Access error (split from $4E) -ERROR50 DW $C200 - ASC 'Can' - DB $27 - ASC 't - file open' ; $50 - File is open -ERROR51 DW $A800 - ASC 'Broken directory' ; $51 - Directory count error -ERROR53 DW $DC00 - ASC 'Invalid parameter' ; $53 - Invalid parameter -ERROR54 DW $D400 - ASC 'Directory not empty' ; $54 - Directory not empty (split from $4E) -ERROR55 DW $FF00 - ASC 'ProDOS: VCB full' ; $55 - Volume Control Block table full -ERROR56 DW $FF00 - ASC 'ProDOS: Bad addr' ; $56 - Bad buffer address -ERROR57 DW $FF00 - ASC 'ProDOS: Dup volm' ; $57 - Duplicate volume -ERROR5B ; spare -ERROR5A DW $FF00 - ASC 'Sector not found' ; $5A - Bit map disk address is impossible -ERROR5D DW $CA00 - ASC 'Data lost' ; $5D - EOF during LOAD or SAVE -ERROR5E DW $C000 - ASC 'Can' - DB $27 - ASC 't save' ; $5E - Couldn't open for save -ERROR27 DW $FF00 - ASC 'I/O error' ; $27 - I/O error - DB $00 - - - +ERROR28 DW $D200 + ASC 'Disk not present' ; $28 - No device detected/connected +ERROR2B DW $C900 + ASC 'Disk write protected'; $2B - Disk write protected +ERROR2C DW $C600 + ASC 'File too big' ; $2C - Too big to save +ERROR2E DW $C800 + ASC 'Disk changed' ; $2E - Disk switched +ERROR40 DW $CC00 + ASC 'Bad filename' ; $40 - Invalid pathname syntax +ERROR41 DW $C400 + ASC 'Is a directory' ; $41 - Duplicate filename (split from $47) +ERROR42 DW $C000 + ASC 'Too many open' ; $42 - File Control Block table full +ERROR43 DW $DE00 + ASC 'Channel not open' ; $43 - Invalid reference number +ERROR44 ; $44 - Path not found +ERROR46 DW $D600 + ASC 'File not found' ; $46 - File not found +ERROR45 DW $D600 + ASC 'Disk not found' ; $45 - Volume directory not found +ERROR47 DW $C400 + ASC 'File exists' ; $47 - Duplicate filename (see also $41) +ERROR48 DW $C600 + ASC 'Disk full' ; $48 - Overrun error +ERROR49 DW $B300 + ASC 'Directory full' ; $49 - Volume directory full +ERROR4A ; $4A - Incompatible file format +ERROR4B ; $4B - Unsupported storage_type +ERROR52 DW $C800 + ASC 'Disk not recognised' ; $52 - Not a ProDOS disk +ERROR4C DW $DF00 + ASC 'End of file' ; $4C - End of file has been encountered +ERROR4D DW $C100 + ASC 'Not open for update' ; $4D - Position out of range +ERROR4E DW $BD00 + ASC 'Insufficient access' ; $4E - Access error (see also $4F) +ERROR4F DW $C300 + ASC 'Entry locked' ; $4F - Access error (split from $4E) +ERROR50 DW $C200 + ASC 'Can' + DB $27 + ASC 't - file open' ; $50 - File is open +ERROR51 DW $A800 + ASC 'Broken directory' ; $51 - Directory count error +ERROR53 DW $DC00 + ASC 'Invalid parameter' ; $53 - Invalid parameter +ERROR54 DW $D400 + ASC 'Directory not empty' ; $54 - Directory not empty (split from $4E) +ERROR55 DW $FF00 + ASC 'ProDOS: VCB full' ; $55 - Volume Control Block table full +ERROR56 DW $FF00 + ASC 'ProDOS: Bad addr' ; $56 - Bad buffer address +ERROR57 DW $FF00 + ASC 'ProDOS: Dup volm' ; $57 - Duplicate volume +ERROR5A DW $FF00 + ASC 'Sector not found' ; $5A - Bit map disk address is impossible +ERROR5E DW $FD00 + ASC 'Wildcards' ; $5E - Can't use wildcards in dest filename +ERROR27 DW $FF00 + ASC 'I/O error' ; $27 - I/O error + DB $00 diff --git a/auxmem.init.s b/auxmem.init.s index d053224..a868acc 100644 --- a/auxmem.init.s +++ b/auxmem.init.s @@ -7,6 +7,8 @@ * BBC Micro 'virtual machine' in Apple //e aux memory *********************************************************** +MAXROM EQU $F9 ; Max sideways ROM number + ZP1 EQU $90 ; $90-$9f are spare Econet space ; so safe to use ZP2 EQU $92 @@ -123,23 +125,22 @@ MOSHIGH SEI DEX BPL :INITPG2 - JSR ROMINIT ; Initialize sideways ROM table - + JSR ROMINIT ; Build list of sideways ROMs JSR KBDINIT ; Returns A=startup MODE JSR VDUINIT ; Initialise VDU driver JSR PRHELLO LDA #7 JSR OSWRCH JSR OSNEWL - LDX MAXROM ; TEMP X=language to enter + LDX MAXROM ; TEMP X=language to enter CLC * OSBYTE $8E - Enter language ROM * X=ROM number to select * BYTE8E PHP ; Save CLC=RESET, SEC=Not RESET - JSR ROMSELECT ; Bring ROM X into memory - STX BYTEVARBASE+$FC ; Set current language ROM + JSR ROMSELECT ; Bring ROM X into memory + STX BYTEVARBASE+$FC ; Set current language ROM LDA #$00 STA FAULT+0 LDA #$80 @@ -156,27 +157,39 @@ BYTE8E PHP ; Save CLC=RESET, SEC=Not RESET * OSBYTE $8F - Issue service call * X=service call, Y=parameter * -SERVICE TAX ; Enter here with A=Service Num +SERVICE TAX ; Enter here with A=Service Num BYTE8F SERVICEX LDA $F4 - PHA ; Save current ROM + PHA ; Save current ROM + +* LDA $E0 ; *DEBUG* +* AND #$20 +* BEQ :SERVDEBUG +* TXA +* JSR PRHEX +* LDA OSLPTR+1 +* JSR PRHEX +* LDA OSLPTR+0 +* JSR PRHEX ; *DEBUG* +*:SERVDEBUG + TXA - LDX MAXROM ; Start at highest ROM -:SERVLP JSR ROMSELECT ; Bring it into memory + LDX MAXROM ; Start at highest ROM +:SERVLP JSR ROMSELECT ; Bring it into memory BIT $8006 - BPL :SERVSKIP ; No service entry - JSR $8003 ; Call service entry + BPL :SERVSKIP ; No service entry + JSR $8003 ; Call service entry TAX BEQ :SERVDONE -:SERVSKIP LDX $F4 ; Restore X=current ROM - DEX ; Step down to next - BPL :SERVLP ; Loop until ROM 0 done -:SERVDONE PLA ; Get caller's ROM back - PHX ; Save return from service call +:SERVSKIP LDX $F4 ; Restore X=current ROM + DEX ; Step down to next + BPL :SERVLP ; Loop until ROM 0 done +:SERVDONE PLA ; Get caller's ROM back + PHX ; Save return from service call TAX - JSR ROMSELECT ; Restore caller's ROM - PLX ; Get return value back - TXA ; Return in A and X and set EQ/NE + JSR ROMSELECT ; Restore caller's ROM + PLX ; Get return value back + TXA ; Return in A and X and set EQ/NE RTS @@ -191,12 +204,7 @@ BYTE00 BEQ BYTE00A ; OSBYTE 0,0 - generate error RTS ; %000x1xxx host type, 'A'pple BYTE00A BRK DB $F7 -HELLO ASC 'Applecorn MOS 2021-10-27' +HELLO ASC 'Applecorn MOS 2021-10-28' DB $00 ; Unify MOS messages -MAXROM DB $00 ; Index of highest sideways ROM - - - - diff --git a/auxmem.mosequ.s b/auxmem.mosequ.s index 79ae8cf..4078e53 100644 --- a/auxmem.mosequ.s +++ b/auxmem.mosequ.s @@ -16,31 +16,35 @@ * $E0-$EE Internal MOS workspace * $EF-$FF MOS API workspace -DEBUG EQU $E0 ; $E0 *TEST* Debug flag +* DEBUG EQU $00 ; $00=*OPT 255 debug code removed +DEBUG EQU $E0 ; $E0=*OPT 255 debug code included * ; $E1 -FSFLAG1 EQU $E2 ; $E2 -FSFLAG2 EQU $E3 ; $E3 HOSTFS *OPT settings -GSFLAG EQU $E4 ; $E4 GSREAD processing flags -GSCHAR EQU $E5 ; $E5 GSREAD accumulator -OSTEXT EQU $E6 ; $E6 => text string $E6 OSNUM+0 -MAXLEN EQU OSTEXT+2 ; $E8 $E8 OSNUM+2 -MINCHAR EQU OSTEXT+3 ; $E9 $E9 OSNUM+3 -MAXCHAR EQU OSTEXT+4 ; $EA $EA OSPAD -OSTEMP EQU $EB ; $EB $EB OSTEMP -OSKBD1 EQU $EC ; $EC kbd ws -OSKBD2 EQU OSKBD1+1 ; $ED kbd ws -OSKBD3 EQU OSKBD1+2 ; $EE kbd ws -OSAREG EQU $EF ; $EF A register -OSXREG EQU OSAREG+1 ; $F0 X register -OSYREG EQU OSXREG+1 ; $F1 Y register -OSCTRL EQU OSXREG ; $F0 (XY)=>control block -OSLPTR EQU $F2 ; $F2 => command line -OSROMNUM EQU $F4 ; $F4 current ROM -* -OSINTWS EQU $FA ; $FA IRQ ZP pointer, use when IRQs off -OSINTA EQU $FC ; $FC IRQ register A store -FAULT EQU $FD ; $FD Error message pointer -ESCFLAG EQU $FF ; $FF Escape status +FSFLAG1 EQU $E2 ; $E2 +FSFLAG2 EQU $E3 ; $E3 HOSTFS *OPT settings +GSFLAG EQU $E4 ; $E4 GSREAD processing flags +GSCHAR EQU $E5 ; $E5 GSREAD accumulator +OSTEXT EQU $E6 ; $E6 => text string $E6 OSNUM+0 +MAXLEN EQU OSTEXT+2 ; $E8 $E8 OSNUM+2 +MINCHAR EQU OSTEXT+3 ; $E9 $E9 OSNUM+3 +MAXCHAR EQU OSTEXT+4 ; $EA $EA OSPAD +OSTEMP EQU $EB ; $EB $EB OSTEMP +OSKBD1 EQU $EC ; $EC kbd ws +OSKBD2 EQU OSKBD1+1 ; $ED kbd ws +OSKBD3 EQU OSKBD1+2 ; $EE kbd ws +OSAREG EQU $EF ; $EF A register +OSXREG EQU OSAREG+1 ; $F0 X register +OSYREG EQU OSXREG+1 ; $F1 Y register +OSCTRL EQU OSXREG ; $F0 (XY)=>control block +OSLPTR EQU $F2 ; $F2 => command line +ROMID EQU $F4 ; $F4 current ROM +ROMTMP EQU $F5 ; $F5 +ROMPTR EQU $F6 ; $F6 => +* ; $F8 *TEMP* pseudo-SROM settings +* ; $F9 *TEMP* pseudo-SROM settings +OSINTWS EQU $FA ; $FA IRQ ZP pointer, use when IRQs off +OSINTA EQU $FC ; $FC IRQ register A store +FAULT EQU $FD ; $FD Error message pointer +ESCFLAG EQU $FF ; $FF Escape status * $0200-$0235 Vectors @@ -48,29 +52,25 @@ ESCFLAG EQU $FF ; $FF Escape status * $0290-$02ED * $02EE-$02FF MOS control block -USERV EQU $200 ; USER vector -BRKV EQU $202 ; BRK vector -CLIV EQU $208 ; OSCLI vector -BYTEV EQU $20A ; OSBYTE vector -WORDV EQU $20C ; OSWORD vector -WRCHV EQU $20E ; OSWRCH vector -RDCHV EQU $210 ; OSRDCH vector -FILEV EQU $212 ; OSFILE vector -ARGSV EQU $214 ; OSARGS vector -BGETV EQU $216 ; OSBGET vector -BPUTV EQU $218 ; OSBPUT vector -GBPBV EQU $21A ; OSGBPB vector -FINDV EQU $21C ; OSFIND vector -FSCV EQU $21E ; FSCV misc file ops +USERV EQU $200 ; USER vector +BRKV EQU $202 ; BRK vector +CLIV EQU $208 ; OSCLI vector +BYTEV EQU $20A ; OSBYTE vector +WORDV EQU $20C ; OSWORD vector +WRCHV EQU $20E ; OSWRCH vector +RDCHV EQU $210 ; OSRDCH vector +FILEV EQU $212 ; OSFILE vector +ARGSV EQU $214 ; OSARGS vector +BGETV EQU $216 ; OSBGET vector +BPUTV EQU $218 ; OSBPUT vector +GBPBV EQU $21A ; OSGBPB vector +FINDV EQU $21C ; OSFIND vector +FSCV EQU $21E ; FSCV misc file ops -BYTEVARBASE EQU $190 ; Base of OSBYTE variables -OSFILECB EQU $2EE ; OSFILE control block -OSGBPBCB EQU OSFILECB+1 ; OSGBPB control block +BYTEVARBASE EQU $190 ; Base of OSBYTE variables +OSFILECB EQU $2EE ; OSFILE control block +OSGBPBCB EQU OSFILECB+1 ; OSGBPB control block * $0300-$03DF * $03E0-$03FF Used for interfacing with ProDOS XFER - - - - diff --git a/mainmem.svc.s b/mainmem.svc.s index b0ec352..0e0fb26 100644 --- a/mainmem.svc.s +++ b/mainmem.svc.s @@ -18,103 +18,104 @@ * 23-Oct-2021 Moved all the OSFILE routines together. * Optimised entry and return from OSFILE routines. * DELETE returns 'Dir not empty' when appropriate. +* 29-Oct-2021 DRVINFO reads current drive if "". * ProDOS file handling to rename a file -RENFILE >>> ENTMAIN - JSR PREPATH ; Preprocess arg1 - JSR MFtoTMP ; Stash arg1 - JSR COPYMF21 ; Copy arg2 - JSR PREPATH ; Preprocess arg2 - JSR COPYMF12 ; Put it back in MOSFILE2 - JSR TMPtoMF ; Recover arg1->MOSFILE - LDA #<MOSFILE - STA RENPL+1 - LDA #>MOSFILE - STA RENPL+2 - LDA #<MOSFILE2 - STA RENPL+3 - LDA #>MOSFILE2 - STA RENPL+4 - JSR MLI - DB RENCMD - DW RENPL - >>> XF2AUX,RENRET +RENFILE >>> ENTMAIN + JSR PREPATH ; Preprocess arg1 + JSR MFtoTMP ; Stash arg1 + JSR COPYMF21 ; Copy arg2 + JSR PREPATH ; Preprocess arg2 + JSR COPYMF12 ; Put it back in MOSFILE2 + JSR TMPtoMF ; Recover arg1->MOSFILE + LDA #<MOSFILE + STA RENPL+1 + LDA #>MOSFILE + STA RENPL+2 + LDA #<MOSFILE2 + STA RENPL+3 + LDA #>MOSFILE2 + STA RENPL+4 + JSR MLI + DB RENCMD + DW RENPL + >>> XF2AUX,RENRET * ProDOS file handling for file copying * Returns with ProDOS error code in A -COPYFILE >>> ENTMAIN - JSR MFtoTMP ; Swap MOSFILE & MOSFILE2 - JSR COPYMF21 - JSR TMPtoMF2 - JSR PREPATH ; Preprocess arg2 (in MOSFILE) - JSR WILDONE ; Handle any wildcards - JSR EXISTS ; See if destination exists - STA :DESTTYPE ; Stash for later - JSR MFtoTMP ; Swap MOSFILE & MOSFILE2 again - JSR COPYMF21 - JSR TMPtoMF2 - JSR PREPATH ; Preprocess arg1 - SEC ; Force wildcard lookup - JSR WILDCARD ; Handle any wildcards in arg1 - BCS :NONE - JSR HASWILD - BCC :MAINLOOP ; No wildcards in final segment - LDA :DESTTYPE ; Wildcards, check dest type - CMP #$02 ; Existing directory? - BNE :BADDEST ; If not, error - BRA :MAINLOOP ; Source: wildcard, dest: dir +COPYFILE >>> ENTMAIN + JSR MFtoTMP ; Swap MOSFILE & MOSFILE2 + JSR COPYMF21 + JSR TMPtoMF2 + JSR PREPATH ; Preprocess arg2 (in MOSFILE) + JSR WILDONE ; Handle any wildcards + JSR EXISTS ; See if destination exists + STA :DESTTYPE ; Stash for later + JSR MFtoTMP ; Swap MOSFILE & MOSFILE2 again + JSR COPYMF21 + JSR TMPtoMF2 + JSR PREPATH ; Preprocess arg1 + SEC ; Force wildcard lookup + JSR WILDCARD ; Handle any wildcards in arg1 + BCS :NONE + JSR HASWILD + BCC :MAINLOOP ; No wildcards in final segment + LDA :DESTTYPE ; Wildcards, check dest type + CMP #$02 ; Existing directory? + BNE :BADDEST ; If not, error + BRA :MAINLOOP ; Source: wildcard, dest: dir :NOWILD :MAINLOOP - LDA MOSFILE2 ; Length - STA :OLDLEN - JSR EXISTS ; See if source is file or dir - CMP #$02 ; Directory - BEQ :SKIP ; Skip directories - LDA :DESTTYPE ; Check dest type - CMP #$02 ; Existing directory? - BNE :NOTDIR - LDY MOSFILE2 ; Dest idx = length - LDA MOSFILE2,Y ; Get last char - CMP #'/' ; Is it slash? - BEQ :HASSLSH - LDA #'/' ; Add a '/' separator - STA MOSFILE2+1,Y - INY -:HASSLSH LDX #$00 ; Source id -:APPLOOP CPX MATCHBUF ; At end? - BEQ :DONEAPP - LDA MATCHBUF+1,X ; Appending MATCHBUF to MOSFILE2 - STA MOSFILE2+1,Y - INX - INY - BRA :APPLOOP -:DONEAPP STY MOSFILE2 ; Update length -:NOTDIR LDA :DESTTYPE ; Recover destination type - JSR COPY1FILE ; Copy an individual file - BCS :COPYERR -:SKIP JSR WILDNEXT - BCS :NOMORE - LDA :OLDLEN ; Restore MOSFILE2 - STA MOSFILE2 - BRA :MAINLOOP - JSR CLSDIR -:EXIT >>> XF2AUX,COPYRET -:NONE JSR CLSDIR - LDA #$46 ; 'File not found' - BRA :EXIT -:BADDEST JSR CLSDIR - LDA #$FD ; 'Wildcards' error - BRA :EXIT -:NOMORE JSR CLSDIR - LDA #$00 - BRA :EXIT -:COPYERR PHA - JSR CLSDIR - PLA - BRA :EXIT -:DESTTYPE DB $00 -:OLDLEN DB $00 + LDA MOSFILE2 ; Length + STA :OLDLEN + JSR EXISTS ; See if source is file or dir + CMP #$02 ; Directory + BEQ :SKIP ; Skip directories + LDA :DESTTYPE ; Check dest type + CMP #$02 ; Existing directory? + BNE :NOTDIR + LDY MOSFILE2 ; Dest idx = length + LDA MOSFILE2,Y ; Get last char + CMP #'/' ; Is it slash? + BEQ :HASSLSH + LDA #'/' ; Add a '/' separator + STA MOSFILE2+1,Y + INY +:HASSLSH LDX #$00 ; Source id +:APPLOOP CPX MATCHBUF ; At end? + BEQ :DONEAPP + LDA MATCHBUF+1,X ; Appending MATCHBUF to MOSFILE2 + STA MOSFILE2+1,Y + INX + INY + BRA :APPLOOP +:DONEAPP STY MOSFILE2 ; Update length +:NOTDIR LDA :DESTTYPE ; Recover destination type + JSR COPY1FILE ; Copy an individual file + BCS :COPYERR +:SKIP JSR WILDNEXT + BCS :NOMORE + LDA :OLDLEN ; Restore MOSFILE2 + STA MOSFILE2 + BRA :MAINLOOP + JSR CLSDIR +:EXIT >>> XF2AUX,COPYRET +:NONE JSR CLSDIR + LDA #$46 ; 'File not found' + BRA :EXIT +:BADDEST JSR CLSDIR + LDA #$5E ; 'Wildcards' error + BRA :EXIT +:NOMORE JSR CLSDIR + LDA #$00 + BRA :EXIT +:COPYERR PHA + JSR CLSDIR + PLA + BRA :EXIT +:DESTTYPE DB $00 +:OLDLEN DB $00 * Copy a single file * Source is in MOSFILE, DEST in MOSFILE2 @@ -122,756 +123,733 @@ COPYFILE >>> ENTMAIN * Returns with ProDOS error code in A * Buffer COPYBUF is used for the file copy, to avoid trashing * directory block in RDBUF (when doing wilcard search) -COPY1FILE LDA #<MOSFILE - STA GINFOPL+1 - STA OPENPL2+1 - LDA #>MOSFILE - STA GINFOPL+2 - STA OPENPL2+2 - JSR GETINFO ; GET_FILE_INFO - BCS :ERR - LDA #<MOSFILE2 - STA GINFOPL+1 - STA DESTPL+1 - LDA #>MOSFILE2 - STA GINFOPL+2 - STA DESTPL+2 - JSR MLI ; DESTROY - DB DESTCMD - DW DESTPL - LDA #$07 ; Fix num parms in PL - STA GINFOPL - LDA #$C3 ; Default permissions - STA GINFOPL+3 - JSR MLI ; Call CREATE with .. - DB CREATCMD ; .. PL from GET_FILE_INFO - DW GINFOPL - LDX #$0A ; Num parms back as we found it - STX GINFOPL - BCS :ERR ; Error creating dest file - LDA #$00 ; Look for empty slot - JSR FINDBUF - STX :BUFIDX1 - JSR BUFADDR - BCS :ERR ; No I/O bufs available - STA OPENPL2+3 - STY OPENPL2+4 - JSR MLI - DB OPENCMD - DW OPENPL2 - BCS :ERR ; Open error - BRA :S1 -:ERR SEC ; Report error - RTS -:S1 LDA OPENPL2+5 ; File ref num - STA RDPLCP+1 - LDX :BUFIDX1 - STA FILEREFS,X ; Record the ref number - LDA #<MOSFILE2 - STA OPENPL2+1 - LDA #>MOSFILE2 - STA OPENPL2+2 - LDA #$00 ; Look for empty slot - JSR FINDBUF - STX :BUFIDX2 - JSR BUFADDR - BCS :ERRCLS1 ; No I/O bufs available - STA OPENPL2+3 - STY OPENPL2+4 - JSR MLI - DB OPENCMD - DW OPENPL2 - BCS :ERRCLS1 - LDA OPENPL2+5 ; File ref num - STA WRTPLCP+1 - LDX :BUFIDX2 - STA FILEREFS,X ; Record the ref number -:MAINLOOP JSR MLI ; Read a block - DB READCMD - DW RDPLCP - BCC :RDOKAY - CMP #$4C ; Is it EOF? - BEQ :EOFEXIT - BRA :ERRCLS2 ; Any other error -:RDOKAY LDA RDPLCP+6 ; Trans count MSB - STA WRTPLCP+4 ; Request count MSB - LDA RDPLCP+7 ; Trans count MSB - STA WRTPLCP+5 ; Request count MSB - JSR MLI ; Write a block - DB WRITECMD - DW WRTPLCP - BCS :ERRCLS2 ; Write error - BRA :MAINLOOP -:EOFEXIT CLC ; No error - PHP - LDA #$00 - PHA -:CLOSE2 LDA WRTPLCP+1 ; Close output file - STA CLSPL+1 - JSR CLSFILE - LDX :BUFIDX2 - STZ FILEREFS,X -:CLOSE1 LDA RDPLCP+1 ; Close input file - STA CLSPL+1 - JSR CLSFILE - LDX :BUFIDX1 - STZ FILEREFS,X - PLA - PLP - RTS -:ERRCLS1 SEC - PHP - PHA - BRA :CLOSE1 -:ERRCLS2 SEC - PHP - PHA - BRA :CLOSE2 -:BUFIDX1 DB $00 -:BUFIDX2 DB $00 +COPY1FILE LDA #<MOSFILE + STA GINFOPL+1 + STA OPENPL2+1 + LDA #>MOSFILE + STA GINFOPL+2 + STA OPENPL2+2 + JSR GETINFO ; GET_FILE_INFO + BCS :ERR + LDA #<MOSFILE2 + STA GINFOPL+1 + STA DESTPL+1 + LDA #>MOSFILE2 + STA GINFOPL+2 + STA DESTPL+2 + JSR MLI ; DESTROY + DB DESTCMD + DW DESTPL + LDA #$07 ; Fix num parms in PL + STA GINFOPL + LDA #$C3 ; Default permissions + STA GINFOPL+3 + JSR MLI ; Call CREATE with .. + DB CREATCMD ; .. PL from GET_FILE_INFO + DW GINFOPL + LDX #$0A ; Num parms back as we found it + STX GINFOPL + BCS :ERR ; Error creating dest file + LDA #$00 ; Look for empty slot + JSR FINDBUF + STX :BUFIDX1 + JSR BUFADDR + BCS :ERR ; No I/O bufs available + STA OPENPL2+3 + STY OPENPL2+4 + JSR MLI + DB OPENCMD + DW OPENPL2 + BCS :ERR ; Open error + BRA :S1 +:ERR SEC ; Report error + RTS +:S1 LDA OPENPL2+5 ; File ref num + STA RDPLCP+1 + LDX :BUFIDX1 + STA FILEREFS,X ; Record the ref number + LDA #<MOSFILE2 + STA OPENPL2+1 + LDA #>MOSFILE2 + STA OPENPL2+2 + LDA #$00 ; Look for empty slot + JSR FINDBUF + STX :BUFIDX2 + JSR BUFADDR + BCS :ERRCLS1 ; No I/O bufs available + STA OPENPL2+3 + STY OPENPL2+4 + JSR MLI + DB OPENCMD + DW OPENPL2 + BCS :ERRCLS1 + LDA OPENPL2+5 ; File ref num + STA WRTPLCP+1 + LDX :BUFIDX2 + STA FILEREFS,X ; Record the ref number +:MAINLOOP JSR MLI ; Read a block + DB READCMD + DW RDPLCP + BCC :RDOKAY + CMP #$4C ; Is it EOF? + BEQ :EOFEXIT + BRA :ERRCLS2 ; Any other error +:RDOKAY LDA RDPLCP+6 ; Trans count MSB + STA WRTPLCP+4 ; Request count MSB + LDA RDPLCP+7 ; Trans count MSB + STA WRTPLCP+5 ; Request count MSB + JSR MLI ; Write a block + DB WRITECMD + DW WRTPLCP + BCS :ERRCLS2 ; Write error + BRA :MAINLOOP +:EOFEXIT CLC ; No error + PHP + LDA #$00 + PHA +:CLOSE2 LDA WRTPLCP+1 ; Close output file + STA CLSPL+1 + JSR CLSFILE + LDX :BUFIDX2 + STZ FILEREFS,X +:CLOSE1 LDA RDPLCP+1 ; Close input file + STA CLSPL+1 + JSR CLSFILE + LDX :BUFIDX1 + STZ FILEREFS,X + PLA + PLP + RTS +:ERRCLS1 SEC + PHP + PHA + BRA :CLOSE1 +:ERRCLS2 SEC + PHP + PHA + BRA :CLOSE2 +:BUFIDX1 DB $00 +:BUFIDX2 DB $00 * ProDOS file handling for MOS OSFIND OPEN call * Options in A: $40 'r', $80 'w', $C0 'rw' -OFILE >>> ENTMAIN - AND #$C0 ; Keep just action bits - PHA ; Preserve arg for later - JSR PREPATH ; Preprocess pathname - BCS :JMPEXIT1 ; Bad filename - PLA - PHA - CMP #$80 ; Is it "w"? - BEQ :NOWILD ; If so, no wildcards - JSR WILDONE ; Handle any wildcards -:NOWILD JSR EXISTS ; See if file exists ... - TAX - CMP #$02 ; ... and is a directory - BNE :NOTDIR - PLA ; Get action back - BPL :NOTDIR2 ; OPENIN(dir) allowed - LDA #$41 ; $41=Directory exists - PHA ; Balance PLA -:JMPEXIT1 PLA -:JMPEXIT JMP FINDEXIT -:NOTDIR PLA -:NOTDIR2 CMP #$80 ; Write mode - BNE :S1 - TXA - BEQ :S0 ; No file, don't try to delete - JSR DODELETE - BCS FINDEXIT ; Abort if error -:S0 LDX #$00 ; LOAD=$0000 - LDY #$00 - JSR CREATEFILE - BCS FINDEXIT ; Abort if error +OFILE >>> ENTMAIN + AND #$C0 ; Keep just action bits + PHA ; Preserve arg for later + JSR PREPATH ; Preprocess pathname + BCS :JMPEXIT1 ; Bad filename + PLA + PHA + CMP #$80 ; Is it "w"? + BEQ :NOWILD ; If so, no wildcards + JSR WILDONE ; Handle any wildcards +:NOWILD JSR EXISTS ; See if file exists ... + TAX + CMP #$02 ; ... and is a directory + BNE :NOTDIR + PLA ; Get action back + BPL :NOTDIR2 ; OPENIN(dir) allowed + LDA #$41 ; $41=Directory exists + PHA ; Balance PLA +:JMPEXIT1 PLA +:JMPEXIT JMP FINDEXIT +:NOTDIR PLA +:NOTDIR2 CMP #$80 ; Write mode + BNE :S1 + TXA + BEQ :S0 ; No file, don't try to delete + JSR DODELETE + BCS FINDEXIT ; Abort if error +:S0 LDX #$00 ; LOAD=$0000 + LDY #$00 + JSR CREATEFILE + BCS FINDEXIT ; Abort if error * Looking for a buffer should be done before creating a file -:S1 LDA #$00 ; Look for empty slot - JSR FINDBUF - STX BUFIDX - JSR BUFADDR - BCS NOBUFFS ; No empty slot (BUFIDX=FF) - STA OPENPL2+3 - STY OPENPL2+4 - LDA #<MOSFILE - STA OPENPL2+1 - LDA #>MOSFILE - STA OPENPL2+2 - JSR MLI - DB OPENCMD - DW OPENPL2 - BCS FINDEXIT - LDA OPENPL2+5 ; File ref number - LDX BUFIDX - STA FILEREFS,X ; Record the ref number -FINDEXIT JSR CHKNOTFND ; Convert NotFound to $00 - >>> XF2AUX,OSFINDRET -NOBUFFS LDA #$42 ; $42=File buffers full - BNE FINDEXIT -BUFIDX DB $00 +:S1 LDA #$00 ; Look for empty slot + JSR FINDBUF + STX BUFIDX + JSR BUFADDR + BCS NOBUFFS ; No empty slot (BUFIDX=FF) + STA OPENPL2+3 + STY OPENPL2+4 + LDA #<MOSFILE + STA OPENPL2+1 + LDA #>MOSFILE + STA OPENPL2+2 + JSR MLI + DB OPENCMD + DW OPENPL2 + BCS FINDEXIT + LDA OPENPL2+5 ; File ref number + LDX BUFIDX + STA FILEREFS,X ; Record the ref number +FINDEXIT JSR CHKNOTFND ; Convert NotFound to $00 + >>> XF2AUX,OSFINDRET +NOBUFFS LDA #$42 ; $42=File buffers full + BNE FINDEXIT +BUFIDX DB $00 * ProDOS file handling for MOS OSFIND CLOSE call * ProDOS can do CLOSE#0 but we need to manually update FILEREFS -CFILE >>> ENTMAIN - LDX #$00 ; Prepare for one file - TYA ; File ref number - BNE :CFILE1 ; Close one file - LDX #$03 ; Loop through all files -:CFILE0 LDA FILEREFS,X - BEQ :CFILE3 ; Not open, try next -:CFILE1 PHX - PHA - STA CLSPL+1 - JSR CLSFILE - BCS :CFILEERR ; Error occured during closing - PLA - JSR FINDBUF - BNE :CFILE2 - LDA #$00 - STA FILEREFS,X ; Release buffer -:CFILE2 PLX -:CFILE3 DEX - BPL :CFILE0 ; Loop to close all files - LDA #$00 - BEQ FINDEXIT -:CFILEERR PLX ; Balance stack - PLX - BCS FINDEXIT +CFILE >>> ENTMAIN + LDX #$00 ; Prepare for one file + TYA ; File ref number + BNE :CFILE1 ; Close one file + LDX #$03 ; Loop through all files +:CFILE0 LDA FILEREFS,X + BEQ :CFILE3 ; Not open, try next +:CFILE1 PHX + PHA + STA CLSPL+1 + JSR CLSFILE + BCS :CFILEERR ; Error occured during closing + PLA + JSR FINDBUF + BNE :CFILE2 + LDA #$00 + STA FILEREFS,X ; Release buffer +:CFILE2 PLX +:CFILE3 DEX + BPL :CFILE0 ; Loop to close all files + LDA #$00 + BEQ FINDEXIT +:CFILEERR PLX ; Balance stack + PLX + BCS FINDEXIT * ProDOS file handling for MOS OSBGET call * Returns with char read in A and error num in Y (or 0) -FILEGET >>> ENTMAIN - STY READPL2+1 ; File ref number - JSR MLI - DB READCMD - DW READPL2 - TAY ; Error number in Y - BCS :EXIT - LDY #$00 ; 0=Ok - LDA BLKBUF -:EXIT >>> XF2AUX,OSBGETRET +FILEGET >>> ENTMAIN + STY READPL2+1 ; File ref number + JSR MLI + DB READCMD + DW READPL2 + TAY ; Error number in Y + BCS :EXIT + LDY #$00 ; 0=Ok + LDA BLKBUF +:EXIT >>> XF2AUX,OSBGETRET * ProDOS file handling for MOS OSBPUT call * Enters with char to write in A -FILEPUT >>> ENTMAIN - STA BLKBUF ; Byte to write - STY WRITEPL+1 ; File ref number - LDA #$01 ; Bytes to write - STA WRITEPL+4 - LDA #$00 - STA WRITEPL+5 - JSR WRTFILE - BCS :FILEPUT2 - LDA #$00 ; 0=Ok -:FILEPUT2 >>> XF2AUX,OSBPUTRET +FILEPUT >>> ENTMAIN + STA BLKBUF ; Byte to write + STY WRITEPL+1 ; File ref number + LDA #$01 ; Bytes to write + STA WRITEPL+4 + LDA #$00 + STA WRITEPL+5 + JSR WRTFILE + BCS :FILEPUT2 + LDA #$00 ; 0=Ok +:FILEPUT2 >>> XF2AUX,OSBPUTRET * ProDOS file handling for FSC $01 called by OSBYTE $7F EOF * Returns EOF status in A ($FF for EOF, $00 otherwise) * A=channel to test -FILEEOF >>> ENTMAIN - STA GEOFPL+1 - STA GMARKPL+1 - JSR MLI - DB GEOFCMD - DW GEOFPL - TAY - BCS :EXIT ; Abort with any error - JSR MLI - DB GMARKCMD - DW GMARKPL - TAY - BCS :EXIT ; Abort with any error +FILEEOF >>> ENTMAIN + STA GEOFPL+1 + STA GMARKPL+1 + JSR MLI + DB GEOFCMD + DW GEOFPL + TAY + BCS :EXIT ; Abort with any error + JSR MLI + DB GMARKCMD + DW GMARKPL + TAY + BCS :EXIT ; Abort with any error - SEC - LDA GEOFPL+2 ; Subtract Mark from EOF - SBC GMARKPL+2 - STA GEOFPL+2 - LDA GEOFPL+3 - SBC GMARKPL+3 - STA GEOFPL+3 - LDA GEOFPL+4 - SBC GMARKPL+4 - STA GEOFPL+4 + SEC + LDA GEOFPL+2 ; Subtract Mark from EOF + SBC GMARKPL+2 + STA GEOFPL+2 + LDA GEOFPL+3 + SBC GMARKPL+3 + STA GEOFPL+3 + LDA GEOFPL+4 + SBC GMARKPL+4 + STA GEOFPL+4 - LDA GEOFPL+2 ; Check bytes remaining - ORA GEOFPL+3 - ORA GEOFPL+4 - BEQ :ISEOF ; EOF -> $00 - LDA #$FF ; Not EOF -> $FF -:ISEOF EOR #$FF ; EOF -> $FF, Not EOF ->$00 - LDY #$00 ; 0=No error -:EXIT >>> XF2AUX,CHKEOFRET + LDA GEOFPL+2 ; Check bytes remaining + ORA GEOFPL+3 + ORA GEOFPL+4 + BEQ :ISEOF ; EOF -> $00 + LDA #$FF ; Not EOF -> $FF +:ISEOF EOR #$FF ; EOF -> $FF, Not EOF ->$00 + LDY #$00 ; 0=No error +:EXIT >>> XF2AUX,CHKEOFRET * ProDOS file handling for OSARGS flush commands -FLUSH >>> ENTMAIN - STY FLSHPL+1 ; File ref number - JSR MLI - DB FLSHCMD - DW FLSHPL - JMP TELLEXIT +FLUSH >>> ENTMAIN + STY FLSHPL+1 ; File ref number + JSR MLI + DB FLSHCMD + DW FLSHPL + JMP TELLEXIT * ProDOS file handling for OSARGS set ptr command * GMARKPL+1=channel, GMARKPL+2,+3,+4=offset already set -SEEK >>> ENTMAIN - JSR MLI - DB SMARKCMD - DW GMARKPL - JMP TELLEXIT +SEEK >>> ENTMAIN + JSR MLI + DB SMARKCMD + DW GMARKPL + JMP TELLEXIT * ProDOS file handling for OSARGS get ptr command * and for OSARGs get length command * A=ZP, Y=channel -SIZE LDX #$02 ; $02=SIZE, Read EXT - BNE TELL2 -TELL LDX #$00 ; $00=TELL, Read PTR -TELL2 STY GMARKPL+1 ; File ref number - PHA ; Pointer to zero page - CPX #$00 ; OSARGS parameter - BEQ :POS - JSR MLI - DB GEOFCMD - DW GMARKPL ; MARK parms same as EOF parms - BRA :S1 -:POS JSR MLI - DB GMARKCMD - DW GMARKPL -:S1 PLX ; Pointer to ZP control block - BCS TELLEXIT ; Exit with error - >>> ALTZP ; Alt ZP & Alt LC on - LDA GMARKPL+2 - STA $00,X - LDA GMARKPL+3 - STA $01,X - LDA GMARKPL+4 - STA $02,X - STZ $03,X ; Sizes are $00xxxxxx - >>> MAINZP ; Alt ZP off, ROM back in - LDA #$00 ; 0=Ok -TELLEXIT >>> XF2AUX,OSARGSRET +SIZE LDX #$02 ; $02=SIZE, Read EXT + BNE TELL2 +TELL LDX #$00 ; $00=TELL, Read PTR +TELL2 STY GMARKPL+1 ; File ref number + PHA ; Pointer to zero page + CPX #$00 ; OSARGS parameter + BEQ :POS + JSR MLI + DB GEOFCMD + DW GMARKPL ; MARK parms same as EOF parms + BRA :S1 +:POS JSR MLI + DB GMARKCMD + DW GMARKPL +:S1 PLX ; Pointer to ZP control block + BCS TELLEXIT ; Exit with error + >>> ALTZP ; Alt ZP & Alt LC on + LDA GMARKPL+2 + STA $00,X + LDA GMARKPL+3 + STA $01,X + LDA GMARKPL+4 + STA $02,X + STZ $03,X ; Sizes are $00xxxxxx + >>> MAINZP ; Alt ZP off, ROM back in + LDA #$00 ; 0=Ok +TELLEXIT >>> XF2AUX,OSARGSRET -ZPMOS EQU $30 +ZPMOS EQU $30 * ProDOS file MOS OSFILE calls -CALLFILE >>> ENTMAIN - JSR FILEDISPATCH - >>> XF2AUX,OSFILERET -FILEDISPATCH CMP #$00 - BEQ SVCSAVE ; A=00 -> SAVE - CMP #$FF - BEQ SVCLOAD ; A=FF -> LOAD - CMP #$06 - BEQ DELFILE ; A=06 -> DELETE - BCC INFOFILE ; A=01-05 -> INFO - CMP #$08 - BEQ MAKEDIR ; A=08 -> MKDIR - RTS -SVCSAVE JMP SAVEFILE -SVCLOAD JMP LOADFILE +CALLFILE >>> ENTMAIN + JSR FILEDISPATCH + >>> XF2AUX,OSFILERET +FILEDISPATCH CMP #$00 + BEQ SVCSAVE ; A=00 -> SAVE + CMP #$FF + BEQ SVCLOAD ; A=FF -> LOAD + CMP #$06 + BEQ DELFILE ; A=06 -> DELETE + BCC INFOFILE ; A=01-05 -> INFO + CMP #$08 + BEQ MAKEDIR ; A=08 -> MKDIR + RTS +SVCSAVE JMP SAVEFILE +SVCLOAD JMP LOADFILE -INFOFILE -* >>> ENTMAIN -* JSR PREPATH ; Preprocess path -* JSR UPDFB ; Update FILEBLK - JSR UPDPATH ; Process path and get info - JMP COPYFB ; Copy back to aux mem -* >>> XF2AUX,OSFILERET +INFOFILE JSR UPDPATH ; Process path and get info + JMP COPYFB ; Copy back to aux mem * ProDOS file handling to delete a file * Called by AppleMOS OSFILE * Return A=0 no object, A=1 file deleted, A=2 dir deleted * A>$1F ProDOS error -DELFILE -* >>> ENTMAIN -* JSR PREPATH ; Preprocess path -* JSR UPDFB ; Update FILEBLK - JSR UPDPATH ; Process path and get info - JSR COPYFB ; Copy back to aux mem - PHA ; Save object type - JSR DODELETE - BCC :DELETED ; Success +DELFILE JSR UPDPATH ; Process path and get info + JSR COPYFB ; Copy back to aux mem + PHA ; Save object type + JSR DODELETE + BCC :DELETED ; Success - TAX ; X=error code - PLA ; Get object back - CPX #$4E - BNE :DELERROR ; Not 'Insuff. access', return it - LDX #$4F ; Change to 'Locked' + TAX ; X=error code + PLA ; Get object back + CPX #$4E + BNE :DELERROR ; Not 'Insuff. access', return it + LDX #$4F ; Change to 'Locked' - CMP #$02 - BNE :DELERROR ; Wasn't a directory, return 'Locked' - LDA FBATTR+0 - AND #$08 - BNE :DELERROR ; Dir locked, return 'Locked' - LDX #$54 ; Change to 'Dir not empty' + CMP #$02 + BNE :DELERROR ; Wasn't a directory, return 'Locked' + LDA FBATTR+0 + AND #$08 + BNE :DELERROR ; Dir locked, return 'Locked' + LDX #$54 ; Change to 'Dir not empty' -:DELERROR TXA - JSR CHKNOTFND - PHA -:DELETED PLA ; Get object back -:EXIT RTS -* >>> XF2AUX,OSFILERET +:DELERROR TXA + JSR CHKNOTFND + PHA +:DELETED PLA ; Get object back +:EXIT RTS -DODELETE LDA #<MOSFILE ; Attempt to destroy file - STA DESTPL+1 - LDA #>MOSFILE - STA DESTPL+2 - JSR MLI - DB DESTCMD - DW DESTPL - RTS +DODELETE LDA #<MOSFILE ; Attempt to destroy file + STA DESTPL+1 + LDA #>MOSFILE + STA DESTPL+2 + JSR MLI + DB DESTCMD + DW DESTPL + RTS * ProDOS file handling to create a directory * Invoked by AppleMOS OSFILE * Return A=$02 on success (ie: 'directory') * A>$1F ProDOS error, translated by OSFILE handler -MAKEDIR -* >>> ENTMAIN -* JSR PREPATH ; Preprocess path -* JSR UPDFB ; Update FILEBLK - JSR UPDPATH ; Process path and get info - CMP #$02 - BEQ :EXIT1 ; Dir already exists +MAKEDIR JSR UPDPATH ; Process path and get info + CMP #$02 + BEQ :EXIT1 ; Dir already exists - LDA #$0D ; OBJT='Directory' - STA CREATEPL+7 ; ->Storage type - LDA #$0F ; TYPE='Directory' - LDX #$00 ; LOAD=$0000 - LDY #$00 - JSR CREATEOBJ - BCS :EXIT ; Failed, exit with ProDOS result - JSR UPDFB ; Update FILEBLK, returns A=$02 -:EXIT1 JSR COPYFB ; Copy FILEBLK to aux mem -:EXIT RTS -* >>> XF2AUX,OSFILERET + LDA #$0D ; OBJT='Directory' + STA CREATEPL+7 ; ->Storage type + LDA #$0F ; TYPE='Directory' + LDX #$00 ; LOAD=$0000 + LDY #$00 + JSR CREATEOBJ + BCS :EXIT ; Failed, exit with ProDOS result + JSR UPDFB ; Update FILEBLK, returns A=$02 +:EXIT1 JSR COPYFB ; Copy FILEBLK to aux mem +:EXIT RTS * ProDOS file handling for MOS OSFILE LOAD call * Invoked by AppleMOS OSFILE * Return A=01 if successful (meaning 'file') * A>$1F ProDOS error, translated by FILERET -LOADFILE -* >>> ENTMAIN - LDX #4 -:LP LDA FBLOAD,X ; Get address to load to - STA ZPMOS,X - DEX - BPL :LP - JSR PREPATH ; Preprocess pathname - JSR WILDONE ; Handle any wildcards - JSR UPDFB ; Get object info - CMP #$20 - BCS :JMPEXIT ; Error occured - CMP #$01 ; Is it a file - BEQ :ISFILE - ROL A ; 0->0, 2->5 - EOR #$05 ; 0->5, 2->0 - ADC #$41 ; 0->$46, 2->$41 -:JMPEXIT JMP :EXIT2 ; Return error +LOADFILE LDX #4 +:LP LDA FBLOAD,X ; Get address to load to + STA ZPMOS,X + DEX + BPL :LP + JSR PREPATH ; Preprocess pathname + JSR WILDONE ; Handle any wildcards + JSR UPDFB ; Get object info + CMP #$20 + BCS :JMPEXIT ; Error occured + CMP #$01 ; Is it a file + BEQ :ISFILE + ROL A ; 0->0, 2->5 + EOR #$05 ; 0->5, 2->0 + ADC #$41 ; 0->$46, 2->$41 +:JMPEXIT JMP :EXIT2 ; Return error -:ISFILE LDA ZPMOS+4 ; If FBEXEC is zero, use addr - BEQ :CBADDR ; in the control block - LDA FBLOAD+0 ; Otherwise, use file's address - STA ZPMOS+0 - LDA FBLOAD+1 - STA ZPMOS+1 +:ISFILE LDA ZPMOS+4 ; If FBEXEC is zero, use addr + BEQ :CBADDR ; in the control block + LDA FBLOAD+0 ; Otherwise, use file's address + STA ZPMOS+0 + LDA FBLOAD+1 + STA ZPMOS+1 -:CBADDR JSR OPENMOSFILE - BCS :EXIT2 ; File not opened +:CBADDR JSR OPENMOSFILE + BCS :EXIT2 ; File not opened -:L1 LDA OPENPL+5 ; File ref number - JSR READDATA ; Read data from open file +:L1 LDA OPENPL+5 ; File ref number + JSR READDATA ; Read data from open file - PHA ; Save result - LDA OPENPL+5 ; File ref num - STA CLSPL+1 - JSR CLSFILE - PLA - BNE :EXIT2 - JSR COPYFB ; Copy FILEBLK to auxmem - LDA #$01 ; $01=File -:EXIT2 RTS -* >>> XF2AUX,OSFILERET + PHA ; Save result + LDA OPENPL+5 ; File ref num + STA CLSPL+1 + JSR CLSFILE + PLA + BNE :EXIT2 + JSR COPYFB ; Copy FILEBLK to auxmem + LDA #$01 ; $01=File +:EXIT2 RTS * A=channel, MOSZP+0/1=address to load to, TO DO: MOS+4/5=length to read -READDATA STA READPL+1 -:RDLP JSR RDFILE - BCS :READERR ; Close file and return any error +READDATA STA READPL+1 +:RDLP JSR RDFILE + BCS :READERR ; Close file and return any error - LDA #<BLKBUF ; LSB of start of data buffer - STA A1L ; A1=>start of data buffer - ADC READPL+6 ; LSB of trans count - TAX ; X=>LSB end of data buffer + LDA #<BLKBUF ; LSB of start of data buffer + STA A1L ; A1=>start of data buffer + ADC READPL+6 ; LSB of trans count + TAX ; X=>LSB end of data buffer - LDA #>BLKBUF ; MSB of start of data buffer - STA A1H ; A1=>start of data buffer - ADC READPL+7 ; MSB of trans count - TAY ; Y=>MSB end of data buffer + LDA #>BLKBUF ; MSB of start of data buffer + STA A1H ; A1=>start of data buffer + ADC READPL+7 ; MSB of trans count + TAY ; Y=>MSB end of data buffer - TXA - BNE :L2 - DEY -:L2 DEX ; XY=XY-1, end address is start+len-1 - STX A2L ; A2=>end of data buffer - STY A2H + TXA + BNE :L2 + DEY +:L2 DEX ; XY=XY-1, end address is start+len-1 + STX A2L ; A2=>end of data buffer + STY A2H - LDA ZPMOS+0 ; A4=>address to load to - STA A4L - LDA ZPMOS+1 - STA A4H - INC ZPMOS+1 ; Step to next block - INC ZPMOS+1 + LDA ZPMOS+0 ; A4=>address to load to + STA A4L + LDA ZPMOS+1 + STA A4H + INC ZPMOS+1 ; Step to next block + INC ZPMOS+1 - SEC ; Main -> AUX - JSR AUXMOVE ; A4 updated to next address - JMP :RDLP + SEC ; Main -> AUX + JSR AUXMOVE ; A4 updated to next address + JMP :RDLP -:READERR CMP #$4C - BNE :EXITERR -:EXITOK LDA #$00 ; $00=Success -:EXITERR RTS +:READERR CMP #$4C + BNE :EXITERR +:EXITOK LDA #$00 ; $00=Success +:EXITERR RTS * ProDOS file handling for MOS OSFILE SAVE call * Invoked by AppleMOS OSFILE * Return A=01 if successful (ie: 'file') * A>$1F ProDOS error translated by FILERET -SAVEFILE -* >>> ENTMAIN - SEC ; Compute file length - LDA FBEND+0 - SBC FBSTRT+0 - STA LENREM+0 - LDA FBEND+1 - SBC FBSTRT+1 - STA LENREM+1 - LDA FBEND+2 - SBC FBSTRT+2 - BNE :TOOBIG ; >64K - LDA FBEND+3 - SBC FBSTRT+3 - BEQ :L0 ; >16M -:TOOBIG JMP :CANTSAVE +SAVEFILE SEC ; Compute file length + LDA FBEND+0 + SBC FBSTRT+0 + STA LENREM+0 + LDA FBEND+1 + SBC FBSTRT+1 + STA LENREM+1 + LDA FBEND+2 + SBC FBSTRT+2 + BNE :TOOBIG ; >64K + LDA FBEND+3 + SBC FBSTRT+3 + BEQ :L0 ; >16M +:TOOBIG LDA #$2C ; Bad byte count - file too long + RTS -:L0 JSR PREPATH ; Preprocess pathname - JSR EXISTS ; See if file exists ... - CMP #$01 - BEQ :NOTDIR ; Overwrite file - BCC :NOFILE ; Create new file - CMP #$02 - BNE :JMPEXIT2 - LDA #$41 ; Dir exists, return $41 -:JMPEXIT2 JMP :EXIT2 +:L0 JSR PREPATH ; Preprocess pathname + JSR EXISTS ; See if file exists ... + CMP #$01 + BEQ :NOTDIR ; Overwrite file + BCC :NOFILE ; Create new file + CMP #$02 + BNE :JMPEXIT2 + LDA #$41 ; Dir exists, return $41 +:JMPEXIT2 JMP :EXIT2 -:NOTDIR LDA #<MOSFILE ; Attempt to destroy file - STA DESTPL+1 - LDA #>MOSFILE - STA DESTPL+2 - JSR MLI - DB DESTCMD - DW DESTPL - BCS :EXIT2 ; Error trying to delete +:NOTDIR LDA #<MOSFILE ; Attempt to destroy file + STA DESTPL+1 + LDA #>MOSFILE + STA DESTPL+2 + JSR MLI + DB DESTCMD + DW DESTPL + BCS :EXIT2 ; Error trying to delete -:NOFILE LDX FBLOAD+0 ; Auxtype = load address - LDY FBLOAD+1 - JSR CREATEFILE - BCS :JMPEXIT2 ; Error trying to create - JSR OPENMOSFILE - BCS :JMPEXIT2 ; Error trying to open - LDA OPENPL+5 ; File ref number - JSR WRITEDATA +:NOFILE LDX FBLOAD+0 ; Auxtype = load address + LDY FBLOAD+1 + JSR CREATEFILE + BCS :JMPEXIT2 ; Error trying to create + JSR OPENMOSFILE + BCS :JMPEXIT2 ; Error trying to open + LDA OPENPL+5 ; File ref number + JSR WRITEDATA -:EXIT1 PHA ; Save result - LDA OPENPL+5 ; File ref num - STA CLSPL+1 - JSR CLSFILE - PLA - BNE :EXIT2 ; Error returned - JSR UPDFB ; Update FILEBLK - JSR COPYFB ; Copy FILEBLK to aux mem - LDA #$01 ; Return A='File' -:EXIT2 CMP #$4E - BNE :EXIT3 ; Change 'Insuff. access' - LDA #$4F ; to 'Locked' -:EXIT3 RTS -* >>> XF2AUX,OSFILERET -:CANTSAVE LDA #$5E ; Can't open/create - BRA :EXIT3 ; TO DO: Error=File too long +:EXIT1 PHA ; Save result + LDA OPENPL+5 ; File ref num + STA CLSPL+1 + JSR CLSFILE + PLA + BNE :EXIT2 ; Error returned + JSR UPDFB ; Update FILEBLK + JSR COPYFB ; Copy FILEBLK to aux mem + LDA #$01 ; Return A='File' +:EXIT2 CMP #$4E + BNE :EXIT3 ; Change 'Insuff. access' + LDA #$4F ; to 'Locked' +:EXIT3 RTS * A=channel, FBSTRT+0/1=address to save from * LENREM+0/1=length to write -WRITEDATA STA WRITEPL+1 -:L1 LDA #$00 ; 512 bytes request count - STA WRITEPL+4 - LDA #$02 - STA WRITEPL+5 +WRITEDATA STA WRITEPL+1 +:L1 LDA #$00 ; 512 bytes request count + STA WRITEPL+4 + LDA #$02 + STA WRITEPL+5 - LDA LENREM+1 - CMP #$02 - BCS :L15 ; More than 511 bytes remaining - STA WRITEPL+5 - LDA LENREM+0 - STA WRITEPL+4 - ORA WRITEPL+5 - BEQ :SAVEOK ; Zero bytes remaining + LDA LENREM+1 + CMP #$02 + BCS :L15 ; More than 511 bytes remaining + STA WRITEPL+5 + LDA LENREM+0 + STA WRITEPL+4 + ORA WRITEPL+5 + BEQ :SAVEOK ; Zero bytes remaining -:L15 SEC - LDA LENREM+0 ; LENREM=LENREM-count - SBC WRITEPL+4 - STA LENREM+0 - LDA LENREM+1 - SBC WRITEPL+5 - STA LENREM+1 +:L15 SEC + LDA LENREM+0 ; LENREM=LENREM-count + SBC WRITEPL+4 + STA LENREM+0 + LDA LENREM+1 + SBC WRITEPL+5 + STA LENREM+1 - CLC - LDA FBSTRT+0 - STA A1L ; A1=>start of this block - ADC WRITEPL+4 - STA FBSTRT+0 ; Update FBSTRT=>start of next block - TAX ; X=>end of this block + CLC + LDA FBSTRT+0 + STA A1L ; A1=>start of this block + ADC WRITEPL+4 + STA FBSTRT+0 ; Update FBSTRT=>start of next block + TAX ; X=>end of this block - LDA FBSTRT+1 - STA A1H - ADC WRITEPL+5 - STA FBSTRT+1 - TAY + LDA FBSTRT+1 + STA A1H + ADC WRITEPL+5 + STA FBSTRT+1 + TAY - TXA - BNE :L2 - DEY -:L2 DEX ; XY=XY-1, end address is start+len-1 - STX A2L ; A2=>end of data buffer - STY A2H + TXA + BNE :L2 + DEY +:L2 DEX ; XY=XY-1, end address is start+len-1 + STX A2L ; A2=>end of data buffer + STY A2H -:S2 LDA #<BLKBUF - STA A4L - LDA #>BLKBUF - STA A4H - CLC ; Aux -> Main - JSR AUXMOVE ; Copy data from aux to local buffer +:S2 LDA #<BLKBUF + STA A4L + LDA #>BLKBUF + STA A4H + CLC ; Aux -> Main + JSR AUXMOVE ; Copy data from aux to local buffer - JSR WRTFILE ; Write the data - BCS :WRITEERR - JMP :L1 ; Loop back for next block -:SAVEOK ; Enter here with A=$00 -:WRITEERR RTS -LENREM DW $0000 ; Remaining length + JSR WRTFILE ; Write the data + BCS :WRITEERR + JMP :L1 ; Loop back for next block +:SAVEOK ; Enter here with A=$00 +:WRITEERR RTS +LENREM DW $0000 ; Remaining length -CREATEFILE LDA #$01 ; Storage type - file - STA CREATEPL+7 - LDA #$06 ; Filetype BIN +CREATEFILE LDA #$01 ; Storage type - file + STA CREATEPL+7 + LDA #$06 ; Filetype BIN -CREATEOBJ STA CREATEPL+4 ; Type = BIN or DIR - STX CREATEPL+5 ; Auxtype = load address - STY CREATEPL+6 - JMP CRTFILE +CREATEOBJ STA CREATEPL+4 ; Type = BIN or DIR + STX CREATEPL+5 ; Auxtype = load address + STY CREATEPL+6 + JMP CRTFILE * Process pathname and read object info -UPDPATH JSR PREPATH ; Process pathname - BCC UPDFB ; If no error, update control block - RTS +UPDPATH JSR PREPATH ; Process pathname + BCC UPDFB ; If no error, update control block + RTS * Update FILEBLK before returning to aux memory * Returns A=object type or ProDOS error -UPDFB LDA #<MOSFILE - STA GINFOPL+1 - LDA #>MOSFILE - STA GINFOPL+2 - JSR GETINFO ; Call GET_FILE_INFO - BCC :UPDFB1 - JMP CHKNOTFND +UPDFB LDA #<MOSFILE + STA GINFOPL+1 + LDA #>MOSFILE + STA GINFOPL+2 + JSR GETINFO ; Call GET_FILE_INFO + BCC :UPDFB1 + JMP CHKNOTFND -:UPDFB1 LDA GINFOPL+5 ; Aux type LSB - STA FBLOAD - STA FBEXEC - LDA GINFOPL+6 ; Aux type MSB - STA FBLOAD+1 - STA FBEXEC+1 - STZ FBLOAD+2 - STZ FBEXEC+2 - STZ FBLOAD+3 - STZ FBEXEC+3 +:UPDFB1 LDA GINFOPL+5 ; Aux type LSB + STA FBLOAD + STA FBEXEC + LDA GINFOPL+6 ; Aux type MSB + STA FBLOAD+1 + STA FBEXEC+1 + STZ FBLOAD+2 + STZ FBEXEC+2 + STZ FBLOAD+3 + STZ FBEXEC+3 * - LDA GINFOPL+3 ; Access byte - CMP #$40 ; Locked? - AND #$03 ; ------wr - PHP - STA FBATTR+0 - ASL A ; -----wr- - ASL A ; ----wr-- - ASL A ; ---wr--- - ASL A ; --wr---- - PLP - BCS :UPDFB2 - ORA #$08 ; --wrl--- -:UPDFB2 ORA FBATTR+0 ; --wrl-wr - STA FBATTR+0 + LDA GINFOPL+3 ; Access byte + CMP #$40 ; Locked? + AND #$03 ; ------wr + PHP + STA FBATTR+0 + ASL A ; -----wr- + ASL A ; ----wr-- + ASL A ; ---wr--- + ASL A ; --wr---- + PLP + BCS :UPDFB2 + ORA #$08 ; --wrl--- +:UPDFB2 ORA FBATTR+0 ; --wrl-wr + STA FBATTR+0 * - LDA GINFOPL+11 ; yyyyyyym - PHA - ROR A ; ?yyyyyyy m - LDA GINFOPL+10 ; mmmddddd m - PHA - ROR A ; mmmmdddd - LSR A ; -mmmmddd - LSR A ; --mmmmdd - LSR A ; ---mmmmd - LSR A ; ----mmmm - STA FBATTR+2 - PLA ; mmmddddd - AND #31 ; ---ddddd - STA FBATTR+1 - PLA ; yyyyyyym - SEC - SBC #81*2 ; Offset from 1981 - BCS :UPDFB3 ; 1981-1999 -> 00-18 - ADC #100*2 ; 2000-2080 -> 19-99 -:UPDFB3 PHA ; yyyyyyym - AND #$E0 ; yyy----- - ORA FBATTR+1 ; yyyddddd - STA FBATTR+1 - PLA ; yyyyyyym - AND #$FE ; yyyyyyy0 - ASL A ; yyyyyy00 - ASL A ; yyyyy000 - ASL A ; yyyy0000 - ORA FBATTR+2 ; yyyymmmm - STA FBATTR+2 - STZ FBATTR+3 + LDA GINFOPL+11 ; yyyyyyym + PHA + ROR A ; ?yyyyyyy m + LDA GINFOPL+10 ; mmmddddd m + PHA + ROR A ; mmmmdddd + LSR A ; -mmmmddd + LSR A ; --mmmmdd + LSR A ; ---mmmmd + LSR A ; ----mmmm + STA FBATTR+2 + PLA ; mmmddddd + AND #31 ; ---ddddd + STA FBATTR+1 + PLA ; yyyyyyym + SEC + SBC #81*2 ; Offset from 1981 + BCS :UPDFB3 ; 1981-1999 -> 00-18 + ADC #100*2 ; 2000-2080 -> 19-99 +:UPDFB3 PHA ; yyyyyyym + AND #$E0 ; yyy----- + ORA FBATTR+1 ; yyyddddd + STA FBATTR+1 + PLA ; yyyyyyym + AND #$FE ; yyyyyyy0 + ASL A ; yyyyyy00 + ASL A ; yyyyy000 + ASL A ; yyyy0000 + ORA FBATTR+2 ; yyyymmmm + STA FBATTR+2 + STZ FBATTR+3 - JSR OPENMOSFILE ; Open file - BCS :ERR - LDA OPENPL+5 ; File ref number - STA GMARKPL+1 - JSR MLI ; Call GET_EOF MLI - DB GEOFCMD - DW GMARKPL ; MARK parms same as EOF - LDA GMARKPL+2 - STA FBSIZE+0 - LDA GMARKPL+3 - STA FBSIZE+1 - LDA GMARKPL+4 - STA FBSIZE+2 - STZ FBSIZE+3 - LDA OPENPL+5 ; File ref number - STA CLSPL+1 - JSR CLSFILE - LDA #$01 ; Prepare A=file - LDX GINFOPL+7 - CPX #$0D ; Is it a directory? - BNE :UPDFB5 - LDA #$02 ; Return A=directory -:UPDFB5 RTS + JSR OPENMOSFILE ; Open file + BCS :ERR + LDA OPENPL+5 ; File ref number + STA GMARKPL+1 + JSR MLI ; Call GET_EOF MLI + DB GEOFCMD + DW GMARKPL ; MARK parms same as EOF + LDA GMARKPL+2 + STA FBSIZE+0 + LDA GMARKPL+3 + STA FBSIZE+1 + LDA GMARKPL+4 + STA FBSIZE+2 + STZ FBSIZE+3 + LDA OPENPL+5 ; File ref number + STA CLSPL+1 + JSR CLSFILE + LDA #$01 ; Prepare A=file + LDX GINFOPL+7 + CPX #$0D ; Is it a directory? + ADC #$00 ; Becomes A=2 for directory +:UPDFB5 RTS :ERR -CHKNOTFND CMP #$44 ; Convert ProDOS 'not found' - BEQ :NOTFND ; into result=$00 - CMP #$45 - BEQ :NOTFND - CMP #$46 - BNE :CHKNOTFND2 -:NOTFND LDA #$00 -:CHKNOTFND2 RTS +CHKNOTFND CMP #$44 ; Convert ProDOS 'not found' + BEQ :NOTFND ; into result=$00 + CMP #$45 + BEQ :NOTFND + CMP #$46 + BNE :CHKNOTFND2 +:NOTFND LDA #$00 +:CHKNOTFND2 RTS * Quit to ProDOS -QUIT INC $3F4 ; Invalidate powerup byte - STA $C054 ; PAGE2 off - STA $C00E ; Turn off alt charset - JSR MLI - DB QUITCMD - DW QUITPL - RTS +QUIT INC $03F4 ; Invalidate powerup byte + STA $C054 ; PAGE2 off + STA $C00E ; Alt font off + JSR MLI + DB QUITCMD + DW QUITPL + RTS * Used for *CAT, *EX and *INFO * On entry: b7=0 - short info (*CAT) @@ -879,241 +857,246 @@ QUIT INC $3F4 ; Invalidate powerup byte * b6=0 - single entry, parameter is object (*INFO) * b6=1 - multiple items, parameter is dir (*CAT, *EX) * -CATALOG >>> ENTMAIN - STA CATARG ; Stash argument - CMP #$80 ; Is it *INFO? - BNE :NOTINFO - JMP INFO ; Handle entry for *INFO -:NOTINFO LDA MOSFILE ; Length of pathname - BEQ :NOPATH ; If zero use prefix - JSR PREPATH ; Preprocess pathname - JSR WILDONE ; Handle any wildcards - JSR EXISTS ; See if path exists ... - CMP #$01 ; ... and is a file - BNE :NOTFILE - LDA #$46 ; Not found (TO DO: err code?) - BRA CATEXIT -:NOTFILE LDA #<MOSFILE - STA OPENPL+1 - LDA #>MOSFILE - STA OPENPL+2 - BRA :OPEN -:NOPATH JSR GETPREF ; Fetch prefix into PREFIX - LDA #<PREFIX - STA OPENPL+1 - LDA #>PREFIX - STA OPENPL+2 -:OPEN JSR OPENFILE - BCS CATEXIT ; Can't open dir +CATALOG >>> ENTMAIN + STA CATARG ; Stash argument + CMP #$80 ; Is it *INFO? + BNE :NOTINFO + JMP INFO ; Handle entry for *INFO +:NOTINFO LDA MOSFILE ; Length of pathname + BEQ :NOPATH ; If zero use prefix + JSR PREPATH ; Preprocess pathname + JSR WILDONE ; Handle any wildcards + JSR EXISTS ; See if path exists ... + CMP #$01 ; ... and is a file + BNE :NOTFILE + LDA #$46 ; Not found (TO DO: err code?) + BRA CATEXIT +:NOTFILE LDA #<MOSFILE + STA OPENPL+1 + LDA #>MOSFILE + STA OPENPL+2 + BRA :OPEN +:NOPATH JSR GETPREF ; Fetch prefix into PREFIX + LDA #<PREFIX + STA OPENPL+1 + LDA #>PREFIX + STA OPENPL+2 +:OPEN JSR OPENFILE + BCS CATEXIT ; Can't open dir CATREENTRY - LDA OPENPL+5 ; File ref num - STA READPL+1 - JSR RDFILE - BCC :S1 - CMP #$4C ; EOF - BEQ :EOF - BRA :READERR -:S1 JSR COPYAUXBLK - >>> XF2AUX,PRONEBLK + LDA OPENPL+5 ; File ref num + STA READPL+1 + JSR RDFILE + BCC :S1 + CMP #$4C ; EOF + BEQ :EOF + BRA :READERR +:S1 JSR COPYAUXBLK + >>> XF2AUX,PRONEBLK :READERR -:EOF LDA OPENPL+5 ; File ref num - STA CLSPL+1 - JSR CLSFILE -CATEXIT >>> XF2AUX,STARCATRET +:EOF LDA OPENPL+5 ; File ref num + STA CLSPL+1 + JSR CLSFILE +CATEXIT >>> XF2AUX,STARCATRET * PRONEBLK call returns here ... CATALOGRET - >>> ENTMAIN - LDA CATARG - CMP #$80 ; Is this an *INFO call? - BEQ INFOREENTRY - BRA CATREENTRY + >>> ENTMAIN + LDA CATARG + CMP #$80 ; Is this an *INFO call? + BEQ INFOREENTRY + BRA CATREENTRY -CATARG DB $00 +CATARG DB $00 * Handle *INFO -INFO JSR PREPATH ; Preprocess pathname - SEC - JSR WILDCARD ; Handle any wildcards - JSR EXISTS ; Check matches something - CMP #$00 - BNE INFOFIRST - JSR CLSDIR - LDA #$46 ; Not found (TO DO: err code?) - BRA CATEXIT +INFO JSR PREPATH ; Preprocess pathname + SEC + JSR WILDCARD ; Handle any wildcards + JSR EXISTS ; Check matches something + CMP #$00 + BNE INFOFIRST + JSR CLSDIR + LDA #$46 ; Not found (TO DO: err code?) + BRA CATEXIT INFOREENTRY - JSR WILDNEXT2 ; Start of new block - BCS INFOEXIT ; No more matches -INFOFIRST LDA WILDIDX - CMP #$FF ; Is WILDNEXT about to read new blk? - BEQ :DONEBLK ; If so, print this blk first - JSR WILDNEXT2 - BCS :DONEBLK ; If no more matches - BRA INFOFIRST -:DONEBLK JSR COPYAUXBLK - >>> XF2AUX,PRONEBLK + JSR WILDNEXT2 ; Start of new block + BCS INFOEXIT ; No more matches +INFOFIRST LDA WILDIDX + CMP #$FF ; Is WILDNEXT about to read new blk? + BEQ :DONEBLK ; If so, print this blk first + JSR WILDNEXT2 + BCS :DONEBLK ; If no more matches + BRA INFOFIRST +:DONEBLK JSR COPYAUXBLK + >>> XF2AUX,PRONEBLK -INFOEXIT CMP #$4C ; EOF - BNE INFOCLS - LDA #$00 ; EOF is not an error -INFOCLS JSR CLSDIR ; Be sure to close it! - BRA CATEXIT +INFOEXIT CMP #$4C ; EOF + BNE INFOCLS + LDA #$00 ; EOF is not an error +INFOCLS JSR CLSDIR ; Be sure to close it! + BRA CATEXIT -* Set prefix. Used by *CHDIR to change directory -SETPFX >>> ENTMAIN - JSR PREPATH ; Preprocess pathname - JSR WILDONE ; Handle any wildcards - BCS :ERR - LDA #<MOSFILE - STA SPFXPL+1 - LDA #>MOSFILE - STA SPFXPL+2 - JSR MLI ; SET_PREFIX - DB SPFXCMD - DW SPFXPL -:EXIT >>> XF2AUX,CHDIRRET -:ERR LDA #$40 ; Invalid pathname syn - BRA :EXIT +* Set prefix. Used by *CHDIR/*DRIVE to change directory +* +SETPFX >>> ENTMAIN + JSR PREPATH ; Preprocess pathname + JSR WILDONE ; Handle any wildcards + BCS :ERR + LDA #<MOSFILE + STA SPFXPL+1 + LDA #>MOSFILE + STA SPFXPL+2 + JSR MLI ; SET_PREFIX + DB SPFXCMD + DW SPFXPL +* Returns $4B 'Unknown storage' if *CD <notdir> +:EXIT >>> XF2AUX,CHDIRRET +:ERR LDA #$40 ; Invalid pathname syn + BRA :EXIT * Obtain info on blocks used/total blocks -DRVINFO >>> ENTMAIN - JSR PREPATH - BCS :ERR - LDA #<MOSFILE - STA GINFOPL+1 - LDA #>MOSFILE - STA GINFOPL+2 - JSR GETINFO ; GET_FILE_INFO - BCS :EXIT - PHA - >>> ALTZP ; Alt ZP & Alt LC on - LDA GINFOPL+8 ; Blcks used LSB - STA AUXBLK - LDA GINFOPL+9 ; Blks used MSB - STA AUXBLK+1 - LDA GINFOPL+5 ; Tot blks LSB - STA AUXBLK+2 - LDA GINFOPL+6 ; Tot blks MSB - STA AUXBLK+3 - >>> MAINZP ; ALt ZP off, ROM back in - PLA -:EXIT >>> XF2AUX,FREERET -:ERR LDA #$40 ; Invalid pathname syn - BRA :EXIT +DRVINFO >>> ENTMAIN + LDA MOSFILE + BNE :DRVINF2 + INC MOSFILE + LDA #'@' + STA MOSFILE+1 ; Convert "" to "@" +:DRVINF2 JSR PREPATH + BCS :ERR + LDA #<MOSFILE + STA GINFOPL+1 + LDA #>MOSFILE + STA GINFOPL+2 + JSR GETINFO ; GET_FILE_INFO + BCS :EXIT + PHA + >>> ALTZP ; Alt ZP & Alt LC on + LDA GINFOPL+8 ; Blcks used LSB + STA AUXBLK + LDA GINFOPL+9 ; Blks used MSB + STA AUXBLK+1 + LDA GINFOPL+5 ; Tot blks LSB + STA AUXBLK+2 + LDA GINFOPL+6 ; Tot blks MSB + STA AUXBLK+3 + >>> MAINZP ; ALt ZP off, ROM back in + PLA +:EXIT >>> XF2AUX,FREERET +:ERR LDA #$40 ; Invalid pathname syn + BRA :EXIT * Change file permissions, for *ACCESS * Filename in MOSFILE, flags in MOSFILE2 -SETPERM >>> ENTMAIN - JSR PREPATH ; Preprocess pathname - BCS :SYNERR - CLC - JSR WILDCARD ; Handle any wildcards - BCS :NONE - STZ :LFLAG - STZ :WFLAG - STZ :RFLAG - LDX MOSFILE2 ; Length of arg2 - INX -:L1 DEX - CPX #$00 - BEQ :MAINLOOP - LDA MOSFILE2,X ; Read arg2 char - CMP #'L' ; L=Locked - BNE :S1 - STA :LFLAG - BRA :L1 -:S1 CMP #'R' ; R=Readable - BNE :S2 - STA :RFLAG - BRA :L1 -:S2 CMP #'W' ; W=Writable - BNE :ERR2 ; Bad attribute - STA :WFLAG - BRA :L1 -:SYNERR LDA #$40 ; Invalid pathname syn - BRA :EXIT -:NONE JSR CLSDIR - LDA #$46 ; 'File not found' - BRA :EXIT -:MAINLOOP LDA #<MOSFILE - STA GINFOPL+1 - LDA #>MOSFILE - STA GINFOPL+2 - JSR GETINFO ; GET_FILE_INFO - BCS :EXIT - LDA GINFOPL+3 ; Access byte - AND #$03 ; Start with R, W off - ORA #$C0 ; Start with dest/ren on - LDX :RFLAG - BEQ :S3 - ORA #$01 ; Turn on read enable -:S3 LDX :WFLAG - BEQ :S4 - ORA #$02 ; Turn on write enable -:S4 LDX :LFLAG - BEQ :S5 - AND #$3D ; Turn off destroy/ren/write -:S5 STA GINFOPL+3 ; Access byte - JSR SETINFO ; SET_FILE_INFO - JSR WILDNEXT - BCS :NOMORE - BRA :MAINLOOP -:EXIT >>> XF2AUX,ACCRET -:NOMORE JSR CLSDIR - LDA #$00 - BRA :EXIT -:ERR2 LDA #$53 ; Invalid parameter - BRA :EXIT -:LFLAG DB $00 ; 'L' attribute -:WFLAG DB $00 ; 'W' attribute -:RFLAG DB $00 ; 'R' attribute +SETPERM >>> ENTMAIN + JSR PREPATH ; Preprocess pathname + BCS :SYNERR + CLC + JSR WILDCARD ; Handle any wildcards + BCS :NONE + STZ :LFLAG + STZ :WFLAG + STZ :RFLAG + LDX MOSFILE2 ; Length of arg2 + INX +:L1 DEX + CPX #$00 + BEQ :MAINLOOP + LDA MOSFILE2,X ; Read arg2 char + CMP #'L' ; L=Locked + BNE :S1 + STA :LFLAG + BRA :L1 +:S1 CMP #'R' ; R=Readable + BNE :S2 + STA :RFLAG + BRA :L1 +:S2 CMP #'W' ; W=Writable + BNE :ERR2 ; Bad attribute + STA :WFLAG + BRA :L1 +:SYNERR LDA #$40 ; Invalid pathname syn + BRA :EXIT +:NONE JSR CLSDIR + LDA #$46 ; 'File not found' + BRA :EXIT +:MAINLOOP LDA #<MOSFILE + STA GINFOPL+1 + LDA #>MOSFILE + STA GINFOPL+2 + JSR GETINFO ; GET_FILE_INFO + BCS :EXIT + LDA GINFOPL+3 ; Access byte + AND #$03 ; Start with R, W off + ORA #$C0 ; Start with dest/ren on + LDX :RFLAG + BEQ :S3 + ORA #$01 ; Turn on read enable +:S3 LDX :WFLAG + BEQ :S4 + ORA #$02 ; Turn on write enable +:S4 LDX :LFLAG + BEQ :S5 + AND #$3D ; Turn off destroy/ren/write +:S5 STA GINFOPL+3 ; Access byte + JSR SETINFO ; SET_FILE_INFO + JSR WILDNEXT + BCS :NOMORE + BRA :MAINLOOP +:EXIT >>> XF2AUX,ACCRET +:NOMORE JSR CLSDIR + LDA #$00 + BRA :EXIT +:ERR2 LDA #$53 ; Invalid parameter + BRA :EXIT +:LFLAG DB $00 ; 'L' attribute +:WFLAG DB $00 ; 'W' attribute +:RFLAG DB $00 ; 'R' attribute * Multi file delete, for *DESTROY * Filename in MOSFILE -MULTIDEL >>> ENTMAIN - JSR PREPATH ; Preprocess pathname - BCS :SYNERR - CLC - JSR WILDCARD ; Handle any wildcards - BCS :NONE - BRA :MAINLOOP -:SYNERR LDA #$40 ; Invalid pathname syn - BRA :EXIT -:NONE JSR CLSDIR - LDA #$46 ; 'File not found' - BRA :EXIT -:MAINLOOP JSR DODELETE - BCS :DELERR - JSR WILDNEXT - BCS :NOMORE - BRA :MAINLOOP -:EXIT >>> XF2AUX,DESTRET -:DELERR PHA - JSR CLSDIR - PLA - BRA :EXIT -:NOMORE JSR CLSDIR - LDA #$00 - BRA :EXIT +MULTIDEL >>> ENTMAIN + JSR PREPATH ; Preprocess pathname + BCS :SYNERR + CLC + JSR WILDCARD ; Handle any wildcards + BCS :NONE + BRA :MAINLOOP +:SYNERR LDA #$40 ; Invalid pathname syn + BRA :EXIT +:NONE JSR CLSDIR + LDA #$46 ; 'File not found' + BRA :EXIT +:MAINLOOP JSR DODELETE + BCS :DELERR + JSR WILDNEXT + BCS :NOMORE + BRA :MAINLOOP +:EXIT >>> XF2AUX,DESTRET +:DELERR PHA + JSR CLSDIR + PLA + BRA :EXIT +:NOMORE JSR CLSDIR + LDA #$00 + BRA :EXIT * Read machid from auxmem -MACHRD LDA $C081 - LDA $C081 - LDA $FBC0 - SEC - JSR $FE1F - BRA MAINRDEXIT +MACHRD LDA $C081 + LDA $C081 + LDA $FBC0 + SEC + JSR $FE1F + BRA MAINRDEXIT * Read mainmem from auxmem -MAINRDMEM STA A1L - STY A1H - LDA $C081 - LDA $C081 - LDA (A1L) -MAINRDEXIT >>> XF2AUX,NULLRTS ; Back to an RTS - - +MAINRDMEM STA A1L + STY A1H + LDA $C081 + LDA $C081 + LDA (A1L) +MAINRDEXIT >>> XF2AUX,NULLRTS ; Back to an RTS