M100 TS-DOS ROM UI Code
From Bitchin100 DocGarden
Jump to navigationJump to search
== TS-DOS Model 100/102 User Interface Code
; ========================================================================================= ; TS-DOS UI Entry location ; ========================================================================================= .org 3535H 3535H LXI H,FCC0H ; Start of Alt LCD character buffer 3538H MVI B,B4H ; Prepare to clear 180 bytes from the ALTLCD buffer 353AH XRA A ; Prepare to clear the ALTLCD buffer 353BH CALL 4A34H ; Fill (HL) with B bytes of A 353EH LXI H,0000H ; Prepare to get current stack pointer 3541H DAD SP ; Copy SP into HL 3542H SHLD FCCEH ; Stack pointer upon entry - pointer to arguments 3545H MVI A,01H ; Set flag to print error message to LCD - GUI mode 3547H CALL 4A85H ; Save the currently selected baud rate settings 354AH XRA A ; Zero A to clear our vars 354BH STA FCD4H ; Current Page of files being displayed 354EH STA FCDAH ; TPDD "skip page" count 3551H STA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3554H STA FCCAH ; TPDD2 Bank number 3557H INR A ; A = 1 to select 1st file on page 3558H STA FCCDH ; Currently selected file index 355BH LXI H,3564H ; Get pointer to main loop routine 355EH SHLD FCD0H ; Return vector after error 3561H CALL 4C27H ; CLS statement ; ========================================================================================= ; UI Main loop ; ========================================================================================= 3564H CALL 4C5AH ; Resume automatic scrolling 3567H CALL 3611H ; Print Copyright and files 356AH LDA FCD5H ; Load currently selected index from temp storage 356DH STA FCCDH ; Currently selected file index 3570H CALL 362FH ; Print length of selected file using inverse video ; ========================================================================================= ; Code will return here when a funtion key is pressed (except F4 & F6) ; ========================================================================================= 3573H LXI H,48B5H ; Get address of "Long jump" 3576H PUSH H ; Push "Long jump" address to stack 3577H PUSH PSW ; Save function key press to stack 3578H CPI 02H ; Test if function key is F5-F8 (Non file operation F Keys) 357AH JNC 35B9H ; Jump to Function key handler if F5-F8 (No tagging to process) 357DH LDA FCCCH ; Last Tag/Untag operation code 3580H ANA A ; Test if a tag operation was performed 3581H JZ 35B9H ; Jump to Function key handler if no tag operation performed 3584H LDA FCD6H ; Count of files on screen 3587H MOV C,A ; Save count of files for loop decrementing 3588H INR C ; Increment by 1 for loop bounding 3589H MVI B,00H ; Start with index zero on the LCD 358BH PUSH B ; Save the current index on the stack ; ========================================================================================= ; Display next file ; ========================================================================================= 358CH LDA FCCDH ; Currently selected file index 358FH STA FCD5H ; Currently selected file index - temp 3592H CALL 3AC4H ; Print selected file using normal video 3595H POP B ; Restore index from stack 3596H INR B ; Increment to the next file index to display 3597H DCR C ; Decrement the loop control 3598H JZ 48B5H ; Branch to perform "Long Jump" if all files printed to LCD 359BH MOV A,B ; Get the index of the current file 359CH STA FCD5H ; Save in temporary "current file" area 359FH STA FCCDH ; Currently selected file index 35A2H PUSH B ; Push the value on the stack for the next iteration 35A3H CALL 3AB2H ; Print currently selected file using inverse video 35A6H LHLD FCE4H ; LCD Buffer address of current file selection 35A9H DCX H ; Decrement to the Tag area for the file 35AAH MOV A,M ; Get the file's Tag code 35ABH CPI 3EH ; Compare with '>' 35ADH JNZ 358CH ; Jump to process next file if not tagged 35B0H POP B ; Pop currently selected file value from stack 35B1H POP PSW 35B2H LXI H,358CH ; Return address to display the next file 35B5H PUSH PSW ; ? Stack trickery 35B6H PUSH B ; Save current file index to stack for use after a RET operation 35B7H PUSH H ; Setup "Display next file" as a return address for RET 35B8H PUSH PSW ; ? More stack trickery ; ========================================================================================= ; Function key handler - Disk mode and dispatch to RAM mode ; ========================================================================================= 35B9H CALL 4C56H ; Stop automatic scrolling 35BCH LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 35BFH ORA A 35C0H JZ 35E2H ; Branch if in RAM mode 35C3H POP PSW 35C4H ANA A ; Test for F1 35C5H JZ 3B2EH ; Branch to F1 handler for disk 35C8H DCR A ; Test for F2 35C9H JZ 3D73H 35CCH DCR A ; Test for F3 35CDH JZ 3D9FH 35D0H DCR A ; Skip F4 - handled at lower level 35D1H DCR A ; Test for F5 35D2H JZ 3D53H 35D5H DCR A ; Skip F6 - handled at lower level 35D6H DCR A ; Test for F7 35D7H JZ 3D00H 35DAH DCR A ; Test for F8 35DBH POP H 35DCH JZ 35FEH ; Jump to exit if F8 35DFH JMP 3564H ; Jump to main loop ; ========================================================================================= ; Function key handler - RAM mode ; ========================================================================================= 35E2H POP PSW 35E3H ANA A ; Test for F1 35E4H JZ 3C4BH 35E7H DCR A ; Test for F2 35E8H JZ 3C2BH 35EBH DCR A ; Test for F3 35ECH JZ 3AF8H 35EFH DCR A ; Skip F4 - handled at lower level 35F0H DCR A ; Test for F5 35F1H JZ 3E5CH 35F4H DCR A ; Skip F6 - handled at lower level 35F5H DCR A ; Skip F7 - not defined for RAM 35F6H DCR A ; Test for F8 35F7H POP H 35F8H JZ 35FEH ; Jump to exit if F8 35FBH JMP 3564H ; Jump back to main loop ; ========================================================================================= ; This is the UI exit routine ; ========================================================================================= 35FEH CALL 4AC4H ; Restore original baud settings 3601H CALL 4BD7H ; Wait for TX empty and Reset UART to accept mode bits 3604H CALL 4C27H ; CLS statement 3607H CALL 4C5AH ; Resume automatic scrolling 360AH LXI H,0000H 360DH PUSH H 360EH JMP 00A6H ; Exit TS-DOS ; ========================================================================================= ; Print Copyright string and files ; ========================================================================================= 3611H LXI H,0101H ; Goto top left corner 3614H SHLD F639H ; Cursor row (1-8) 3617H LXI H,3E69H ; Point to "TS-DOS" copyright string 361AH CALL 4A2CH ; Send buffer at M to screen 361DH XRA A ; Indicate no previous Tag/Untag operation 361EH STA FCCCH ; Last Tag/Untag operation code 3621H MVI A,01H ; Start with 1st file in list 3623H STA FCD5H ; Currently selected file index - temp 3626H LXI H,0202H ; Goto first file entry location 3629H SHLD F639H ; Cursor row (1-8) 362CH JMP 383BH ; Draw the display ; ========================================================================================= ; Print length of selected file using inverse video ; ========================================================================================= 362FH LDA FCCDH ; Currently selected file index 3632H STA FCD5H ; Currently selected file index - temp 3635H CALL 3AB2H ; Print currently seleted file using inverse video 3638H LDA FCD5H ; Currently selected file index - temp 363BH DCR A ; Make index zero based for multiply x2 363CH STC ; Set Carry flag 363DH CMC ; Compliment (clear) carry flag 363EH RLC ; Rotate left circular 363FH MOV E,A ; E = File index * 2 to point to file length value 3640H MVI D,00H ; Clear MSB of file length offset 3642H LXI H,F685H ; Keyboard buffer - store file lengths 3645H DAD D ; Add file lenght offset from beginning of keyboard buffer 3646H XCHG ; HL <--> DE Save file length address pointer in DE 3647H LXI H,2307H ; Load position of File Size area on LCD 364AH SHLD F639H ; Cursor row (1-8) 364DH CALL 4C2BH ; Erase from cursor to end of line 3650H LHLX ; Load HL with file length 3651H CALL 4C2FH ; Start inverse character mode 3654H CALL 4C3EH ; Print binary number in HL at current position 3657H CALL 4C33H ; Cancel inverse character mode ; ========================================================================================= ; Keyboard scan loop ; ========================================================================================= 365AH CALL 3DFEH ; Process automatic power off logic 365DH CALL 4BEFH ; Scan keyboard for character (CTRL-BREAK ==> CTRL-C) 3660H JZ 365AH ; Jump to scan keyboard again if no key pressed 3663H JC 380CH ; Jump to Function Key Handler if FKey 3666H CPI 0DH ; Test for CR 3668H JZ 3722H 366BH CPI 17H ; Test for Ctrl-Up key 366DH JZ 37AAH 3670H CPI 14H ; Test for Shift-Up key 3672H JZ 3798H 3675H CPI 5DH ; Test for "]" key 3677H JZ 3798H 367AH CPI 3FH ; Test for "?" key 367CH JZ 3777H 367FH CPI 02H ; Test for Shift-Down arrow key 3681H JZ 3777H 3684H CPI 1EH ; Test for up key 3686H JZ 36EEH 3689H CPI 1FH ; Test for down key 368BH JZ 36FCH 368EH CPI 1DH ; Test for "left arrow" key 3690H JZ 36DDH 3693H CPI 1CH ; Test for "Right arrow" key 3695H JZ 36CAH 3698H CPI 20H ; Test for space key 369AH JZ 36CAH ; Treat space the same as right arrow 369DH ANI DFH ; Convert to Upper case 369FH CPI 52H ; Test for 'R' character 36A1H JZ 3759H 36A4H CPI 54H ; Test for 'T' character 36A6H JZ 37EEH 36A9H CPI 41H ; Test for "A" key 36ABH JZ 3715H 36AEH CPI 47H ; Test for "G" key 36B0H JZ 3715H 36B3H CPI 55H ; Test for "U" key 36B5H JZ 37AEH 36B8H CPI 44H ; Test for "D" key 36BAH JZ 39B9H 36BDH CPI 4CH ; Test for "L" key 36BFH JZ 39C2H 36C2H CPI 50H ; Test for "P" key 36C4H JZ 39C2H 36C7H JMP 365AH ; Go scan keyboard again ; ========================================================================================= ; Handle Right Arrow key from TS-DOS key scan ; ========================================================================================= 36CAH MVI A,01H ; Prepare to add 1 to selected file 36CCH LXI H,FCD5H ; Currently selected file index - temp storage 36CFH ADD M ; Add 1 to the selected file index 36D0H INX H ; Point to file count on screen 36D1H CMP M ; Compare new index with screen file count 36D2H JC 370AH ; Jump to process new file if we didn't wrap 36D5H JZ 370AH ; Jump to process new file if = file count 36D8H MVI A,01H ; Wrap to the first file 36DAH JMP 370AH ; Go process file 1 as the new selection ; ========================================================================================= ; Handle Left Arrow key from TS-DOS key scan ; ========================================================================================= 36DDH LDA FCD5H ; Currently selected file index - temp storage 36E0H DCR A ; Move to next lowest file index 36E1H JNZ 370AH ; If no wrap, jump to process new selection 36E4H LDA FCD6H ; Count of files on screen 36E7H ANA A ; Ensure there is at least 1 file on the screen 36E8H JZ 365AH ; Jump to keyboard scan loop if no files on LCD 36EBH JMP 370AH ; Go process new selection as the max (wrap-around) ; ========================================================================================= ; Handle Up Arrow key from TS-DOS key scan ; ========================================================================================= 36EEH LDA FCD5H ; Currently selected file index - temp storage 36F1H SUI 04H ; Subtract 4 from file count (4 files per line) 36F3H JC 365AH ; Jump to keysacn loop if negative 36F6H JZ 365AH ; Jump to keysacn loop if zero 36F9H JMP 370AH ; Go process the new file index setting ; ========================================================================================= ; Handle Down Arrow key from TS-DOS key scan ; ========================================================================================= 36FCH MVI A,04H ; There are 4 files per line 36FEH LXI H,FCD5H ; Currently selected file index - temp storage 3701H ADD M ; Add 4 to the index number 3702H MOV C,A ; Save new index for comparison and further processing 3703H INX H ; Maximum file index count 3704H MOV A,M ; Load maximum index for bounds 3705H CMP C ; Compare new index with maximum 3706H JC 365AH ; Jump to keyboard scan if moving past last file 3709H MOV A,C ; Restore new current file index 370AH PUSH PSW ; Save new file index for storage after the call 370BH CALL 3AC4H ; Print selected file using normal video 370EH POP PSW ; Restore new file index from stack 370FH STA FCCDH ; Save the new file index 3712H JMP 362FH ; Print length of selected file using inverse video. ; ========================================================================================= ; Handle "A" or "G" key from TS-DOS key scan ; ========================================================================================= 3715H MVI A,3EH ; Load ">" for the tag symbol 3717H CALL 37CAH ; Go tag all files on the LCD 371AH MVI A,01H ; Indicate last operation as "Tag All" 371CH STA FCCCH ; Last Tag/Untag operation code 371FH JMP 362FH ; Print length of selected file using inverse video. ; ========================================================================================= ; Handle Enter key from TS-DOS key scan - Change Directory ; ========================================================================================= 3722H LDA FCCBH ; Get NADSBox/Desklink/TPDD2 flag 3725H CPI 02H ; Test if NADSBox current directory valid 3727H JNZ 365AH ; Back to keyscan if no "current directory" - Enter is meaningless 372AH LHLD FCE4H ; LCD Buffer address of current file selection 372DH LXI B,0007H ; Load offset of file extension 3730H DAD B ; Point to file extension of selected file 3731H MOV A,M ; Load the 1st byte of the file extension 3732H CPI 3CH ; Test if 1st byte of extension is "<" 3734H JNZ 365AH ; Jump to keyscan if current selection not directory entry 3737H CALL 4A3BH ; Initialize blank filename and attribute byte 373AH LHLD FCE4H ; LCD Buffer address of current file selection 373DH CALL 3D95H ; Copy filename at (HL) to TX buffer 3740H CALL 408AH ; Open TPDD file for Read Mode 3743H LXI H,0002H ; Load opcode to close currently opened file 3746H CALL 409BH ; Send Request in HL and await response 3749H LHLD FCE4H ; LCD Buffer address of current file selection 374CH LXI D,FCC0H ; NADSBox current directory storage 374FH LXI B,0009H ; Copy 9 bytes of NADSBox directory to the LCD 3752H CALL 4A05H ; Move BC bytes from M to (DE) with increment 3755H XRA A ; Clear A to show 1st page of files 3756H JMP 378AH ; Branch to show the page of files in A ; ========================================================================================= ; Handle "R" key from TS-DOS key scan ; ========================================================================================= 3759H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 375CH ANA A ; Test if in Disk mode 375DH JNZ 362FH ; Jump to keyscan if in Disk mode 3760H LHLD FCE4H ; LCD Buffer address of current file selection 3763H CALL 4902H ; Copy filename at (HL) to current BASIC program 3766H CALL 4A51H ; Get RAM directory address of current BASIC program 3769H CPI C0H ; Test if filetype is .DO 376BH CZ 5000H ; Call routine to Compress / Decompress .DO files 376EH CALL 4C0FH ; Update system pointers 3771H CALL 3611H ; Print Copyright and files 3774H JMP 362FH ; Jump to keyscan ; ========================================================================================= ; Handle "?" and Shift-Down key from TS-DOS key scan ; ========================================================================================= 3777H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 377AH ANA A ; Test if RAM mode 377BH JZ 365AH ; Branch to keyscan if in RAM mode 377EH LDA FCD6H ; Count of files on screen 3781H CPI 14H ; Maximum number of files that fit on the screen 3783H JC 365AH ; Branch to keyscan if on last page 3786H LDA FCD4H ; Current Page of files being displayed 3789H INR A ; Increment to next page of files ; ========================================================================================= ; Show the page of files indicated by A ; ========================================================================================= 378AH STA FCD4H ; Current Page of files being displayed 378DH MVI A,01H ; Go to 1st file on the new page 378FH STA FCCDH ; Currently selected file index 3792H CALL 3611H ; Print copyright and files 3795H JMP 362FH ; Print length of selected file using inverse video ; ========================================================================================= ; Handle "]" and Shift-Up key from TS-DOS key scan ; ========================================================================================= 3798H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 379BH ANA A ; Test if RAM mode 379CH JZ 365AH ; Branch to keyscan if in RAM mode 379FH LDA FCD4H ; Current Page of files being displayed 37A2H ANA A ; Test if current page is zero 37A3H JZ 365AH ; Branch to keyscan if already on page 0 37A6H DCR A ; Decrement the page number 37A7H JMP 378AH ; Show the page of files indicated by A ; ========================================================================================= ; Handle Ctrl-Up key from TS-DOS key scan ; ========================================================================================= 37AAH XRA A ; Go to page zero 37ABH JMP 378AH ; Show the page of files indicated by A ; ========================================================================================= ; Handle "U" key from TS-DOS key scan - Remove all tags ; ========================================================================================= 37AEH MVI A,20H ; Display ' ' as the tag marker 37B0H CALL 37CAH ; Go process tag for all files 37B3H XRA A ; Indicate last tag operation was untag 37B4H STA FCCCH ; Store as "last tag" operation 37B7H JMP 362FH ; Print length of selected file using inverse video ; ========================================================================================= ; Swap TPDD2 Bank number ; ========================================================================================= 37BAH LDA FCCBH ; NADSBox / Desklink / TPDD2 flag 37BDH DCR A ; Test if the flag = 1 (TPDD2) 37BEH JNZ 365AH ; Jump to keyscan if not 1 37C1H LDA FCCAH ; Get TPDD Bank Number 37C4H XRI 01H ; Switch to the other bank 37C6H STA FCCAH ; Save TPDD bank number 37C9H RET ; ========================================================================================= ; Process Tag or Untag for all files on screen ; ========================================================================================= 37CAH STA FCCCH ; Store tag/untag code for later 37CDH LDA FCD6H ; Get Maximum file count on screen 37D0H ANA A ; Test for zero 37D1H RZ ; Return if no files on screen 37D2H XRA A ; Clear A 37D3H INR A ; A=1 to selet 1st file 37D4H STA FCD5H ; Currently selected file index 37D7H CALL 3ACDH ; Calculate Row and Column of soon-to-be (newly) selected file 37DAH LHLD FCE4H ; LCD Buffer address of current file selection 37DDH DCX H ; Point to Tag location for the file 37DEH LDA FCCCH ; Get the tag/untag code 37E1H RST 4 ; Display A to the LCD 37E2H LDA FCD5H ; Get currently selected file index 37E5H LXI H,FCD6H ; Point to count of files on screen 37E8H CMP M ; Compare current selection with count of files on LCD 37E9H JC 37D3H ; Jump to process next file if more files left 37ECH ANA A ; Set zero flag to indicate files were tagged/untagged 37EDH RET ; ========================================================================================= ; Handle "T" key key from TS-DOS key scan - TAG ; ========================================================================================= 37EEH CALL 3ACDH ; Calculate Row and Column of soon-to-be (newly) selected file 37F1H CALL 4C2FH ; Start inverse character mode 37F4H LHLD FCE4H ; LCD Buffer address of current file selection 37F7H DCX H ; Point to the "Tag" area for the file 37F8H MVI A,3EH ; Load the code for ">" 37FAH CMP M ; Compare if file is already tagged 37FBH JNZ 3800H ; Skip ahead if already tagged 37FEH MVI A,20H ; Need to untag - load the untag code 3800H RST 4 ; Display the tag code on the LCD 3801H CALL 4C33H ; Cancel inverse character mode 3804H LXI H,FCCCH ; Point to "last tag" operation code 3807H MVI M,01H ; Indicate last operation was "tag" 3809H JMP 36CAH ; Move to next file - jump to Right Arrow key handler ; ========================================================================================= ; 1st level Function Key Handler (handles F4 and F6) ; ========================================================================================= 380CH CPI 08H ; Test for valid function key code 380EH JNC 365AH ; Branch back to scan loop if invalid 3811H CPI 05H ; Test for F6 3813H JZ 3833H ; Jump if F6 pressed 3816H CPI 03H ; Test for F4 3818H RNZ ; Return to "Main Loop" if not F4 pressed 3819H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 381CH XRI 01H ; Swap RAM/DISK mode 381EH STA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3821H XRA A ; Clear A to go to 1st page of files 3822H STA FCD4H ; Current Page of files being displayed 3825H MVI A,01H ; Select the 1st file in the page 3827H STA FCCDH ; Currently selected file index 382AH CALL 4C27H ; CLS statement 382DH CALL 3611H ; Print the title bar and files 3830H JMP 362FH ; Print length of selected file using inverse video. ; ========================================================================================= ; F6 Function Key Handler ; ========================================================================================= 3833H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3836H ANA A ; Test if in RAM or DISK mode 3837H RZ ; Return if RAM mode 3838H JMP 37AAH ; Jump to Ctrl-Up key handler ; ========================================================================================= ; Draw the display. This takes care of RAM and Disk mode displays, handles ; skipping page number to the proper "Disk" page, displaying the Bank# or ; current directory for NADSBox/Desklink, showing free space, filling in ; empty slots with "-.-", etc. ; ========================================================================================= 383BH LXI H,F685H ; Keyboard buffer 383EH SHLD FCDBH ; Initialize pointer to file length table (in keyboard buffer) 3841H XRA A ; Prepare to set 1st file lenght to zero 3842H MOV M,A ; Set LSB of length of 1st file to zero 3843H INX H ; Increment to MSB of length 3844H MOV M,A ; Set MSB of length of file to zero 3845H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3848H ANA A ; Test if RAM or DISK 3849H JZ 395DH ; Jump to show RAM files if in RAM mode 384CH XRA A ; Prepare to initialize the "page being processed" variable 384DH STA FCDAH ; Clear the "page being processed" variable 3850H CALL 4735H ; Clear #files displayed, init TPDD and send 1st file dir referene opcode 3853H JNZ 390FH ; Process unformated disk (empty slots and error message) 3856H LDA FCD4H ; Current Page of files being displayed 3859H ANA A ; Test if displaying page 0 385AH JZ 3871H ; Jump if showing page 0 - don't need to skikp any pages 385DH STA FCDAH ; Initialize the number of pages left to skip count 3860H CALL 4742H ; Read next page of files from server 3863H LDA FCDAH ; Get the "Pages left to skip" count 3866H DCR A ; Decrement the remaining skip page count 3867H JNZ 385DH ; Keep reading pages until we have skipped enough pages 386AH XRA A ; Prepare to clear the remaining skip page count 386BH STA FCDAH ; Clear the remaining skip page count 386EH STA FCD6H ; Count of files on screen 3871H CALL 4742H ; Read next page of files from server 3874H LDA FCD6H ; Count of files on screen 3877H CPI 14H ; Test if all file slots are full 3879H CC 39AAH ; Print "-.-" for all empty file slots (if any) ; ========================================================================================= ; Print NADSBox directory or TPDD Bank number to LCD ; ========================================================================================= 387CH LDA FCCBH ; NADSBox / Desklink / TPDD2 flag 387FH ANA A ; Test if server is TPDD 3880H JZ 389FH ; Skip processing Bank # or Current Dir if TPDD 3883H DCR A ; Test if server is TPDD2 3884H JZ 388DH ; Jump to print bank number if TPDD2 3887H LXI H,FCC0H ; Load pointer to NADSBox current directory storage 388AH JMP 38A5H ; Jump to print the NADSBox / Desklink directory ; ========================================================================================= ; Print the TPDD Bank number to LCD ; ========================================================================================= 388DH LXI H,2401H ; Go to Row 1, column 24 3890H SHLD F639H ; Cursor row (1-8) 3893H CALL 4C2FH ; Start inverse character mode 3896H MVI A,23H ; ASCII code for '#' 3898H RST 4 ; Send character in A to the LCD 3899H LDA FCCAH ; Load TPDD Bank number 389CH ADI 30H ; Convert to ASCII digit 389EH RST 4 ; Send it to the LCD 389FH CALL 4C33H ; Cancel inverse character mode 38A2H JMP 38B8H ; Branch to print the function menu, RAM/Disk free, etc. ; ========================================================================================= ; Print the NADSBox / Desklink current directory in title bar ; ========================================================================================= 38A5H PUSH H ; Save address of the directory string 38A6H LXI H,2101H ; Prepare to position the cursor in the title bar 38A9H SHLD F639H ; Cursor row (1-8) 38ACH CALL 4C2FH ; Start inverse character mode 38AFH POP H ; Retrieve the directory string from the stack 38B0H MVI C,06H ; Prepare to redraw 6 chars with inverse video 38B2H CALL 48E5H ; Redraw C characters from buffer at HL using current video mode 38B5H CALL 4C33H ; Cancel inverse character mode ; ========================================================================================= ; Print funtion menu, RAM/Disk free & selected file length ; ========================================================================================= 38B8H LXI H,3E97H ; Point to Disk function menu 38BBH LXI B,3936H ; Routine to print free disk space 38BEH LDA FCD9H ; RAM/Disk mode 38C1H ANA A ; Test if in Disk mode and skip ahead to print Disk FKeys 38C2H JNZ 38CBH ; Skip ahead if in disk mode to keep vectors 38C5H LXI H,3ED9H ; Point to RAM function menu 38C8H LXI B,3922H ; Routine to print free RAM space 38CBH PUSH B ; Save routine address to stack 38CCH PUSH H ; Save pointer to function text to stack 38CDH LDA FCCDH ; Currently selected file index 38D0H LXI H,FCD6H ; Count of files on screen 38D3H CMP M ; Compare selected file with count of files on screen 38D4H JC 38DDH ; Branch if within bounds 38D7H MOV A,M ; Get the file count 38D8H ANA A ; Test if #files = 0 38D9H JNZ 38DDH ; Skip ahead if not zero 38DCH INR A ; Don't allow a count of zero - must be 1 38DDH STA FCD5H ; Currently selected file index - temp 38E0H LXI H,0B07H ; Row & column of start of text 38E3H SHLD F639H ; Cursor row (1-8) 38E6H POP H ; Get address of text from the stack and display it 38E7H CALL 4A2CH ; Send buffer at M to screen 38EAH LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 38EDH ANA A ; Test if in RAM mode 38EEH JZ 3905H ; Jump if in RAM mode (0 = RAM) 38F1H LDA FCCBH ; NADSBox / Desklink / TPDD2 flag 38F4H ANA A ; Test if server is TPDD 38F5H JZ 3905H ; Skip printing of "Bank" or "Mkdr" if TPDD 38F8H LXI H,3FE9H ; Point to text for "Bank" 38FBH DCR A ; Test if server is TPDD2 38FCH JZ 3902H ; Jump to print "Bank" if TPDD2 38FFH LXI H,3FD8H ; Point to text for "Mkdr" 3902H CALL 4A2CH ; Send buffer at M to screen 3905H CALL 3940H ; Display DISK ON/OFF status on LCD 3908H LXI H,1507H ; Point to location for "Free" space (RAM or DISK) 390BH SHLD F639H ; Cursor row (1-8) 390EH RET ; ========================================================================================= ; Handle unformatted disks. Print message and show empty slots. ; ========================================================================================= 390FH XRA A ; Starting with slot zero... 3910H CALL 39AAH ; Print "-.-" for all empty file slots 3913H LXI H,3E97H ; Point to Disk Function menu string 3916H LXI B,391CH ; Print NOT FORMATTED to the display 3919H JMP 38CBH ; Go process the print and jump to error handler ; ========================================================================================= ; Print "NOT FORMATTED" on the LCD and return ; ========================================================================================= 391CH LXI H,`H ; Point to "NOT FORMATTED" string 391FH JMP 4A2CH ; Send buffer at M to screen ; ========================================================================================= ; Print RAM free space at current posiiton ; ========================================================================================= 3922H LHLD FBB2H ; Start of variable data pointer 3925H XCHG ; HL <--> DE 3926H LHLD F678H ; BASIC string buffer pointer 3929H MOV A,L ; Prepare for 16 bit subtract 392AH SUB E ; Subtract LSB 392BH MOV L,A ; Save LSB of difference for printing 392CH MOV A,H ; Prepare for subtrating MSB 392DH SBB D ; Subtract MSB 392EH MOV H,A ; Save in H for printing 392FH LXI B,FFF2H ; Load signed number -14 3932H DAD B ; Subtract 14 from free memory 3933H JMP 4C3EH ; Print binary number in HL at current position ; ========================================================================================= ; Display free space on disk ; ========================================================================================= 3936H CALL 4A10H ; Calculate free space on disk 3939H CALL 4C3EH ; Print binary number in HL at current position 393CH MVI A,30H ; Prepare to add an extra '0' since calc is /10 393EH RST 4 ; Send A to the LCD 393FH RET ; ========================================================================================= ; Display DISK ON/OFF status on LCD ; ========================================================================================= 3940H LDA FCD9H ; DISK/RAM mode (0=RAM, 1=DISK) 3943H ANA A ; Test if in RAM mode 3944H RNZ ; Return if not in RAM mode 3945H LDA FB2CH ; DISK-OFF/ON status 3948H LXI D,3FF2H ; Load pointer to "OFF" text 394BH CPI DBH ; Test if DISK mode (vector LSB) indicates ON or OFF 394DH JZ 3953H ; Branch if in DISK-OFF mode 3950H LXI D,3FF6H ; Load pointer to "ON" text 3953H LXI H,1908H ; Location of DISK-OFF/ON indication on LCD 3956H SHLD F639H ; Cursor row (1-8) 3959H XCHG ; HL = pointer to text in DE 395AH JMP 4A2CH ; Send buffer at M to screen ; ========================================================================================= ; Display RAM files to LCD and calculate file lengths ; ========================================================================================= 395DH LXI H,F9BAH ; Load pointer to 1st available file slot in catalog 3960H XRA A ; Set count of RAM files on screen to zero 3961H STA FCD6H ; Count of files on screen 3964H MVI A,14H ; Get max # files that will fit on LCD 3966H DCR A ; Decrement the max file count 3967H PUSH PSW ; Save count to the stack 3968H MOV A,M ; Get file type 3969H XRI 80H ; Compliment ?active bit 396BH ANI 9FH ; Test if file is active and should be displayed 396DH JNZ 3996H ; Branch to test next file if not displayed 3970H PUSH H ; Save address of current catalog file 3971H INX H ; Point to file address 3972H MOV E,M ; Get LSB of file address 3973H INX H ; Point to MSB of address 3974H MOV D,M ; Get MSB of file address 3975H XTHL ; HL <--> (SP) Get address of file within catalog 3976H PUSH H ; Push pointer to MSB of address on stack 3977H CALL 3CD3H ; Calculate length of RAM file 397AH XCHG ; HL <--> DE DE has the length 397BH CALL 4791H ; Store next file length to keyboard buffer 397EH POP H ; Get catalog address of current file from stack 397FH XTHL ; HL <--> (SP) swap catalog address with pointer to MSB of file address 3980H INX H ; Increment to filename 3981H MVI C,06H ; Prepare to print 6 characters of filename 3983H CALL 48E5H ; Redraw C characters from buffer at HL using current video mode 3986H MVI A,2EH ; Load code for '.' 3988H RST 4 ; Send A to the LCD 3989H MVI C,02H ; Prepare to print 2 ext bytes to LCD 398BH CALL 48E5H ; Redraw C characters from buffer at HL using current video mode 398EH MVI A,20H ; Load code for space 3990H RST 4 ; Send A to the LCD 3991H LXI H,FCD6H ; Count of files on screen 3994H INR M ; Increment number of files displayed on LCD 3995H POP H ; Get catalog address of file from stack 3996H LXI D,000BH ; Load offset to next file locaion in catalog 3999H DAD D ; Offset HL to next file 399AH POP PSW ; Restore the file count from the stack 399BH DCR A ; Decrement the max file count on the LCD 399CH JNZ 3967H ; Branch to test and display next file until zero 399FH LDA FCD6H ; Get the count of files actually displayed on screen 39A2H CPI 14H ; Test if max number of files displayed 39A4H CC 39AAH ; Branch to display "-.-" for remaining empty slots if not max 39A7H JMP 387CH ; Print NADSBox directory or TPDD Bank number to LCD ; ========================================================================================= ; Print "-.-" for all empty file slots ; ========================================================================================= 39AAH PUSH PSW ; Save current file index count on stack 39ABH LXI H,3FCDH ; Point to "-.-" text 39AEH CALL 4A2CH ; Send buffer at M to screen 39B1H POP PSW ; Restore current count 39B2H INR A ; Increment file index number 39B3H CPI 14H ; Compare A with max files that fit on LCD 39B5H JNZ 39AAH ; Jump to print next "-.-" if not done 39B8H RET ; ========================================================================================= ; Handle "D" key from TS-DOS key scan ; ========================================================================================= 39B9H CALL 3AA8H ; Test if printer busy. Return if not busy or error 39BCH CALL 4C52H ; LCOPY statement 39BFH JMP 362FH ; Print length of selected file using inverse video. ; ========================================================================================= ; Handle "L", "P" and "O" keys from TS-DOS key scan - list or print .DO file contents ; ========================================================================================= 39C2H STA FCDFH ; Save key pressed 39C5H LXI D,0007H ; Load offset of Extension bytes 39C8H LHLD FCE4H ; LCD Buffer address of current file selection 39CBH DAD D ; Point to extension bytes in LCD buffer 39CCH MOV A,M ; Get 1st extension byte 39CDH CPI 44H ; Compare byte with "D" 39CFH JNZ 362FH ; Print length of selected file using inverse video if not "D" 39D2H INX H ; Point to 2nd extension byte 39D3H MOV A,M ; Load 2nd extension byte for comparison 39D4H CPI 4FH ; Compare with "0" 39D6H JNZ 3A06H ; Jump to print compressed file 39D9H CALL 3A49H ; Prepare file for reading (open disk file, address of RAM file) 39DCH LDA FCDFH ; Restore key pressed 39DFH CPI 4CH ; Test if key was "L" - List to LCD 39E1H CZ 4C27H ; CLS statement if LCD 39E4H CNZ 3AA8H ; Test if printer busy. Return if not busy or error 39E7H CALL 3A24H ; Get next block of data to display/print (HL=address) 39EAH PUSH PSW ; Push Z flag indicating if a full 128 bytes was read 39EBH CALL 3A6BH ; Display / print file data bytes at HL, A has length 39EEH POP PSW ; Get Z flag indicating if 128 bytes read 39EFH JZ 39E7H ; Jump to process more if 128 bytes were read last time 39F2H LDA FCDFH ; Restore key pressed 39F5H CPI 4CH ; Test if key was "L" 39F7H JNZ 3A00H ; Skip beep if printing 39FAH MVI A,07H ; Load code for BELL 39FCH RST 4 ; Go print a BELL (beep) 39FDH CALL 3DF8H ; Process power-off logic and wait for a key from keyboard ; ========================================================================================= ; Clear screen and perform Long Jump ; ========================================================================================= 3A00H CALL 4C27H ; CLS statement 3A03H JMP 48B5H ; Branch to "Long Jump" operation ; ========================================================================================= ; Handler for the "O" key - print a compressed file?? ; ========================================================================================= 3A06H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3A09H ANA A ; Test if in Disk mode 3A0AH JNZ 362FH ; Jump to keyscan if in Disk mode 3A0DH LHLD FCE4H ; LCD Buffer address of current file selection 3A10H CALL 4902H ; Copy filename at (HL) to current BASIC program 3A13H CALL 4A51H ; Get RAM directory address of current BASIC program 3A16H CPI C0H ; Test if filetype is .DO 3A18H CZ 5004H ; Call routine to Compress / Decompress .DO files 3A1BH CALL 4C0FH ; Update system pointers 3A1EH CALL 3611H ; Print Copyright and files 3A21H JMP 362FH ; Jump to keyscan ; ========================================================================================= ; Get next 128 bytes (or less) of data from RAM or disk file for display ; ========================================================================================= 3A24H LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3A27H ANA A ; Test if RAM mode 3A28H JNZ 40B6H ; If not RAM mode, go send TPDD_READ data opcode and recieve response 3A2BH LHLD FCDDH ; Get length of file to be displayed / printed 3A2EH LXI B,0080H ; Prepare to subtract 128 from length 3A31H MOV A,C ; Save 128 to A 3A32H DSUB ; Subtract 128 from file length 3A33H JNC 3A3AH ; Branch if length >= 128 3A36H DAD B ; Add 128 back to length to print "partial" buffer 3A37H MOV A,L ; Move remainder of bytes to display/print 3A38H MOV L,H ; Clear LSB of remainder 3A39H MOV C,A ; Move LSB of remainder to C 3A3AH SHLD FCDDH ; Save new remaining file length 3A3DH LHLD FCE0H ; Load the address to be printed / saved 3A40H PUSH H ; Save on stack 3A41H DAD B ; Update address to be used for display/printing next time 3A42H SHLD FCE0H ; Save address to be displayed / printed 3A45H POP H ; Retrieve address to be printed this loop from stack 3A46H CPI 80H ; Compare length with maximum 3A48H RET ; ========================================================================================= ; Initialize Selected file for display (RAM or Disk) ; ========================================================================================= 3A49H CALL 4A3BH ; Initialize blank filename and attribute byte 3A4CH LHLD FCE4H ; LCD Buffer address of current file selection 3A4FH LDA FCD9H ; RAM / Disk mode (0=RAM, 1=DISK) 3A52H ANA A ; Test if in RAM mode 3A53H JNZ 3A65H ; Branch to process Disk files if in Disk mode 3A56H CALL 4A4BH ; Get RAM directory address of selected file 3A59H PUSH D ; Push file address to stack 3A5AH CALL 3CD3H ; Calculate length of RAM file, HL=address of catalog entry, DE=file address 3A5DH SHLD FCDDH ; Save length to FDC emulation sector storage area 3A60H POP H ; Pop address of file into H 3A61H SHLD FCE0H ; Save file address 3A64H RET ; ===================================================================================== ; Send TPDD Open command to open selected file ; ===================================================================================== 3A65H CALL 3D95H ; Copy filename at (HL) to TX buffer 3A68H JMP 408AH ; Open TPDD file for Read Mode ; ===================================================================================== ; Display / print file data bytes at HL, A has length ; ===================================================================================== 3A6BH XCHG ; HL <--> DE 3A6CH ORA A ; Test if length = 0 3A6DH RZ ; Return if length = 0 3A6EH MOV C,A ; Save length count in C 3A6FH LDA FCDFH ; Load key press value 3A72H CPI 4CH ; Test if key was "L" 3A74H JNZ 3A82H ; Jump to print contents if not "L" 3A77H CALL 3A8FH ; Check for CTRL-C 3A7AH LDAX D ; Load next byte from src pointer 3A7BH RST 4 ; Send A to LCD 3A7CH INX D ; Increment the pointer 3A7DH DCR C ; Decrement the length count 3A7EH JNZ 3A77H ; Keep looping until all data displayed 3A81H RET ; ===================================================================================== ; Print file data bytes at HL, A has length ; ===================================================================================== 3A82H CALL 3A8FH ; Test for CTRL-C, etc. 3A85H LDAX D ; Load next file byte from source poiner 3A86H CALL 4C42H ; Print A to printer, expanding tabs if necessary 3A89H INX D ; Increment pointer 3A8AH DCR C ; Decrement length count 3A8BH JNZ 3A82H ; Keep looping until all data printed 3A8EH RET ; ========================================================================================= ; Test for ESC, CTRL-C or Space ; ========================================================================================= 3A8FH CALL 4C4AH ; Check keyboard queue for pending characters 3A92H RZ ; Return if no pending characters 3A93H CALL 4BEBH ; Wait for key from keyboard 3A96H CPI 03H ; Test for F4 maybe? 3A98H JZ 3A00H ; Clear screen and perform Long Jump if F4 maybe? 3A9BH CPI 1BH ; Test for ESC key 3A9DH JZ 3A00H ; Clear screen and perform Long Jump if ESC 3AA0H CPI 20H ; Test for space key 3AA2H JNZ 3A8FH ; Branch back to wait for ESC, CTRL-C or space if not space 3AA5H JMP 4BEBH ; Wait for key from keyboard ; ========================================================================================= ; Test if printer busy. Return if not busy, print error if it is ; ========================================================================================= 3AA8H IN BBH ; Get printer port input 3AAAH ANI 06H ; Mask all but BUSY and /BUSY 3AACH XRI 02H ; Compliment /BUSY 3AAEH JNZ 487BH ; Printer not ready / FF error 3AB1H RET ; ========================================================================================= ; Print currently selected file using inverse video ; ========================================================================================= 3AB2H CALL 3ACDH ; Calculate Row and Column of newly selected file 3AB5H SHLD FCE4H ; LCD Buffer address of current file selection 3AB8H CALL 4C2FH ; Start inverse character mode 3ABBH DCX H ; Start drawing from left edge of selection (include space) 3ABCH MVI C,0AH ; Draw 10 characters 3ABEH CALL 48E5H ; Redraw C characters from buffer at HL using current video mode 3AC1H JMP 4C33H ; Cancel inverse character mode ; ========================================================================================= ; Print selected file using normal video to "unselect" it ; ========================================================================================= 3AC4H CALL 4C33H ; Cancel inverse character mode 3AC7H CALL 3ACDH ; Calculate row and column of newly selected file 3ACAH JMP 3ABBH ; Print the file to the LCD ; ========================================================================================= ; Calculate Row and Column of soon-to-be (newly) selected file ; ========================================================================================= 3ACDH LDA FCD5H ; Currently selected file index 3AD0H DCR A ; Make selected file zero based 3AD1H MOV L,A ; Save index to 16-bit HL 3AD2H MVI H,00H ; Make MSB zero 3AD4H LXI D,000AH ; Prepare to multiply index * 10 cols 3AD7H CALL 4C1FH ; Signed integer muliply (FAC1=HL*DE) 3ADAH LXI D,FE28H ; Load address of line 2 in the LCD buffer 3ADDH DAD D ; Calculate starting LCD buffer address for this file 3ADEH INX H ; Skip the "tag" space on the LCD 3ADFH PUSH H ; Save address on the stack 3AE0H LXI B,FE00H ; Load starting address of LCD character buffer 3AE3H DSUB ; Calculate file start offset from start of LCD buffer 3AE4H LXI D,0028H ; Load 1 LCD line width 3AE7H XCHG ; HL <--> DE Prepare for divide 3AE8H CALL 4C1BH ; Signed integer divide (FAC1=DE/HL) 3AEBH MOV A,L ; Save selected file's row number to A 3AECH INR A ; Make row 1-based 3AEDH STA F639H ; Cursor row (1-8) 3AF0H XCHG ; HL <--> DE DE had remainder*2 from divide 3AF1H ASHR ; Divide HL by 2 3AF2H MOV A,L ; Prepare to save remainder as the column 3AF3H STA F63AH ; Cursor column (1-40) 3AF6H POP H ; Restore address of LCD buffer location from stack 3AF7H RET ; ========================================================================================= ; F3 Function key handler for RAM mode - Rename ; ========================================================================================= 3AF8H CALL 4A4BH ; Get RAM directory address of selected file 3AFBH SHLD FCE0H ; Save address of file being processed 3AFEH LXI H,3F4AH ; Address of "New name" string 3B01H CALL 3E1AH ; Get 6-byte input filename from keyboard 3B04H RZ ; Return if no input provided 3B05H CALL 4902H ; Copy filename at (HL) to current BASIC program 3B08H LHLD FCE0H ; Load RAM directory address of file being renamed 3B0BH LXI B,0009H ; Load offset of extension within catalog entry 3B0EH DAD B ; Point to extension bytes 3B0FH LXI D,FC99H ; Load address of extension field of current BASIC program name 3B12H MOV A,M ; Get 1st byte of extension of catalog file being renamed 3B13H STAX D ; Save extension byte in current BASIC program filename - preserve EXT 3B14H INX D ; Point to 2nd ext byte of BASIC program name 3B15H INX H ; Point to 2nd ext byte of catalog filename 3B16H MOV A,M ; Get 2nd extension byte from catalog filename 3B17H STAX D ; Save byte in current BASIC program filename area 3B18H CALL 4A51H ; Get RAM directory address of current BASIC program 3B1BH JNZ 487EH ; If found, jump to File Exists Error 3B1EH LHLD FCE0H ; Load catalog address of file being renamed 3B21H INX H ; Point to LSB of file address 3B22H INX H ; Point to MSB of file address 3B23H INX H ; Point to name 3B24H LXI D,FC93H ; Load address of filename of current BASIC program 3B27H LXI B,0006H ; Prepare to copy 6 bytes of filename (ext doesn't change) 3B2AH XCHG ; HL <--> DE 3B2BH JMP 4A05H ; Move BC bytes from M to (DE) with increment ; ========================================================================================= ; F1 Function key handler for DISK mode - Load ; ========================================================================================= 3B2EH CALL 4A3BH ; Initialize blank filename and attribute byte 3B31H LHLD FCE4H ; LCD Buffer address of current file selection 3B34H CALL 3D95H ; Copy filename at (HL) to TX buffer 3B37H LDA FCCCH ; Last Tag/Untag operation code 3B3AH ANA A ; Test if a tag operation is pending 3B3BH JNZ 3B56H ; Branch if doing tag load operation 3B3EH LXI H,3F7AH ; Point to "Load as:" text 3B41H CALL 3E1AH ; Get 6-byte filename input from keyboard 3B44H JZ 3B56H ; Jump to use existing disk name as filename 3B47H CALL 4902H ; Copy filename at (HL) to current BASIC program 3B4AH LXI B,0002H ; Prepare to copy 2 extension bytes to current BASIC program space 3B4DH LXI H,FCEFH ; Point to disk file extension in TX buffer 3B50H LXI D,FC99H ; Point to current BASIC program extension address 3B53H CALL 4A05H ; Move BC bytes from M to (DE) with increment 3B56H CALL 4A51H ; Get RAM directory address of current BASIC program 3B59H JZ 3B69H ; Branch to load if file doesn't already exist 3B5CH LXI H,3FB0H ; Point to "File Exists, Replace?" text 3B5FH CALL 48F4H ; Print string at HL to col 1 on the bottom line 3B62H CALL 3DEEH ; Get key from keyboard and test for 'Y' or 'y' 3B65H RNZ ; Return if isn't 'y' or 'Y' 3B66H CALL 3C38H ; Kill file in current BASIC program space 3B69H LHLD FD1DH ; Get file size from RX buffer 3B6CH MOV A,H ; Swap bytes (big endian in RX buffer) 3B6DH MOV H,L ; Move LSB to MSB 3B6EH MOV L,A ; Move MSB to LSB 3B6FH SHLD FD1DH ; Save with little endian to RX buffer 3B72H LDA FCEFH ; Get 1st byte of extension from TX buffer 3B75H CPI 44H ; Test if 1st extension byte is "D" 3B77H JNZ 3B82H ; Jump if not "D" to check for "C" or "B" 3B7AH LHLD FBAEH ; Get start of DO files pointer for location of new file 3B7DH MVI A,C0H ; Load file type code for .DO files 3B7FH JMP 3BA3H ; Process the file load ; ========================================================================================= ; Test file exension type in A for .CO files ; ========================================================================================= 3B82H CPI 43H ; Test if A contains "C" 3B84H JNZ 3B95H ; Branch if not .CO file 3B87H LHLD FBB0H ; Start of CO files pointer 3B8AH SHLD FCD5H ; Save in currently selected file index storage area 3B8DH LHLD FBB2H ; Get Start of variable data pointer as location for new file 3B90H MVI A,A0H ; Load file type code for .CO files 3B92H JMP 3BA3H ; Process the file load ; ========================================================================================= ; Process load of .BA file ; ========================================================================================= 3B95H LHLD FD1DH ; Get file size from RX buffer 3B98H SHLD FCD5H ; Save in Currently selected file index storage 3B9BH LHLD F99AH ; Get BASIC program not saved pointer 3B9EH SHLD FCE0H ; Save as address of file being processed 3BA1H MVI A,80H ; Load file type code for .BA files ; ========================================================================================= ; Process file load operation ; ========================================================================================= 3BA3H STA FCDFH ; Save file type code for later 3BA6H SHLD FCE2H ; Save address for new file 3BA9H LHLD FD1DH ; Get file size from RX buffer 3BACH SHLD FCDDH ; Save in FDC emulation physical/logical sector storage area 3BAFH PUSH H ; Save file size on stack 3BB0H POP B ; Copy file size to BC 3BB1H LDA FCDFH ; Get file type code 3BB4H CPI A0H ; Test for .CO file 3BB6H JZ 3BC0H ; Skip increment if .CO file (.BA has trailing 0x0000, .DO a 0x1A) 3BB9H INX B ; Increment file length for .BA and .DO files 3BBAH CPI 80H ; Test if file is .BA 3BBCH JNZ 3BC0H ; Skip additional increment if .BA 3BBFH INX B ; Add 1 more to length for .BA files to account for both trailing 0's 3BC0H PUSH B ; Save updated length on stack 3BC1H CALL 3E48H ; Find empty catalog entry 3BC4H JC 4887H ; Generate system error 0x0A ("DD") if full 3BC7H POP B ; Get length from stack 3BC8H PUSH H ; Save new file catalog address on stack 3BC9H PUSH B ; Save new file length on stack 3BCAH LHLD FCE2H ; Get address for new contents of new file 3BCDH CALL 4C0BH ; Insert BC spaces at M - make room 3BD0H JC 488AH ; Branch if error - RAM full error 3BD3H LHLD FCE2H ; Restore address of new file contents 3BD6H POP B ; Get file length from stack 3BD7H MVI M,00H ; Fill newly created file space with zero's 3BD9H INX H ; Increment pointer 3BDAH DCX B ; Decrement count 3BDBH MOV A,C ; Move LSB to A to check for zero - could use JNX here! 3BDCH ORA B ; Or in MSB to check for zero 3BDDH JNZ 3BD7H ; Keep looping until all are zero 3BE0H DCX H ; Decrement pointer to last byte in new file 3BE1H POP D ; Get File catalog address from stack 3BE2H LDA FCDFH ; Load file type code byte 3BE5H CPI C0H ; Test for .DO file 3BE7H JNZ 3BF3H ; Branch if not .DO file 3BEAH MVI M,1AH ; Terminate .DO file with EOF marker 3BECH LHLD FCE2H ; Reload address of new file contents 3BEFH DCX H ; Decrement pointer to jump into middle of loop 3BF0H JMP 3C1BH ; Write file entry to catalog ; ========================================================================================= ; Process end-of-file / file length for .CO and .BA files ; ========================================================================================= 3BF3H CPI A0H ; Test if new file is .CO 3BF5H JNZ 3C04H ; Branch if not .CO - must be .BA 3BF8H LHLD FCD5H ; Get old start of CO files pointer 3BFBH SHLD FBB0H ; Save as current start of CO files pointer 3BFEH LHLD FCE2H ; Reload address of new file contents 3C01H JMP 3C1BH ; Write file entry to catalog ; ========================================================================================= ; Process end-of-file for .BA files ; ========================================================================================= 3C04H PUSH D ; Push file catalog address to stack 3C05H LHLD FBAEH ; Get start of DO files pointer 3C08H DCX H ; Decrement address by 1 3C09H SHLD F99AH ; Save as new BASIC program not saved pointer 3C0CH INX H ; Increment back to start of .DO files 3C0DH XCHG ; HL <--> DE DE has start of DO files 3C0EH LHLD FCD5H ; Get BA file size 3C11H INX H ; Increment file size to account for trailing 0's 3C12H INX H ; Increment file size to account for trailing 0's 3C13H DAD D ; Add new length to start of DO files pointer 3C14H SHLD FBAEH ; Save new start of DO files pointer 3C17H POP D ; Retrieve file catalog address from stack 3C18H LHLD FCE0H ; Reload address of new file contents ; ========================================================================================= ; Write file entry to catalog ; ========================================================================================= 3C1BH XCHG ; HL <--> DE DE has file address, HL has catalog address 3C1CH CALL 4C17H ; Write new entry to catalog (A=type, DE=file address,HL=catalog address) 3C1FH CALL 4127H ; Open TPDD file and read data to file address being processed 3C22H CALL 4C0FH ; Update system pointers 3C25H LXI H,0002H ; Load TPDD_READ opcode in HL 3C28H JMP 409BH ; Send Request in HL and await response ; ========================================================================================= ; F2 Function key handler for RAM mode - Kill ; ========================================================================================= 3C2BH LDA FCCCH ; Get last Tag/Untag operation code 3C2EH ANA A ; Test if there is a pending tag operation 3C2FH CZ 3DE1H ; Display "Sure ?", validate and return if validated if no tag 3C32H LHLD FCE4H ; LCD Buffer address of current file selection 3C35H CALL 4902H ; Copy filename at (HL) to current BASIC program ; ========================================================================================= ; Kill file in current BASIC program space ; ========================================================================================= 3C38H CALL 4A51H ; Get RAM directory address of current BASIC program 3C3BH CPI C0H ; Test if file is .DO 3C3DH JZ 4BFFH ; Kill .DO file 3C40H CPI A0H ; Test if file is .CO 3C42H JZ 4C07H ; Kill .CO file 3C45H CPI 80H ; Test if file is .BA 3C47H JZ 4C03H ; Kill .BA file 3C4AH RET ; ========================================================================================= ; F1 Function key handler for RAM mode - Save ; ========================================================================================= 3C4BH CALL 4A3BH ; Initialize blank filename and attribute byte 3C4EH CALL 4A4BH ; Get RAM directory address of selected file 3C51H PUSH D ; Push file address to stack 3C52H PUSH H ; Push file catalog address to stack 3C53H INX H ; Point to LSB of file address 3C54H INX H ; Point to MSB of file address 3C55H INX H ; Point to filename in catalog 3C56H LXI D,FCE8H ; Point to TX buffer data area (payload) 3C59H LXI B,0006H ; Prepare to copy 6 filename bytes to TX packet data 3C5CH CALL 4A05H ; Move BC bytes from M to (DE) with increment 3C5FH MVI A,2EH ; Load code for '.' 3C61H STAX D ; Store '.' separator in TX packet data 3C62H INX D ; Increment TX packet data pointer 3C63H LXI B,0002H ; Prepare to copy 2 extention bytes from catalog 3C66H CALL 4A05H ; Move BC bytes from M to (DE) with increment 3C69H LDA FCCCH ; Last Tag/Untag operation code 3C6CH ANA A ; Test if a tag save operation is being performed 3C6DH JNZ 3C88H ; Jump ahead if doing a tag save - skip filename questioning 3C70H LXI H,3F71H ; Point to "Save as:" text 3C73H CALL 3E1AH ; Get 6-byte input filename from keyboard 3C76H JZ 3C88H ; Skip ahead to use catalog name if no input given 3C79H CALL 4902H ; Copy filename at (HL) to current BASIC program 3C7CH LXI B,0006H ; Prepare to copy 6 filename bytes from input string 3C7FH LXI D,FCE8H ; Point to filename area in TX buffer 3C82H LXI H,FC93H ; Filename of current BASIC program 3C85H CALL 4A05H ; Move BC bytes from M to (DE) with increment 3C88H POP H ; Restore file catalog address from stack 3C89H POP D ; Restore file address from stack 3C8AH PUSH D ; Save file address on stack 3C8BH CALL 3CD3H ; Calculate length of RAM file, HL=address of catalog entry, DE=file address 3C8EH MOV A,H ; Test for zero length file - move H to A 3C8FH ORA L ; OR LSB to test for zero 3C90H JZ 4884H ; Branch if empty - File Empty Error 3C93H PUSH H ; Save file address to stack 3C94H MVI A,01H ; Set file open mode to new file 3C96H STA FCD6H ; Save open mode to pass to open routine 3C99H CALL 4943H ; Configure baud, test for NADSBox, get NADSBox dir 3C9CH CALL 4A72H ; Send Dir Reference opcode 3C9FH JZ 3CCEH ; Jump to write data if file doesn't exist (size = 0) 3CA2H LXI H,3F8BH ; Point to "File Exists, A)ppend R)eplace Q)uit" text 3CA5H CALL 48F4H ; Print string at HL to col 1 on the bottom line 3CA8H CALL 3DF8H ; Process power-off logic and wait for a key from keyboard 3CABH ANI DFH ; Make key uppercase 3CADH RST 4 ; Display key on LCD 3CAEH CPI 52H ; Test if key is 'R' 3CB0H JNZ 3CBCH ; Jump if not 'R'eplace 3CB3H CALL 431AH ; Issue TPDD Delete file Opcode 3CB6H CALL 4A72H ; Send Dir Reference opcode 3CB9H JMP 3CCEH ; Go write data to the file ; ========================================================================================= ; F1-Save: Test for 'A'ppend ; ========================================================================================= 3CBCH POP H ; Get file length from stack 3CBDH POP D ; Get file address from stack 3CBEH CPI 41H ; Test if response is 'A'ppend 3CC0H RNZ ; Return if not 'A' 3CC1H LDA FCEFH ; Load 1st byte of extension from TX buffer 3CC4H CPI 44H ; Test if file is "D"O file 3CC6H RNZ ; Don't allow appending non DO files 3CC7H MVI A,02H ; Set open mode to open existing (append) 3CC9H STA FCD6H ; Save mode to pass to open routine 3CCCH PUSH D ; Save file address on stack 3CCDH PUSH H ; Save file length on stack ; ========================================================================================= ; Save function - Replace or new file, write data to file ; ========================================================================================= 3CCEH POP H ; Retrieve file length from stack 3CCFH POP D ; Retrieve file address from stack 3CD0H JMP 40C8H ; Write HL bytes of data from (DE) to TPDD ; ========================================================================================= ; Calculate length of RAM file, HL=address of catalog entry, DE=file address ; ========================================================================================= 3CD3H MOV A,M ; Get RAM file type from catalog 3CD4H CPI C0H ; Test for .DO file 3CD6H JZ 3CE6H ; Jump to calculate length if .DO file 3CD9H CPI A0H ; Test for .CO file 3CDBH JZ 3CF5H ; Jump to calculate length if .CO file 3CDEH PUSH D ; Save address of start of BASIC program to stack 3CDFH CALL 4C13H ; Call ROM routine to find BASIC end of program 3CE2H POP B ; Get BASIC program start address from stack 3CE3H DSUB ; Subtract starting address from end address 3CE4H DCX H ; Don't count trailing 0x00 as part of BASIC program length 3CE5H RET ; ========================================================================================= ; Calculate length of .DO file, HL=Catalog address, DE=file address ; ========================================================================================= 3CE6H XCHG ; HL <--> DE Get file address in HL 3CE7H LXI D,0000H ; Clear file length 3CEAH MOV A,M ; Get next byte from .DO file 3CEBH INX H ; Increment pointer 3CECH INX D ; Increment length 3CEDH CPI 1AH ; Test for EOF marker 3CEFH JNZ 3CEAH ; Branch to next byte if not EOF 3CF2H DCX D ; Subtract EOF marker from file length 3CF3H XCHG ; HL <--> DE HL=length 3CF4H RET ; ========================================================================================= ; Calculate length of .CO file, HL=Catalog address, DE=file address ; ========================================================================================= 3CF5H XCHG ; HL <--> DE Get file address in HL 3CF6H INX H ; Increment past .CO load address 3CF7H INX H ; Increment past MSB of load address 3CF8H MOV C,M ; Get LSB of length 3CF9H INX H ; Increment to MSB of length 3CFAH MOV B,M ; Get MSB of length 3CFBH LXI H,0006H ; Prepare to add 6-byte header to length 3CFEH DAD B ; Add 6-byte header to length 3CFFH RET ; ========================================================================================= ; F7 Function key handler for DISK mode - Mkdir ; ========================================================================================= 3D00H LDA FCCBH ; NADSBox / TPDD2 / Desklink flag 3D03H ANA A ; Test if server is TPDD 3D04H RZ ; Return if not NADSBox or TPDD2 3D05H DCR A ; Test if TPDD2 3D06H JZ 37BAH ; Go Swap TPDD Bank Number if TPDD2 3D09H CALL 4A3BH ; Must be NADSBOx Initialize blank filename 3D0CH LXI H,3F61H ; Load pointer to "Directory name:" text 3D0FH CALL 3E1AH ; Get 6-byte input filename from keyboard 3D12H RZ ; Return if no input given 3D13H CALL 4902H ; Copy filename at (HL) to current BASIC program 3D16H LXI H,FC93H ; Filename of current BASIC program 3D19H LXI D,FCE8H ; Point to TX buffer data area (payload) 3D1CH LXI B,0006H ; Prepare to copy 6 filename bytes to TX buffer 3D1FH CALL 4A05H ; Move BC bytes from M to (DE) with increment 3D22H LXI H,3E3CH ; Load code for "<>" 3D25H SHLD FCEFH ; Save "<>" extension bytes in TX buffer - NADSBox Mkdir 3D28H MVI A,2EH ; Load code for '.' extension separator 3D2AH STA FCEEH ; Save "." to TX buffer 3D2DH CALL 4943H ; Configure baud, test for NADSBox, get NADSBox dir 3D30H LDA FCCBH ; NADSBox / Desklink / TPDD2 flag 3D33H CPI 02H ; Test if we have NADSBox current directory 3D35H RNZ ; Return if we don't have current directory 3D36H CALL 4A72H ; Send Directory Reference opcode 3D39H JNZ 3D4DH ; If the file exists, branch to open it for READ mode 3D3CH MVI A,01H ; Load OPEN_WRITE mode into A to create the directory 3D3EH STA FCE8H ; Save A in TX data storage mode field 3D41H LXI H,0101H ; Load opcode to open a file 3D44H CALL 409BH ; Send Request in HL and await response 3D47H LXI H,0002H ; Load opcode to close the file 3D4AH JMP 409BH ; Send Request in HL and await response ; ========================================================================================= ; Open and close a directory file (from above) ; ========================================================================================= 3D4DH CALL 408AH ; Open TPDD file for Read Mode 3D50H JMP 3D47H ; Branch to close the directory open request ; ========================================================================================= ; F5 Function key handler for DISK mode - Format ; ========================================================================================= 3D53H LDA FCCBH ; NADSBox / Desklink / TPDD2 flag 3D56H CPI 02H ; Test if we have "current directory" name 3D58H RZ ; Return if server is NADSBox / Desklink - No format supported 3D59H LXI H,3F1BH ; Load pointer to "Insert Disk" string 3D5CH CALL 48F4H ; Print string at HL to col 1 on the bottom line 3D5FH CALL 3DEEH ; Get key from keyboard and test for 'Y' or 'y' 3D62H RNZ ; Return if response not 'Y' 3D63H CALL 4943H ; Configure baud, test for NADSBox, get NADSBox dir 3D66H CALL 49E3H ; Delay routine - about 3ms 3D69H LXI H,0006H ; Load TPDD_FORMAT opcode in HL 3D6CH CALL 409BH ; Send Request in HL and await response 3D6FH MVI A,07H ; Load code for BELL 3D72H RET ; Go beep to indicate format ; ========================================================================================= ; F2 Function key handler for DISK mode - Kill ; ========================================================================================= 3D73H LDA FCCCH ; Last Tag/Untag operation code 3D76H ANA A ; Test if there's an active tag group 3D77H CZ 3DE1H ; Display "Sure ?", validate and return if validated if no tag 3D7AH CALL 4A3BH ; Initialize blank filename and attribute byte 3D7DH CALL 3D83H ; Copy selected filename to TX buffer and init TPDD/NADSBox 3D80H JMP 431AH ; Issue TPDD Delete file Opcode ; ========================================================================================= ; Copy selected filename to TX buffer and init TPDD/NADSBox ; ========================================================================================= 3D83H LXI B,0009H ; Prepare to copy 9 filename bytes 3D86H LHLD FCE4H ; LCD Buffer address of current file selection 3D89H LXI D,FCE8H ; Address of TX packet data 3D8CH CALL 4A05H ; Move BC bytes from M to (DE) with increment 3D8FH CALL 4943H ; Configure baud, test for NADSBox, get NADSBox dir 3D92H JMP 4A72H ; Send Dir Reference opcode ; ========================================================================================= ; Copy filename at (HL) to TX buffer ; ========================================================================================= 3D95H CALL 4902H ; Copy filename at (HL) to current BASIC program 3D98H LXI H,FC93H ; Filename of current BASIC program 3D9BH CALL 4A57H ; Send Dir Reference for filename at (HL) 3D9EH RET ; ========================================================================================= ; F3 Function key handler for DISK mode - Name ; ========================================================================================= 3D9FH CALL 4A3BH ; Initialize blank filename and attribute byte 3DA2H CALL 3D83H ; Copy selected filename to TX buffer and init TPDD/NADSBox 3DA5H LXI H,FCE8H ; Point to TX buffer data area (payload) 3DA8H LXI D,FC9CH ; Filename of last program loaded from tape 3DABH LXI B,0009H ; Prepare to copy 9 bytes to "last program loaded" filename 3DAEH CALL 4A05H ; Move BC bytes from M to (DE) with increment 3DB1H LHLD FD1DH ; Get file size from RX buffer 3DB4H MOV C,H ; Save file size MSB to C (swap endian) 3DB5H MOV B,L ; Save file size LSB to B (swap endian) 3DB6H LXI H,7CC0H ; ? Load HL with 31936 3DB9H DSUB ; ? Compare file length with 31936 3DBAH LXI H,3F4AH ; Address of "New name" string 3DBDH JNZ 3DD7H ; Branch to change filename if not 30656 3DC0H LXI B,0009H ; Allow a 9-byte filename input string 3DC3H CALL 3E1DH ; Get max BC length input for filename and convert to uppercase 3DC6H RZ ; Return if no input provided 3DC7H PUSH H ; Save pointer to input string to stack 3DC8H PUSH PSW ; Save string length to stack 3DC9H CALL 4A3BH ; Initialize blank filename and attribute byte 3DCCH POP PSW ; Get string length from stack 3DCDH POP H ; Get string address from stack 3DCEH LXI D,FCE8H ; Point to TX buffer data area (payload) 3DD1H MOV C,A ; Copy length to BC 3DD2H MVI B,00H ; Make MSB of length = 0 3DD4H JMP 41B0H ; Rename the TPDD file whose name is in (HL) ; ========================================================================================= ; Get filename from keyboard and rename Disk file, filename in "current BASIC program" ; ========================================================================================= 3DD7H CALL 3E1AH ; Get 6-byte input filename from keyboard 3DDAH RZ ; Return if no input provided 3DDBH CALL 4902H ; Copy filename at (HL) to current BASIC program 3DDEH JMP 41A7H ; Rename the TPDD file whose name is in "current BASIC program" ; ========================================================================================= ; Display "Sure ?", validate and return if validated ; ========================================================================================= 3DE1H LXI H,3F83H ; Load pointer to "Sure ?" string 3DE4H CALL 48F4H ; Print string at HL to col 1 on the bottom line 3DE7H CALL 3DEEH ; Get key and test for 'Y' or 'y' 3DEAH JNZ 48B5H ; Branch to "Long jump" operation to abort if not 'y' 3DEDH RET ; ========================================================================================= ; Get key from keyboard and test for 'Y' or 'y' ; ========================================================================================= 3DEEH CALL 3DF8H ; Process power-off logic and wait for a key from keyboard 3DF1H RST 4 ; Display the key on the LCD 3DF2H CPI 59H ; Test if key pressed was 'Y' 3DF4H RZ ; Return if key pressed was 'Y' 3DF5H CPI 79H ; Test if key pressed was 'y' 3DF7H RET ; ========================================================================================= ; Process power-off logic and wait for a key from keyboard ; ========================================================================================= 3DF8H CALL 3DFEH ; Process automatic poweroff logic 3DFBH JMP 4BEBH ; Wait for key from keyboard ; ========================================================================================= ; Process automatic power-off logic during key scan loop ; ========================================================================================= 3DFEH XRA A ; Clear A 3DFFH DCR A ; Set A to 0xFF 3E00H STA F656H ; Power off exit condition switch 3E03H CALL 4C4AH ; Check keyboard queue for pending characters 3E06H JZ 3DFEH ; Branch back if no keyboard characters in queue - wait for key 3E09H XRA A ; Clear A 3E0AH STA F656H ; Power off exit condition switch 3E0DH LXI H,F932H ; Load address of "Renew Automatic Poweroff Counter Flag" 3E10H ORA M ; Test if auto poweroff counter should be renewed 3E11H JZ 4BF7H ; Renew automatic power-off counter if enabled 3E14H CALL 4BF3H ; Turn off the computer 3E17H JMP 3DFEH ; Branch back to continue processing power off logic ; ========================================================================================= ; Get max 6-byte input for filename and convert to uppercase ; ========================================================================================= 3E1AH LXI B,0006H ; Get maximum 6 characters of input ; ========================================================================================= ; Get max BC length input for filename and convert to uppercase ; ========================================================================================= 3E1DH CALL 3E2FH ; Get max BC length input string from keyboard 3E20H RZ ; Return if no input provided 3E21H PUSH H ; Preserve pointer to input string 3E22H PUSH PSW ; Preserve flags from input 3E23H CALL 4C5EH ; Get char at M and convert to uppercase 3E26H MOV M,A ; Save uppercase char back to string 3E27H INX H ; Point to next byte in input 3E28H ANA A ; Test for NULL - end of string 3E29H JNZ 3E23H ; Keep looping until end of string 3E2CH POP PSW ; Restore flags from input routine 3E2DH POP H ; Restore pointer to input string 3E2EH RET ; ========================================================================================= ; Get maximum BC length input character string from keyboard ; ========================================================================================= 3E2FH PUSH B ; Save maximum input length to stack 3E30H CALL 48F4H ; Print string at HL to col 1 on the bottom line 3E33H CALL 4C46H ; Input and display (no "?") line and store 3E36H JC 48B5H ; Branch to "Long jump" if CTRL-C 3E39H INX H ; Point to start of input string 3E3AH MOV A,B ; Get string length (counting NULL) 3E3BH DCR A ; Remove NULL from count 3E3CH POP D ; Restore maximum input length 3E3DH RZ ; Return if string length is zero 3E3EH CMP E ; Compare expected length with actual length 3E3FH RC ; Return if string is shorter than expected 3E40H PUSH H ; Save pointer to start of string on stack 3E41H DAD D ; Add Expected length to pointer 3E42H MVI M,00H ; Truncate the string to the max length 3E44H POP H ; Restore pointer to input string 3E45H MOV A,E ; Update length to reflect maximum 3E46H ORA A ; Clear zero flag to indicate input provided 3E47H RET ; ========================================================================================= ; Find Empty catalog entry (only 9 instructions...Don't bother with Main ROM) ; ========================================================================================= 3E48H LXI H,F9AFH ; Point to the "RickY" catalog entry (start of valid entries) 3E4BH LXI B,000BH ; Load length of each catalog entry 3E4EH DAD B ; Point to next catalog entry to test if empty 3E4FH MOV A,M ; Get file attribute byte from catalog entry 3E50H CPI FFH ; Test if at end of catalog 3E52H JZ 3E5AH ; Jump to report directory full if at end 3E55H ADD A ; Test if MSB is set (entry being used) 3E56H JC 3E4EH ; Jump to test next enry if MSB set 3E59H RET ; Entry found...return with Carry clear ; ========================================================================================= ; Empty catalog entry not found...set Carry and exit ; ========================================================================================= 3E5AH STC ; Indicate empty entry not found 3E5BH RET ; ========================================================================================= ; F5 Function key handler for RAM mode - DOS ON/OF ; ========================================================================================= 3E5CH LHLD FB2CH ; Get LFILES statement hook address 3E5FH LXI B,08DBH ; Load address of default (DOS-OFF) hook for LFILES 3E62H DSUB ; Test if in DOS-OFF mode 3E63H JZ 401FH ; Jump to add our custom RST 7 hooks if in DOS-OFF mode 3E66H JMP 3FFAH ; Must be in DOS-ON mode, jump to turn it off ; ========================================================================================= ; Strings ; ========================================================================================= 3E69H DB 0x1B, "p TS-DOS (100 v4.00) (c)87,TSI. ",0x1B,'q',0x00 3E97H DB "DISK Free: File:",0DH,0AH,"Load Kill Name Ram Frmt Log Menu",00H 3ED9H DB " RAM Free: File:",0DH,0AH,"Save Kill Name Disk DOS- Menu",00H 3F1BH DB "Insert Disk, Press \"Y\" to begin ",00H 3F3CH DB "NOT FORMATTED",00H 3F4AH DB "New Name:",00H 3F54H DB "System name:",00H 3F61H DB "Directory name:",00H 3F71H DB "Save as:",00H 3F7AH DB "Load as:",00H 3F83H DB "Sure ? ",00H 3F8BH DB "File exists, A)ppend R)eplace Q)uit:",00H 3FB0H DB "File exists, Replace? (Y/N):",00H 3FCDH DB "-.- ",00H 3FD8H DB 0x1B,"Y74 ",1BH,"Y7>MkDr",00H ; TODO: Check this 3FE9H DB 0x1B,"Y7>Bank",00H ; TODO: Check this 3FF2H DB "OFF",00H 3FF6H DB "ON ",00H
Navigate to: