TRS-80 DOS - NEWDOS/80 v2.0 for the Model I - SUPERZAP/CMD Disassembled

Page Customization

SUPERZAP/CMD/CMD - NEWDOS/80 v2.0 Disk Modifier Utility

SUPERZAP is a powerful disk utility program for NEWDOS/80 v2.0 on the TRS-80 Model I. Created by APPARAT, it provides low-level disk access capabilities for viewing, editing, and manipulating disk sectors directly. SUPERZAP is an essential tool for disk recovery, system maintenance, and understanding disk structure.

Primary Functions:

  • 'DD - Disk Dump to Disk: Copy entire disks sector by sector
  • 'DM - Dump Memory: Display memory contents in hex and ASCII format
  • 'DFS - Disk File Sector: Display sectors belonging to a specific file
  • 'DTS - Disk Track Sector: Display sectors by track and sector number
  • 'DMDB - Dump Memory Data Block: View memory in block format
  • 'VDS - Verify Disk Sector: Verify disk sector integrity
  • 'ZDS - Zap Disk Sector: Write/modify disk sectors directly
  • 'CDS - Copy Disk Sector: Copy sectors between locations
  • 'CDD - Copy Disk to Disk: Full disk copy operation
  • 'DPWE - Disk Password Write Enable: Enable write access with password
  • 'DNTH - Disk N-th Sector: Display the N-th absolute sector

Key Features:

  • Compressed String System: Messages are stored using a sophisticated compression scheme where common words (AT, BE, DO, IF, IS, OF, OK, OR, TO, ALL, AND, BAD, END, EOF, FEW, FOR, MAY, NOT, OUT, THE, TOO, YOU, etc.) are replaced with single-byte codes (80H-FFH). This saves significant memory while providing extensive user messages.
  • Multi-Mode Display: Supports different display modes (DFS, DTS, DD) with appropriate status labels (DRV, TRK, TRS, DRS, FRS).
  • Comprehensive Error Handling: Robust error detection with retry/skip/exit options for disk errors.
  • Input Validation: Thorough validation of all user input including drive numbers, track numbers, sector numbers, addresses, and hex values.
  • Mathematical Routines: Built-in 8×8, 8×16 multiply and 16÷8 divide routines for address calculations.
  • Flexible Number Parsing: Accepts both decimal and hexadecimal input with automatic detection.

Memory Layout:

SUPERZAP loads at 5400H and extends through 6FFFH. The program entry point is at 54C5H. The code is organized into several major sections:

  • 5400H-54FFH: FCB area, variables, and working storage
  • 54C5H-6689H: Main program code (initialization, menu, commands)
  • 668AH-68F6H: Utility routines (memory copy, comparisons, validation, math)
  • 68FEH-6BECH: Status labels, menu data, and compressed word tables
  • 6BEDH-6EFFH: Error message table and compressed message strings
  • 6F00H-6FFDH: Work buffer (254 bytes of zeros)

Variable and Memory Map

AddressBytesPurpose
5400H-5405H6FCB (File Control Block) area - start of file control structure
5406H1FCB drive byte - contains current drive number (0-3)
5487H-548BH5Decimal conversion buffer - 5-digit ASCII output for number display
5491H1Primary mode flags - controls display and operation modes
5492H1Secondary mode flags - additional state information
5493H1Tertiary mode flags - bit 6: special mode, bit 1: alternate handling
5494H1Error code storage - holds current error code for display
5499H1Working drive variable - current drive being accessed
549BH1Tracks per disk - total track count for current drive
549CH1Tracks per disk (copy) - duplicate for calculations
549EH1Sector within track - relative sector number (1-based)
54A0H1Current track number - track being accessed
54A2H2Current absolute sector number - 16-bit sector address
54A8H2Maximum sector count - total sectors on disk (tracks × sectors/track)
54ACH2Address value variable - 16-bit address for memory operations
54AEH1Granule number variable - current granule for file operations
54C5H-Program entry point / abort handler address
6F00H-6FFDH254Work buffer - temporary storage for disk and memory operations
430DH1DOS workspace - sectors per track (typically 10)
430EH1DOS workspace - tracks per disk
430FH1DOS workspace - tracks (alternate location)

Subroutine Reference:

AddressPurpose
445EHNEWDOS/80 PDRIVE lookup - select drive and retrieve parameters
4409HDOS error handler - display error message via SVC
6245HDisplay compressed string with newline
6248HDisplay newline only
6255HDisplay compressed string (no newline)
62BAHDisplay B bytes from buffer at HL
6345HDisplay prompt (alternate entry)
634EHDisplay prompt and collect user input
6578HDisk error handler
6598HSpecial exit - empty input (returns with carry and Z set)
65A0HSyntax error handler
65A5HSpecial exit - comma handling
668AHBlock memory copy - copy B bytes from HL to DE
6691H16-bit equality comparison - compare HL vs DE
6697HRange check - check if HL is within BC:DE range
66A2HRange check - check if BC is within DE range
66ADH16-bit equality comparison - compare BC vs DE
66B3HMemory block comparison - compare B bytes at DE vs HL
66BBHUppercase letter check - test if A contains A-Z
66CBHHex digit validation - test if A contains A-F
66D5HDecimal digit check - test if A contains 0-9
66DCHPrompt for TO address
66E1HPrompt for FROM address
66EFHPrompt for granule number
670FHParse/validate drive number (0-3)
6732HParse/validate sector-within-track
6751HParse/validate track number
6770HParse hex value with error check
677BHParse/store 16-bit address at 54ACH
678FHPrompt for disk parameters
67B5HSelect drive and get disk parameters
67E5HParse hex value with terminator validation
67EDHParse hex input with special character handling
6822HParse decimal number into DE
684FHParse hexadecimal number into DE
686DHConvert ASCII character to hex digit value (0-15)
687BH8×8-bit multiply entry (sets H=0)
687DH8×16-bit multiply - HL = HL × A
6896H16÷8-bit divide - HL = HL ÷ A, remainder in A
68A6HConvert 8-bit value to decimal string
68ABHConvert 16-bit value from memory to decimal
68C5HConvert and display 16-bit value
68D1HCore decimal conversion - DE to 5-digit ASCII at 5487H

Compressed String Tables:

SUPERZAP uses a dual-table compression system to reduce memory usage for displayed messages:

Table 1: Short Words (Codes 80H-9FH) at 69BDH

CodeWordCodeWordCodeWord
80H(space)8BHOR96HNOT
81H-8CHTO97HYOU
82HAT8DHTO?98HMAY
83HBE8EH-99HBAD
84HDO8FHOR9AH-
85H-90HAND9BHEND
86HDO91HNOT9CHEOF
87HIF92HTHE9DHFEW
88HIS93HALL9EH-
89HOK94HFOR9FH-
8AHOF95HTOO

Table 2: Long Words (Codes A0H-FFH) at 69F6H

CodeWordCodeWordCodeWord
A0H(space)B8HREADD0HRECORD
A1HBASEB9HSEEKD1HRETURN
A2HBASEBAHSKIPD2HRETURN
A3HBYTEBBHWRITED3H-
A4HCODEBCHDEVICED4H-
A5HCOPYBDHPROTECTD5H-
A6HDATABEHSECTORD6H-
A7HDUMPBFHZEROD7HWITHIN
A8HDISKC0H-D8HSYSTEM
A9HEXITC1HVERIFYD9HDISKETTE
AAH-C2HVERIFYDAHINVALID
ABH-C3HCONTAINDBHDESTINATION
ACH-C4HILLEGALDCH-
ADH-C5HMEMORYDDHDESTINATION
AEHINPUTC6HMEMORYDEH-
AFHPAUSEC7H-DFH-
B0HBEYONDC8HOFFSET......
B1HEXTRAC9H-
B2HFOUNDCAH-
B3HSOURCECBHPARITY
B4H-CCH-
B5HSOURCECDH-
B6HBUFFERCEHPARITY
B7HBUFFERCFHOFFSET

Note: Words are terminated with the high bit (bit 7) set on the final character.

String Table Addresses:

AddressString/Message
6D50H"DRIVE,SECTOR?" prompt
6D6DH"TO?" prompt
6D71H"FR?" (FROM?) prompt
6D75H"GR?" (Granule?) prompt
6DEBH"INVALID DRIVE" error
6DEFH"INVALID SECTOR" error
6DF3H"INVALID TRACK" error
6DF7H"INVALID SECTOR" (absolute) error
6DFCH"INVALID ADDRESS" error
6DFFHGeneral input error
6E04HValue out of range error
6E38H"ERROR CODE" prefix
6E3FH"PREVIOUSLY SUCCESSFULLY" message
6E59H"INTERNAL PROGRAMMING ERROR"
6E71H"'R'ETRY, 'S'KIP, E'X'IT" prompt
6EBCH"SHALL I WRITE?" confirmation
6ECBH"PARTIAL DATA DUE" message
6EDBH"NO MATCH" search result
6EE6H"UNDER DOS-CALL" message

Powers of 10 Table:

Located at 68F6H, this table contains negated powers of 10 used by the decimal conversion routine (68D1H):

AddressValue (Hex)Value (Decimal)Purpose
68F6HD8F0H-10000Ten-thousands place
68F8HFC18H-1000Thousands place
68FAHFF9CH-100Hundreds place
68FCHFFF6H-10Tens place

The units place (1) is handled separately by directly adding 30H to the remainder.

Disassembly:

5200H - Conditional Copy of Relative Sector to Current Display Position

This routine checks bit 3 of the mode flags at 5491H (the "memory mode" flag indicating whether we're working with memory rather than disk). If bit 3 is set, the routine exits early without doing anything. Otherwise, it copies the relative sector value from 54B4H to the current display position variable at 5495H. This allows SUPERZAP to track which relative sector is currently being displayed.

5200
LD A,(5491H) 3A 91 54
Load Register A with the mode flags byte from address 5491H. This byte contains various operational mode bits: bit 1 = file mode, bit 3 = memory mode, bit 4 = jump pending, bit 5 = alternate display, bit 6 = file open.
5203
BIT 3,A CB 5F
Test bit 3 of Register A (the memory mode flag). If bit 3 is set (1), the Z flag is cleared (NZ condition); if bit 3 is clear (0), the Z flag is set (Z condition). Bit 3 indicates we are in memory zap mode rather than disk sector mode.
5205
RET NZ C0
If the NZ flag is set (meaning bit 3 was 1, indicating memory mode), return immediately from this subroutine. In memory mode, there is no concept of "relative sector" so we skip this operation.
5206
LD HL,(54B4H) 2A B4 54
Load Register pair HL with the 16-bit relative sector number from addresses 54B4H-54B5H. This is the sector offset within the current file or disk being examined.
5209
LD (5495H),HL 22 95 54
Store the relative sector number from HL into the current display position variable at 5495H-5496H. This records which relative sector is currently being shown on screen.
520C
RET C9
Return from subroutine.

520DH - Initialize HL and C from E, Store to 54C3H

This short routine sets Register L, Register H, and Register C all to the value in Register E, then stores HL to address 54C3H. This appears to be used for initializing position or offset values. The address 54C3H holds a 16-bit position value used in various SUPERZAP operations.

520D
LD L,E 6B
Copy Register E into Register L. Register E contains the initialization value passed by the caller.
520E
LD H,E 63
Copy Register E into Register H. Now HL contains E in both bytes (forming E*256+E if E≠0, or 0000H if E=0).
520F
LD C,E 4B
Copy Register E into Register C. This sets C to the same initialization value.
5210
LD (54C3H),HL 22 C3 54
Store Register pair HL into the position/offset variable at addresses 54C3H-54C4H. This variable is used by SUPERZAP to track various position states.
5213
RET C9
Return from subroutine.

5214H - Load H from 54B3H and Store HL to 54C3H

This routine loads a byte from 54B3H into Register H (the high byte of the track/sector indicator), then jumps to 5210H to store HL into 54C3H. This is used to set up position tracking with a specific high byte value.

5214
LD A,(54B3H) 3A B3 54
Load Register A with the byte stored at address 54B3H. This location holds the high byte of the relative sector or a track indicator value.
5217
LD H,A 67
Copy Register A into Register H. This sets the high byte of HL to the value just loaded.
5218
Jump relative backward to 5210H to store HL into 54C3H and return. The L register retains whatever value it had on entry.

521AH - Reserved Space (NOP Padding)

This area from 521AH to 52FFH contains NOP instructions (00H bytes). This is reserved space, possibly for future expansion or patch area. The NOPs serve no functional purpose in normal execution.

521A-52FF
NOP (repeated) 00
No operation. This block of 230 bytes (521AH through 52FFH) is filled with NOPs, serving as reserved/unused space within SUPERZAP.

54C5H - SUPERZAP Main Entry Point and Initialization

This is the main entry point for SUPERZAP (as indicated by "PROGRAM ENTRY = 54C5H" in the disassembly). This routine initializes the stack pointer, clears mode flags, sets up buffer pointers, copies default values from ROM to RAM, and then proceeds to display the main menu and parse command line arguments. The initialization sets up the operating environment for all SUPERZAP functions.

54C5
LD SP,5300H 31 00 53
Initialize the Stack Pointer to 5300H. This establishes the stack area just below the sector buffer at 5300H, growing downward toward lower addresses.
54C8
XOR A AF
Clear Register A to zero by XORing it with itself. Also clears the carry flag.
54C9
LD (5493H),A 32 93 54
Store zero into the secondary mode flags at address 5493H. This clears all secondary mode bits (bit 4 = sector changed, bit 5 = alternate mode, bit 7 = reverse direction).
54CC
LD HL,5300H 21 00 53
Load Register pair HL with 5300H, the address of the sector data buffer.
54CF
LD (5423H),HL 22 23 54
Store 5300H into the buffer pointer at 5423H-5424H. This sets up the pointer to the sector buffer used for disk read/write operations.
54D2
LD (5495H),HL 22 95 54
Store 5300H into the display position variable at 5495H-5496H. This initializes the current display position.
54D5
LD HL,5420H 21 20 54
Load Register pair HL with 5420H, the address of the default initialization data stored in ROM/initial data area.
54D8
LD DE,5400H 11 00 54
Load Register pair DE with 5400H, the address of the working variable area where the defaults will be copied.
54DB
LD BC,0020H 01 20 00
Load Register pair BC with 0020H (32 decimal), the number of bytes to copy from the default area to the working area.
54DE
LDIR ED B0
Block copy 32 bytes from address 5420H (pointed to by HL) to address 5400H (pointed to by DE). HL and DE are incremented, BC is decremented until BC=0. This initializes the working variables with default values.

Initialization complete. Now display the main menu banner and process command line.

54E0
Load Register pair HL with 6C30H, the address of the SUPERZAP banner/menu text string to be displayed.
54E3
Call the display string with prompt routine at 634EH. This displays the SUPERZAP menu/banner and waits for user input, returning the command line pointer in HL and Z flag set if only ENTER was pressed.
54E6
LD DE,690FH 11 0F 69
Load Register pair DE with 690FH, the address of the command keyword table. This table contains the valid SUPERZAP command names and their associated flags/addresses.
54E9
If the Z flag is set (user pressed only ENTER with no command), jump forward to 550BH to handle the empty command case (likely re-display menu or default action).

[LOOP START] - Command parsing loop. Search the keyword table for a matching command.

54EB
DEC DE 1B
Decrement DE by 1 to adjust the table pointer position.
54EC
DEC DE 1B
Decrement DE again. The table pointer is now positioned for the search loop.
54ED
PUSH HL E5
Save the current command line pointer (HL) onto the stack for later restoration if this keyword doesn't match.
54EE
DEC HL 2B
Decrement HL to prepare for the comparison loop that follows.
54EF
DEC DE 1B
Decrement DE to move backward in the keyword table.
54F0
INC DE 13
Increment DE to advance to the next character in the keyword.
54F1
INC HL 23
Increment HL to advance to the next character in the user's input.
54F2
LD A,(DE) 1A
Load Register A with the current character from the keyword table (pointed to by DE).
54F3
CP (HL) BE
Compare Register A with the character from the user's command line (pointed to by HL). If they match, Z flag is set.
54F4
If the characters match (Z flag set), jump back to 54F0H to compare the next character pair. [LOOP]
54F6
BIT 7,A CB 7F
Test bit 7 of Register A. In the keyword table, bit 7 being set indicates the end of the keyword (last character has high bit set).
54F8
If bit 7 was set (NZ), we've reached the end of a keyword and the match was successful. Jump to 550BH to process the matched command.

Keyword didn't match - skip to the next keyword in the table.

54FA
INC DE 13
Increment DE to scan forward in the keyword table.
54FB
LD A,(DE) 1A
Load the next byte from the keyword table.
54FC
BIT 7,A CB 7F
Test bit 7 to check if this is the last character of the current keyword.
54FE
If bit 7 is clear (Z), we haven't reached the end of this keyword yet. Loop back to continue scanning. [LOOP]
5500
INC DE 13
Increment DE past the keyword's terminator.
5501
INC DE 13
Skip past the first byte of the keyword's data (flags byte).
5502
INC DE 13
Skip past the second byte of the keyword's data (address low).
5503
INC DE 13
Skip past the third byte of the keyword's data (address high). DE now points to the next keyword.
5504
POP HL E1
Restore the original command line pointer from the stack.
5505
LD A,(DE) 1A
Load the first byte of the next keyword entry.
5506
OR A B7
Test if Register A is zero (OR A sets Z flag if A=0). A zero byte marks the end of the keyword table.
5507
If not zero (more keywords remain), jump back to 54EDH to try matching the next keyword. [LOOP]
5509
No keyword matched and we've reached the end of the table. Jump back to 54C5H to reinitialize and redisplay the menu.

550BH - Process Matched Command or Handle Options

This routine is called when a command keyword has been matched (or when handling the command line after the keyword). It checks for the ",P" option (printer mode), validates command flags, and ultimately dispatches to the appropriate command handler. The routine reads the command flags byte and the handler address from the keyword table entry.

550B
LD B,00H 06 00
Clear Register B to zero. This initializes the command modifier flags (bit 1 will be set if ",P" option is found).
550D
LD A,(HL) 7E
Load Register A with the current character from the command line (pointed to by HL).
550E
CP 2CH FE 2C
Compare Register A with 2CH (ASCII comma ,). Check if the user specified an option.
5510
If not a comma, jump to 5521H to check for end of line and proceed with command execution.
5512
INC HL 23
Increment HL to point past the comma to the option character.
5513
LD A,(HL) 7E
Load the option character into Register A.
5514
CP 50H FE 50
Compare with 50H (ASCII P). Check if this is the ",P" (printer) option.
5516
INC HL 23
Increment HL to point past the option character.
5517
If not P, this is an unrecognized option. Jump to 5500H to skip to the next keyword (treating this as a non-match).
5519
LD A,(DE) 1A
Load the command flags byte from the keyword table entry (pointed to by DE).
551A
BIT 0,A CB 47
Test bit 0 of the flags byte. Bit 0 indicates whether this command supports the printer option.
551C
If bit 0 is clear (Z), the command doesn't support printer mode. Jump to the error handler at 65B9H to display an error message.
551F
LD B,02H 06 02
Set Register B to 02H. This sets bit 1 in B, indicating the printer option was specified.
5521
LD A,(HL) 7E
Load the current command line character into Register A.
5522
CP 0DH FE 0D
Compare with 0DH (ASCII carriage return). Check if we've reached the end of the command line.
5524
If not at end of line, there's extra text after the command. Jump to 5500H to try the next keyword match.

Command matched and validated. Now extract and process the command entry from the keyword table.

5526
EX DE,HL EB
Exchange DE and HL. Now HL points to the keyword table entry and DE points to the command line.
5527
LD A,(HL) 7E
Load the command flags byte from the keyword table entry into Register A.
5528
AND 7FHAND 01111111 E6 7F
Mask off bit 7 (the high-bit marker) keeping only the flag bits 0-6.
552A
OR B B0
OR in the modifier flags from Register B (bit 1 = printer option). This combines the command flags with any user-specified options.
552B
LD (5491H),A 32 91 54
Store the combined flags into the mode flags variable at 5491H. This configures the operation mode for the command.
552E
INC HL 23
Increment HL to point to the next byte in the keyword table entry (secondary flags).
552F
LD A,(HL) 7E
Load the secondary flags byte from the keyword table entry.
5530
LD (5492H),A 32 92 54
Store the secondary flags into address 5492H. These control additional command behavior.
5533
BIT 3,A CB 5F
Test bit 3 of the secondary flags. Bit 3 indicates this command requires system disk validation.
5535
If bit 3 is clear, skip the system disk check and continue to 553FH.
5537
LD A,(436AH) 3A 6A 43
Load Register A with the system configuration byte from DOS address 436AH. This contains system status flags.
553A
BIT 5,A CB 6F
Test bit 5 of the system configuration. Bit 5 indicates write-protected system mode or similar restriction.
553C
If bit 5 is set (system is protected), jump to the error handler at 65BEH to display an appropriate error message.
553F
INC HL 23
Increment HL to point to the command handler address (low byte).
5540
LD A,(HL) 7E
Load the low byte of the handler address into Register A.
5541
INC HL 23
Increment HL to point to the high byte of the handler address.
5542
LD H,(HL) 66
Load the high byte of the handler address into Register H.
5543
LD L,A 6F
Load the low byte (from Register A) into Register L. Now HL contains the command handler address.
5544
JP (HL) E9
Jump to the address in HL. This dispatches to the command handler for the matched command.

5545H - "J" Command Handler (Jump to Disk/Track/Sector)

This routine handles the "J" (Jump) command when in disk mode with the jump pending flag set. It prompts for disk/track/sector parameters, validates input, and positions SUPERZAP to display the specified location.

5545
Load HL with 6D3BH, the address of the disk number prompt string.
5548
Call the display string and get input routine at 634EH. Display the prompt and wait for user input.
554B
If Z flag is set (user pressed ENTER only), jump to 55A0H to use default values and continue.
554D
Call the parse disk number routine at 670FH. Parse the disk number from user input.
5550
If carry flag is set (parse error), jump back to 5545H to re-prompt. [LOOP]
5552
Jump forward to 555AH to continue with track/sector prompts.

5554H - "K" Command Handler (Track/Sector Jump) Entry

This entry point handles the "K" command when the jump pending flag (bit 4) is set. It prompts for track number input.

5554
Load HL with 6D44H, the address of the track number prompt string.
5557
Call the display string and get input routine. Display track prompt and wait for user input.
555A
If Z flag is set (ENTER only), jump to 55A0H to use defaults.
555C
Call the parse track number routine at 6732H.
555F
If carry set (error), loop back to re-prompt for track. [LOOP]
5561
Jump forward to 5569H to continue with sector prompt.

5563H - Sector Number Prompt

Prompts for sector number input after disk and track have been specified.

5563
Load HL with 6D4BH, the address of the sector number prompt string.
5566
Display the sector prompt and get user input.
5569
If Z flag set (ENTER only), jump to 5570H to continue with defaults.
556B
Call the parse sector number routine at 6751H.
556E
If carry set (error), loop back to re-prompt. [LOOP]
5570
LD A,(549EH) 3A 9E 54
Load Register A with the sectors per track value from address 549EH.
5573
LD L,A 6F
Copy sectors per track into Register L.
5574
LD A,(549BH) 3A 9B 54
Load Register A with the tracks per side (or granules) value from 549BH.
5577
Call the multiply A×L routine at 687BH to calculate total sectors.
557A
LD A,(54A0H) 3A A0 54
Load Register A with the starting sector offset from 54A0H.
557D
LD E,A 5F
Copy the offset into Register E.
557E
LD D,00H 16 00
Clear Register D, making DE a 16-bit value with the offset.
5580
ADD HL,DE 19
Add the offset (DE) to the total (HL). HL now contains the absolute sector address.
5581
EX DE,HL EB
Exchange DE and HL. DE now holds the absolute sector address.
5582
Jump forward to 55A7H to continue processing.

5584H - "J" Command - Physical Disk/Sector Jump

This routine handles the physical disk jump when no special mode flags are set.

5584
Load HL with 6D50H, the address of the disk prompt string for physical mode.
5587
Display the disk prompt and get user input.
558A
If Z flag set (ENTER only), jump to 55A0H for defaults.
558C
Call the parse disk number routine.
558F
If error, loop back to re-prompt. [LOOP]
5591
Jump forward to continue.

5593H - Absolute Sector Prompt

Prompts for absolute sector number in physical disk mode.

5593
Load HL with 6D58H, the address of the absolute sector prompt string.
5596
Display the prompt and get user input.
5599
If Z flag set, jump to 55A0H for defaults.
559B
Call the parse absolute sector routine at 679EH.
559E
If error, loop back to re-prompt. [LOOP]
55A0
Call the read disk parameters routine at 67B5H to set up disk geometry information.
55A3
LD DE,(54A2H) ED 5B A2 54
Load Register pair DE with the current absolute sector from address 54A2H-54A3H.
55A7
LD HL,(54A8H) 2A A8 54
Load Register pair HL with the maximum sector number from address 54A8H-54A9H.
55AA
LD (540CH),HL 22 0C 54
Store the maximum sector into address 540CH-540DH (working variable).
55AD
LD (54A2H),DE ED 53 A2 54
Store DE (current sector) into the absolute sector variable at 54A2H-54A3H.
55B1
LD HL,(54A2H) 2A A2 54
Load HL with the absolute sector number (just stored).
55B4
LD (540AH),HL 22 0A 54
Store it into the FCB sector field at 540AH-540BH for the DOS read operation.
55B7
LD A,(5491H) 3A 91 54
Load the mode flags byte from 5491H.
55BA
BIT 1,A CB 4F
Test bit 1 (printer mode flag).
55BC
If printer mode is active (bit 1 set), jump to 5BB8H for printer output handling.
55BF
Call the read sector routine at 6457H to read the sector into the buffer.
55C2
Jump to 56BAH to enter the main display/edit loop.

55C5H - File Zap Command Handler Entry

This routine handles file-based zap operations. It prompts for a filespec, opens the file, and sets up for file sector editing. The routine validates the file exists and is accessible before proceeding.

55C5
OR 0C0HOR 11000000 F6 C0
OR Register A with C0H, setting bits 6 and 7. This sets the file mode flags.
55C7
Call the DOS routine at 4409H to prepare for file operations.
55CA
Load HL with 6D5DH, the address of the filespec prompt string.
55CD
LD DE,5400H 11 00 54
Load DE with 5400H, the address of the FCB (File Control Block) buffer.
55D0
LD B,1FH 06 1F
Load Register B with 1FH (31 decimal), the maximum filespec length.
55D2
Call the get filespec input routine at 633CH.
55D5
If Z flag set (empty input), return to the main menu at 54C5H.
55D8
LD DE,5400H 11 00 54
Load DE with the FCB buffer address again.
55DB
LD HL,5300H 21 00 53
Load HL with 5300H, the sector buffer address.
55DE
LD B,00H 06 00
Clear Register B (file open flags = 0 for read mode).
55E0
Call the DOS OPEN file routine at 4424H.
55E3
If NZ (file open failed), jump back to 55C5H to re-prompt. [LOOP]
55E5
LD HL,5401H 21 01 54
Load HL with 5401H, pointing to the FCB flags byte.
55E8
SET 6,(HL) CB F6
Set bit 6 of the FCB flags, indicating file is open.
55EA
LD A,(5406H) 3A 06 54
Load Register A with the drive number from FCB offset 06H.
55ED
LD (5499H),A 32 99 54
Store the drive number into the current drive variable at 5499H.
55F0
LD A,(5491H) 3A 91 54
Load the mode flags from 5491H.
55F3
BIT 3,A CB 5F
Test bit 3 (memory mode flag).
55F5
If bit 3 is clear (not memory mode), jump to 5641H for normal file handling.

Memory mode - load file into memory for editing.

55F7
LD HL,5300H 21 00 53
Load HL with 5300H, the memory load address.
55FA
LD (5403H),HL 22 03 54
Store the load address into FCB offset 03H-04H.
55FD
LD HL,0000H 21 00 00
Load HL with 0000H.
5600
LD (540AH),HL 22 0A 54
Store 0000H into FCB offset 0AH-0BH (starting record = 0).
5603
Call the read sector/file routine to load the file.
5606
LD HL,(5300H) 2A 00 53
Load HL with the first two bytes of the loaded file (load address for /CMD files).
5609
LD (54B2H),HL 22 B2 54
Store this value into 54B2H-54B3H for reference.
560C
EX DE,HL EB
Exchange DE and HL. DE now contains the load address.
560D
LD HL,5487H 21 87 54
Load HL with 5487H, address of a display format buffer.
5610
PUSH HL E5
Save HL on the stack.
5611
Call the convert DE to hex string routine at 61EAH.
5614
LD (HL),48H 36 48
Store 48H (ASCII H) at the current position as the hex suffix.
5616
INC HL 23
Increment HL past the 'H'.
5617
POP HL E1
Restore HL from the stack (back to 5487H).
5618
LD B,05H 06 05
Load B with 05H, the number of characters to display.
561A
Call the display B characters from HL routine at 62BAH.
561D
Load HL with 6D2DH, address of a continuation message.
5620
Call the display string routine at 6245H.
5623
Load HL with 6D7BH, address of the relative sector prompt.
5626
Display prompt and get input.
5629
Call the parse hex/decimal number routine at 6770H.
562C
If error (carry set), loop back to re-prompt. [LOOP]
562E
LD E,00H 1E 00
Clear Register E.
5630
LD (54B4H),DE ED 53 B4 54
Store DE into the relative sector variable at 54B4H-54B5H.
5634
LD A,(5491H) 3A 91 54
Load the mode flags.
5637
BIT 1,A CB 4F
Test bit 1 (printer mode).
5639
If printer mode, jump to 5668H for printer output.
563B
Call routine at 617BH to set up display.
563E
Jump to the main display/edit loop at 56BAH.

5641H - File Relative Sector Prompt

Prompts for relative sector number when in file mode (not memory mode).

5641
Load HL with 6D68H, address of the relative sector prompt for file mode.
5644
Display prompt and get input.
5647
Parse the relative sector number.
564A
If error, loop back. [LOOP]
564C
Jump to 55ADH to continue with sector setup.

564FH - Alternate Relative Sector Prompt

Alternative entry for relative sector prompting with different initial conditions.

564F
Load HL with 6D36H, address of alternate relative sector prompt.
5652
Display prompt and get input.
5655
Parse the input as hex/decimal.
5658
If error, loop back. [LOOP]
565A
LD E,00H 1E 00
Clear Register E.
565C
LD (54B4H),DE ED 53 B4 54
Store DE into the relative sector variable.
5660
LD A,(5491H) 3A 91 54
Load mode flags.
5663
BIT 1,A CB 4F
Test printer mode flag.
5665
If not printer mode, jump to 56BDH.

5668H - Printer Output Setup

Sets up for printer output mode, calculating how many sectors to print.

5668
Call routine at 66E1H to initialize printer output mode.
566B
LD C,10H 0E 10
Load Register C with 10H (16 decimal), the sectors per page for printing.
566D
LD HL,(54ACH) 2A AC 54
Load HL with the remaining byte count from 54ACH-54ADH.
5670
LD DE,0100H 11 00 01
Load DE with 0100H (256 decimal), one sector's worth of bytes.
5673
OR A B7
Clear the carry flag for the subtraction.
5674
SBC HL,DE ED 52
Subtract 256 from the remaining count. Check if at least one more sector remains.
5676
If no borrow (NC), at least 256 bytes remain. Jump to 568FH to continue.
5678
OR A B7
Clear carry for addition.
5679
ADC HL,DE ED 5A
Add 256 back to restore the original count (since we borrowed).
567B
If result is zero (Z), no more data to print. Jump to 65C6H to finish.
567E
LD A,L 7D
Load Register A with the low byte of remaining count.
567F
RRCA 0F
Rotate A right (divide by 2).
5680
RRCA 0F
Rotate again (divide by 4).
5681
RRCA 0F
Rotate again (divide by 8).
5682
RRCA 0F
Rotate again (divide by 16). A now contains bytes/16 = lines to print.
5683
AND 0FHAND 00001111 E6 0F
Mask to keep only lower 4 bits (0-15 lines).
5685
LD C,A 4F
Copy line count to Register C.
5686
LD A,L 7D
Reload the low byte of remaining count.
5687
AND 0FHAND 00001111 E6 0F
Check if there's a partial line (count mod 16).
5689
If no partial line (Z), skip incrementing C.
568B
INC C 0C
Increment C to account for the partial line.
568C
LD HL,0000H 21 00 00
Clear HL to zero.
568F
LD (54ACH),HL 22 AC 54
Store the updated remaining count.
5692
Call the update display position routine at 5200H.
5695
BIT 3,A CB 5F
Test bit 3 (memory mode) of Register A (returned from 5200H).
5697
If in memory mode, jump to 56A2H.
5699
Call routine at 613AH to output sector data.
569C
LD HL,54B5H 21 B5 54
Load HL with address of relative sector high byte.
569F
INC (HL) 34
Increment the relative sector number (high byte).
56A0
Loop back to 566BH to continue printing. [LOOP]
56A2
PUSH BC C5
Save BC on the stack.
56A3
Call routine at 617BH for memory mode output setup.
56A6
POP BC C1
Restore BC from the stack.
56A7
Jump to 5699H to continue processing.

56A9H - Display Error Message (Sector Out of Range)

Displays an error message when the user attempts to access a sector that is out of the valid range.

56A9
Load HL with 6E20H, address of the "out of range" error message.
56AC
LD A,4BH 3E 4B
Load Register A with 4BH (ASCII K), the command to retry.
56AE
PUSH AF F5
Save AF on the stack.
56AF
Call the display string routine to show the error message.
56B2
Load HL with 6DD5H, address of a continuation prompt.
56B5
Call routine to display string and wait for keypress.
56B8
Jump to 571AH to process the keystroke.

56BAH - Main Display/Edit Loop Initialization

This is the main entry point for the sector display and editing loop. It initializes the stack pointer and display position, then enters the command processing loop where users can view and modify sector data.

56BA
LD DE,5300H 11 00 53
Load DE with 5300H, the sector buffer address.
56BD
LD (5495H),DE ED 53 95 54
Store DE into the display position variable at 5495H-5496H.
56C1
LD SP,5300H 31 00 53
Reset the Stack Pointer to 5300H, cleaning up any stale stack data.
56C4
Call the display sector contents routine at 5FB2H to show the current sector on screen.
56C7
LD HL,5493H 21 93 54
Load HL with 5493H, address of the secondary mode flags.
56CA
BIT 4,(HL) CB 66
Test bit 4 of the flags (sector modified flag).
56CC
If bit 4 is clear (sector not modified), jump to 56DBH.

Sector was modified - prompt to write it back to disk.

56CE
RES 4,(HL) CB A6
Clear bit 4 (the modified flag) since we're about to write.
56D0
LD A,(54AEH) 3A AE 54
Load Register A with the original sector number that was modified, from 54AEH.
56D3
LD C,A 4F
Copy the sector number to Register C.
56D4
LD A,95H 3E 95
Load A with 95H, a flag value indicating write with verification.
56D6
Call the write sector routine at 5DBCH to save the modified sector.
56D9
Jump to 56DEH to continue.
56DB
Call routine at 620BH (display status or prompt).
56DE
Call the get command key routine at 5DFAH. Wait for user input and return the key in Register A.

Process the command key entered by the user.

56E1
LD HL,5491H 21 91 54
Load HL with 5491H, address of the mode flags.
56E4
CP 4DH FE 4D
Compare A with 4DH (ASCII M for Modify).
56E6
If not M, jump to 56EDH to check next command.
56E8
BIT 3,(HL) CB 5E
Test bit 3 of mode flags (memory mode).
56EA
If not in memory mode (Z), jump to the Modify handler at 5C5AH.
56ED
CP 58H FE 58
Compare A with 58H (ASCII X for eXit).
56EF
If X, jump to 54C5H to exit to main menu.
56F2
CP 45H FE 45
Compare A with 45H (ASCII E for Edit).
56F4
If E, jump to the Edit handler at 5814H.
56F7
CP 53H FE 53
Compare A with 53H (ASCII S for Search).
56F9
If Register A equals 53H (ASCII S for Search), jump to the Search command handler at 5795H.
56FC
CP 46H FE 46
Compare Register A with 46H (ASCII F for Find/File).
56FE
If F, jump to the Find/File command handler at 582CH.
5701
CP 4CH FE 4C
Compare Register A with 4CH (ASCII L for List).
5703
If not L, jump to 570AH to check next command.
5705
BIT 6,(HL) CB 76
Test bit 6 of the mode flags at (HL=5491H). Bit 6 indicates a file is currently open.
5707
If bit 6 is set (file is open), jump to the List file handler at 5821H.

Check for alternate key mappings: semicolon (;) maps to plus (+), equals (=) maps to minus (-).

570A
CP 3BH FE 3B
Compare Register A with 3BH (ASCII ; semicolon).
570C
If not semicolon, jump to 5710H to continue checking.
570E
LD A,2BH 3E 2B
Replace semicolon with 2BH (ASCII +). This maps ; to + for easier keyboard access on TRS-80.
5710
CP 3DH FE 3D
Compare Register A with 3DH (ASCII = equals sign).
5712
If not equals, jump to 5716H to continue.
5714
LD A,2DH 3E 2D
Replace equals with 2DH (ASCII -). This maps = to - for easier keyboard access.
5716
PUSH AF F5
Save Register A (the command key) and flags onto the stack.
5717
Call the clear command line area routine at 62A7H to prepare for status display.
571A
POP AF F1
Restore Register A (command key) and flags from the stack.
571B
LD HL,5491H 21 91 54
Load HL with 5491H, address of the mode flags byte for testing.
571E
CP 4AH FE 4A
Compare Register A with 4AH (ASCII J for Jump).
5720
If not J, jump to 5734H to check for K command.

J (Jump) command - dispatch based on current mode flags.

5722
BIT 4,(HL) CB 66
Test bit 4 of mode flags (jump pending/disk prompt needed).
5724
If bit 4 set (jump pending), jump to 5545H for disk/track/sector prompt.
5727
BIT 5,(HL) CB 6E
Test bit 5 of mode flags (alternate display mode).
5729
If bit 5 set (alternate mode), jump back to 56C1H to redisplay (J is invalid here).
572B
LD A,(HL) 7E
Load Register A with the mode flags byte from (HL).
572C
AND 48HAND 01001000 E6 48
Mask with 48H to test bits 3 and 6 (memory mode and file open flags).
572E
If either bit 3 or 6 is set, jump to 55CAH for file/memory jump handling.
5731
Otherwise, jump to 5584H for physical disk jump (standard disk sector mode).

5734H - "K" Command Handler (Sector Navigation)

Handles the K command which is used for sector navigation. The behavior varies based on current mode: in alternate mode it prompts for relative sector, in file mode it prompts for file sector, in memory mode it prompts for memory address, and in disk mode it prompts for track/sector.

5734
CP 4BH FE 4B
Compare Register A with 4BH (ASCII K).
5736
If not K, jump to 574FH to check navigation commands (+/-/R).
5738
BIT 5,(HL) CB 6E
Test bit 5 of mode flags (alternate display mode).
573A
If in alternate mode (bit 5 set), jump to 564FH for relative sector prompt.
573D
BIT 6,(HL) CB 76
Test bit 6 of mode flags (file open).
573F
If file is open (bit 6 set), jump to 5641H for file relative sector prompt.
5742
BIT 3,(HL) CB 5E
Test bit 3 of mode flags (memory mode).
5744
If in memory mode (bit 3 set), jump to 5623H for memory address prompt.
5747
BIT 4,(HL) CB 66
Test bit 4 of mode flags (jump pending/track mode).
5749
If bit 4 set, jump to 5554H for track/sector prompt.
574C
Otherwise, jump to 5593H for absolute sector prompt.

574FH - Navigation Key Handler (+, -, R)

Handles the navigation keys: + advances to the next sector, - goes to the previous sector, and R re-reads/refreshes the current sector. The behavior varies based on whether we're in alternate mode (bit 5) or memory mode (bit 3), which changes whether we navigate by absolute sector or relative sector.

574F
BIT 5,(HL) CB 6E
Test bit 5 of mode flags at (HL=5491H) to check for alternate display mode.
5751
If in alternate mode (bit 5 set), jump to 5774H for relative sector navigation.
5753
BIT 3,(HL) CB 5E
Test bit 3 of mode flags (memory mode).
5755
If in memory mode (bit 3 set), jump to 5774H for relative navigation.

Normal disk mode - navigate by absolute sector number.

5757
LD DE,(54A2H) ED 5B A2 54
Load Register pair DE with the current absolute sector number from 54A2H-54A3H.
575B
CP 52H FE 52
Compare Register A with 52H (ASCII R for Re-read/Refresh).
575D
If R, jump to 5771H to re-read the current sector without changing position.
575F
INC DE 13
Increment DE (tentatively advance to next sector).
5760
CP 2BH FE 2B
Compare Register A with 2BH (ASCII +).
5762
If +, jump to 5771H to use the incremented sector number.
5764
CP 2DH FE 2D
Compare Register A with 2DH (ASCII -).
5766
If not -, the key is unrecognized. Jump back to 56C1H to redisplay and wait for valid input.

- key pressed - decrement sector number, but check for underflow (going below sector 0).

5769
DEC DE 1B
Decrement DE (undo the earlier INC).
576A
DEC DE 1B
Decrement DE again to go to the previous sector.
576B
LD A,D 7A
Load Register A with the high byte of DE (sector number).
576C
AND E A3
AND the high byte with the low byte. Result is FFH only if both D and E are FFH (DE=FFFFH, indicating underflow).
576D
INC A 3C
Increment A. If A was FFH (underflow), it becomes 00H and Z flag is set.
576E
If Z flag is set (sector underflowed to FFFFH), jump to 56A9H to display "out of range" error.
5771
Jump to 55ADH to store the new sector number and read/display it.

5774H - Relative Sector Navigation (Alternate/Memory Mode)

Handles navigation when in alternate display mode or memory mode. Instead of navigating by absolute sector number, this uses the relative sector value stored at 54B4H. The high byte of the relative sector (D register) is incremented or decremented.

5774
LD DE,(54B4H) ED 5B B4 54
Load Register pair DE with the relative sector number from 54B4H-54B5H.
5778
CP 52H FE 52
Compare Register A with 52H (ASCII R for Refresh).
577A
If R, jump to 5789H to re-read without changing position.
577C
INC D 14
Increment the high byte of relative sector (D register). This advances by 256 bytes (one display page).
577D
CP 2BH FE 2B
Compare Register A with 2BH (ASCII +).
577F
If +, jump to 5789H to use the incremented value.
5782
CP 2DH FE 2D
Compare Register A with 2DH (ASCII -).
5784
If not -, unrecognized key. Jump back to 56C1H to redisplay.
5787
DEC D 15
Decrement D (undo the earlier INC).
5788
DEC D 15
Decrement D again to go to the previous page.
5789
LD (54B4H),DE ED 53 B4 54
Store the updated relative sector back to 54B4H-54B5H.
578D
BIT 3,(HL) CB 5E
Test bit 3 of mode flags (memory mode).
578F
If not in memory mode (bit 3 clear), jump to 56BDH for standard display update.
5792
In memory mode, jump to 563BH for memory-specific display handling.

5795H - "S" Command Handler (Search)

Handles the S (Search) command. This command searches for a byte pattern across sectors. It validates that the command is appropriate for the current mode, then uses inline parameter data to configure the search. The pattern "COPY" at 579EH-57A1H appears to be placeholder data that gets overwritten with the actual search pattern.

5795
LD A,(HL) 7E
Load Register A with the mode flags byte from (HL=5491H).
5796
AND 68HAND 01101000 E6 68
Mask with 68H to test bits 3, 5, and 6 (memory mode, alternate mode, file open).
5798
If any of these bits are set, Search is not valid. Jump to 56C1H to redisplay.
579B
Call the inline parameter processor at 5803H. This reads parameters from the bytes following this CALL instruction.

The following bytes are inline data, not executable code. They spell "COPY" followed by a NOP (00H) terminator, representing a command signature that 5803H validates.

579E
DEFM "COPY " + 00H 43 4F 50 59 00

Execution resumes here after 5803H returns (it adjusts the return address past the inline data).

57A3
Call the clear command line area routine at 62A7H.
57A6
Call routine at 65D0H to initialize search parameters.
57A9
Load HL with 6DB7H, address of the search pattern prompt string.
57AC
Call routine at 678FH to display prompt and get search pattern input.
57AF
If carry set (user cancelled or error), jump to 6582H to abort the search.
57B2
LD HL,4200H 21 00 42
Load HL with 4200H, the search buffer address where found sectors will be loaded.
57B5
LD (5403H),HL 22 03 54
Store the search buffer address into FCB offset 03H-04H (DMA address).
57B8
LD HL,(54A2H) 2A A2 54
Load HL with the current absolute sector from 54A2H.
57BB
LD (540AH),HL 22 0A 54
Store it into FCB offset 0AH-0BH (sector to search from).
57BE
PUSH HL E5
Save the current sector on the stack.
57BF
Call the sector search routine at 644CH. This performs the actual search operation.
57C2
LD HL,5300H 21 00 53
Load HL with 5300H, the standard sector buffer address.
57C5
LD (5403H),HL 22 03 54
Restore the DMA address to the standard buffer.
57C8
POP HL E1
Restore the original sector number from the stack.
57C9
LD (540AH),HL 22 0A 54
Store it back into the FCB sector field.
57CC
Load HL with 6EABH, address of "NOT FOUND" message (default result).
57CF
If NZ flag (pattern not found), jump to 57DEH to display "NOT FOUND".

Pattern was found. Determine which result message to display based on search type.

57D1
Load HL with 6EB8H, address of "FOUND" message.
57D4
LD A,(5494H) 3A 94 54
Load Register A with the search type flag from 5494H.
57D7
CP 50H FE 50
Compare with 50H (ASCII P for Pattern search).
57D9
If pattern search, jump to 57DEH to display "FOUND".
57DB
Load HL with 6EB3H, address of alternate "FOUND AT" message (for hex search).
57DE
PUSH HL E5
Save the message address on the stack.
57DF
Load HL with 6D0EH, address of a prefix/header message.
57E2
Call routine to display the prefix message.
57E5
POP HL E1
Restore the result message address from the stack.
57E6
Call the display string routine to show the result message.
57E9
Load HL with 6EBCH, address of "PROTECT?" or similar prompt.
57EC
Call routine at 6231H to check/display protection status.
57EF
LD A,20H 3E 20
Load A with 20H (ASCII space), the default search type value.
57F1
If Z flag set, jump to 57F5H to use space as search type.
57F3
LD A,50H 3E 50
Load A with 50H (ASCII P), indicating pattern search type.
57F5
LD (5494H),A 32 94 54
Store the search type flag to 5494H.
57F8
Call routine at 6474H to write sector or finalize the operation.
57FB
Load HL with 6C2DH, address of a completion/status message.
57FE
LD A,52H 3E 52
Load A with 52H (ASCII R), the key code to simulate a Re-read command.
5800
Jump to 56AEH to display the message and return to the command loop.

5803H - Inline Parameter Processor

This utility routine processes inline parameter data that follows a CALL instruction. It reads bytes from the return address, comparing them against user input character by character. When a zero byte (terminator) is found, the routine adjusts the return address to point past the inline data and returns. This allows commands to embed their parameter signatures directly after the CALL instruction.

5803
Call routine at 5DF7H to get the next input character into Register A.
5806
POP HL E1
Pop the return address from the stack into HL. This points to the inline data following the CALL 5803H.
5807
CP (HL) BE
Compare the input character (A) with the expected character at (HL).
5808
INC HL 23
Increment HL to point to the next byte of inline data.
5809
If the characters don't match (NZ), the parameter is wrong. Jump to 56C1H to redisplay the sector.
580C
PUSH HL E5
Push the updated address back onto the stack (for the recursive CALL or final return).
580D
LD A,(HL) 7E
Load the next byte from the inline data.
580E
OR A B7
Test if this byte is zero (the terminator).
580F
If not zero, more characters to check. Jump back to 5803H to process the next one. [LOOP]

Terminator found - all parameters matched. Adjust return address and exit.

5811
POP HL E1
Pop the address (now pointing to the terminator) from the stack.
5812
INC HL 23
Increment HL past the terminator to the actual code that follows the inline data.
5813
JP (HL) E9
Jump to the address in HL, effectively returning past the inline data to continue execution.

5814H - "E" Command Handler (Exit to DOS)

This routine handles the E (Exit) command. It uses the inline parameter processor at 5803H to verify the user typed "EXIT", then clears the command line area and jumps to the DOS warm start entry point at 402DH to return to NEWDOS/80 Ready prompt.

5814
Call the inline parameter processor at 5803H. This routine reads bytes following this CALL and compares them against user input to verify the command keyword.

The following bytes are inline data spelling "XIT" (the "E" was already matched). The routine at 5803H compares each byte against user input.

5817
DEFB 58H 58
Inline data: 58H = ASCII X
5818
DEFB 49H 49
Inline data: 49H = ASCII I
5819
DEFB 54H 54
Inline data: 54H = ASCII T
581A
DEFB 00H 00
Inline data: 00H = terminator byte marking end of keyword

Execution continues here after 5803H validates "EXIT" was typed.

581B
Call the clear command line area routine at 62A7H to clean up the display before exiting.
581E
JP 402DH C3 2D 40
Jump to 402DH, the DOS warm start entry point. This exits SUPERZAP and returns to the NEWDOS/80 Ready prompt.

5821H - "L" Command Handler (List File Sectors)

This routine handles the L (List) command when a file is open (bit 6 of mode flags is set). It saves the current key code, calls the file sector read routine, and determines whether to continue listing or return to the display loop.

5821
LD B,A 47
Copy Register A (the command key L = 4CH) into Register B for later use.
5822
Call the read next file sector routine at 5E37H. This reads the next sector of the open file. Returns with carry set on error, Z flag set if end of file.
5825
If carry flag is set (read error occurred), jump to 5829H to return to the display loop.
5827
If NZ flag (not end of file, more sectors available), jump to 5834H to continue processing.
5829
Jump to 56C1H to return to the main display/edit loop and redisplay the current sector.

582CH - "F" Command Handler (Find/File Operations)

This routine handles the F (Find) command. It initializes the search parameters and calls the file sector read routine to begin searching. If no match is found immediately, it continues to the search setup at 5834H.

582C
LD B,00H 06 00
Clear Register B to zero. This initializes the search direction/mode flags.
582E
Call the read file sector routine at 5E37H. Returns Z flag if at end of file, carry if error.
5831
If Z flag is set (end of file reached), jump to 58BEH to finalize the search setup.

5834H - Find Command Parameter Setup

This section sets up the search parameters for the Find command. It saves various state variables including the search position, mode flags, and relative sector information. The routine handles both memory mode and disk mode searches differently based on the mode flags.

5834
PUSH AF F5
Save Register A and flags onto the stack. A contains the result from the previous sector read.
5835
LD A,B 78
Load Register A with the value from Register B (search mode/direction flags).
5836
LD (54BEH),A 32 BE 54
Store the search mode flags into address 54BEH. This variable controls the search direction (forward/backward).
5839
XOR A AF
Clear Register A to zero.
583A
LD (54C0H),A 32 C0 54
Store zero into address 54C0H. This clears the search offset counter.
583D
LD C,A 4F
Copy zero into Register C, initializing the byte position counter.
583E
LD A,(HL) 7E
Load Register A with the byte at (HL). HL points to the mode flags at 5491H.
583F
AND 28HAND 00101000 E6 28
Mask with 28H to isolate bits 3 and 5 (memory mode and alternate display mode flags).
5841
LD B,A 47
Save the masked mode flags into Register B for later testing.
5842
LD HL,(54B4H) 2A B4 54
Load Register pair HL with the relative sector number from 54B4H-54B5H.
5845
LD (54C3H),HL 22 C3 54
Store the relative sector into 54C3H-54C4H as the search starting position.
5848
If NZ (either memory mode or alternate mode is active), jump to 5851H to skip absolute sector setup.

Standard disk mode - set up search using absolute sector number.

584A
LD L,C 69
Load Register L with C (zero), clearing the low byte.
584B
LD DE,(54A2H) ED 5B A2 54
Load Register pair DE with the current absolute sector from 54A2H-54A3H.
584F
LD H,E 63
Copy the low byte of absolute sector (E) into Register H.
5850
LD C,D 4A
Copy the high byte of absolute sector (D) into Register C.
5851
POP AF F1
Restore Register A and flags from the stack.
5852
If carry flag is set (indicating a special search mode), jump to 586AH for alternate processing.
5854
LD E,00H 1E 00
Clear Register E to zero, initializing the search byte offset.
5856
Call the initialize position variables routine at 520DH. This sets up HL and C from E, then stores to 54C3H.
5859
BIT 3,B CB 58
Test bit 3 of Register B (memory mode flag).
585B
If bit 3 is clear (not in memory mode), jump to 5860H.
585D
Call routine at 5214H to load H from 54B3H and store HL to 54C3H (memory mode position setup).
5860
Call the read file sector routine at 5E37H to get the next sector for searching.
5863
If carry set (error), jump to 5872H to handle the result.
5865
If Z flag set (end of file), jump to 5872H to handle the result.
5867
Jump to 56C1H to return to main display loop (search completed or aborted).

586AH - Alternate Search Mode Entry

This section handles the alternate search mode when the carry flag was set on entry. It processes hex input for the search pattern.

586A
Call routine at 5E2EH to get hex byte input for the search pattern.
586D
If carry set (input error or cancel), jump to 5867H to abort and return to display.
586F
If NZ (valid input received), call the read file sector routine at 5E37H.

5872H - Search Position Calculation

This section calculates and stores the search position within the current sector. It handles the byte offset calculation and adjusts for memory mode if needed.

5872
PUSH AF F5
Save Register A and flags onto the stack.
5873
LD A,E 7B
Load Register A with the value from Register E (the byte offset within the sector).
5874
LD (54C2H),A 32 C2 54
Store the byte offset into address 54C2H. This is the position within sector for the search.
5877
ADD A,L 85
Add the byte offset (A) to Register L (low byte of position).
5878
LD L,A 6F
Store the result back into Register L.
5879
BIT 3,B CB 58
Test bit 3 of Register B (memory mode flag).
587B
If bit 3 is clear (not memory mode), jump to 5896H to skip memory-specific calculations.

Memory mode - adjust position relative to file load address.

587D
LD DE,(54B2H) ED 5B B2 54
Load Register pair DE with the file load address from 54B2H-54B3H. This is where the file was loaded into memory.
5881
OR A B7
Clear the carry flag for subtraction.
5882
SBC HL,DE ED 52
Subtract the load address (DE) from the current position (HL). This gives the offset from start of file.
5884
If no carry (position ≥ load address), jump to 588FH to continue.

Position is before load address - adjust to start of file.

5886
LD A,L 7D
Load Register A with the low byte of the result (negative offset).
5887
LD HL,54C2H 21 C2 54
Load HL with the address of the byte offset variable at 54C2H.
588A
SUB (HL) 96
Subtract the current byte offset from A to get the adjustment needed.
588B
LD (HL),A 77
Store the adjusted offset back to 54C2H.
588C
LD HL,0000H 21 00 00
Clear HL to zero (start of file).
588F
LD DE,0002H 11 02 00
Load DE with 0002H, an offset adjustment value (skip the 2-byte load address header).
5892
ADD HL,DE 19
Add 2 to HL to skip past the load address header in the file.
5893
If no carry (no overflow), jump to 5896H.
5895
INC C 0C
Increment C to account for the carry (position wrapped past 64K).
5896
LD (54B6H),HL 22 B6 54
Store the calculated position into 54B6H-54B7H. This is the search start position.
5899
LD A,C 79
Load Register A with Register C (high byte of position or sector count).
589A
LD (54B8H),A 32 B8 54
Store the high byte/count into address 54B8H.
589D
POP AF F1
Restore Register A and flags from the stack.
589E
If Z flag is set (end of data), jump to 58BEH to finalize search setup.

58A0H - Multi-Byte Search Pattern Input

This section collects multiple bytes for the search pattern. It allows up to 4 bytes to be entered for the search string.

58A0
LD B,04H 06 04
Load Register B with 04H, the maximum search pattern length (4 bytes).
58A2
LD HL,54B9H 21 B9 54
Load HL with 54B9H, the address of the search pattern buffer.
58A5
Call routine at 5E2EH to get the next hex byte from user input.
58A8
If carry set (input error or cancel), jump to 5867H to abort the search.
58AB
LD (HL),E 73
Store the input byte (E) into the search pattern buffer at (HL).
58AC
INC HL 23
Increment HL to point to the next position in the pattern buffer.
58AD
If Z flag set (end of input), jump to 58B8H to finish pattern collection.
58AF
DEC B 05
Decrement the remaining byte count in B.
58B0
If B reached zero (4 bytes collected), jump to 5867H - pattern is full.
58B3
Call routine at 5E33H to get additional input for the pattern.
58B6
Loop back to 58A8H to process the next byte. [LOOP]
58B8
LD A,05H 3E 05
Load Register A with 05H (maximum pattern length + 1).
58BA
SUB B 90
Subtract the remaining count (B) from 5 to get the actual pattern length.
58BB
LD (54BDH),A 32 BD 54
Store the pattern length into address 54BDH.

58BEH - Search Initialization Complete

This section finalizes the search setup by storing the starting position and initiating the search loop. It checks for the BREAK key and handles both disk sector and memory mode searches.

58BE
PUSH HL E5
Save HL onto the stack (preserves current position).
58BF
POP HL E1
Immediately restore HL from the stack. This is effectively a NOP but may be a placeholder or alignment.
58C0
LD HL,(54C3H) 2A C3 54
Load HL with the search starting position from 54C3H-54C4H.
58C3
LD (54B4H),HL 22 B4 54
Store it into the relative sector variable at 54B4H-54B5H.
58C6
LD A,(38C0H) 3A C0 38
Load Register A with the byte at 38C0H. This is the keyboard matrix address for detecting the BREAK key.
58C9
AND 08HAND 00001000 E6 08
Mask with 08H to isolate the BREAK key bit.
58CB
If NZ (BREAK key is pressed), jump to 5937H to abort the search.

BREAK not pressed - continue with the search.

58CD
LD A,(54C0H) 3A C0 54
Load Register A with the search offset counter from 54C0H.
58D0
LD (54BFH),A 32 BF 54
Store it into address 54BFH (working copy of offset).
58D3
LD A,(54B6H) 3A B6 54
Load Register A with the low byte of the search position from 54B6H.
58D6
LD C,A 4F
Copy the position low byte into Register C.
58D7
LD HL,(54B7H) 2A B7 54
Load HL with the search position high word from 54B7H-54B8H.
58DA
Call the search execution routine at 593CH. This performs the actual byte-by-byte search.
58DD
LD A,C 79
Load Register A with Register C (updated position low byte).
58DE
LD (54B6H),A 32 B6 54
Store the updated position back to 54B6H.
58E1
LD (54B7H),HL 22 B7 54
Store the updated high word back to 54B7H-54B8H.
58E4
PUSH HL E5
Save HL (current position) onto the stack.
58E5
LD A,(54BFH) 3A BF 54
Load Register A with the working offset from 54BFH.
58E8
LD (54C0H),A 32 C0 54
Store it back to the master offset counter at 54C0H.
58EB
LD A,(5491H) 3A 91 54
Load Register A with the mode flags from 5491H.
58EE
AND 28HAND 00101000 E6 28
Mask with 28H to test bits 3 and 5 (memory mode and alternate display).
58F0
PUSH AF F5
Save the masked flags onto the stack.
58F1
If NZ (memory or alternate mode active), jump to 5902H to skip disk sector calculations.

Standard disk mode - calculate absolute sector from position.

58F3
LD D,H 54
Copy H to D (high byte of position).
58F4
LD E,L 5D
Copy L to E (mid byte of position). DE now holds the sector number.
58F5
LD A,C 79
Load Register A with C (low byte of position = byte offset in sector).
58F6
OR A B7
Test if the byte offset is zero.
58F7
If NZ (offset not zero), jump to 58FAH.
58F9
DEC DE 1B
Decrement DE (sector number) if offset was zero, pointing to previous sector.
58FA
DEC A 3D
Decrement A (adjust byte offset).
58FB
LD (54C2H),A 32 C2 54
Store the adjusted byte offset to 54C2H.
58FE
LD (54A2H),DE ED 53 A2 54
Store DE as the new current absolute sector at 54A2H-54A3H.

5902H - Update Search State and Continue

This section updates the search state variables and determines whether to continue searching or if a match was found. It handles incrementing through sectors and checking for sector boundaries.

5902
LD HL,54C2H 21 C2 54
Load HL with 54C2H, the address of the byte offset variable.
5905
LD A,(HL) 7E
Load Register A with the current byte offset from (HL).
5906
LD (54AEH),A 32 AE 54
Store the byte offset into address 54AEH for later reference.
5909
POP AF F1
Restore the masked mode flags from the stack.
590A
If Z flag (standard disk mode), jump to 5919H to continue with search pattern matching.

Memory or alternate mode - check for sector boundary crossing.

590C
INC (HL) 34
Increment the byte offset at (HL).
590D
If NZ (offset didn't wrap to zero), jump to 5919H to continue.

Byte offset wrapped - advance to next 256-byte page.

590F
LD HL,(54C3H) 2A C3 54
Load HL with the current page/sector position from 54C3H-54C4H.
5912
LD DE,0100H 11 00 01
Load DE with 0100H (256 decimal), one page/sector worth of bytes.
5915
ADD HL,DE 19
Add 256 to HL to advance to the next page.
5916
LD (54C3H),HL 22 C3 54
Store the updated page position back to 54C3H-54C4H.

5919H - Search Pattern Matching Loop

This is the core pattern matching loop. It compares bytes from the search pattern buffer against the current position in the data being searched. When all pattern bytes match, the search is successful.

5919
LD HL,54B9H 21 B9 54
Load HL with 54B9H, the address of the search pattern buffer.
591C
LD A,(54BDH) 3A BD 54
Load Register A with the search pattern length from 54BDH.
591F
LD D,A 57
Copy the pattern length into Register D as a byte counter.
5920
LD A,(HL) 7E
Load Register A with the next byte from the search pattern at (HL).
5921
CP B B8
Compare the pattern byte (A) with the data byte (B). If they match, Z flag is set.
5922
INC HL 23
Increment HL to point to the next pattern byte.
5923
If NZ (bytes don't match), jump back to 58BFH to continue searching from next position. [LOOP - NO MATCH]
5925
DEC D 15
Decrement the pattern byte counter D.
5926
If D reached zero (all pattern bytes matched), jump to 5931H - MATCH FOUND!

More pattern bytes to check - get next data byte.

5928
EX (SP),HL E3
Exchange HL with the value on the stack. This retrieves the data position while saving the pattern position.
5929
PUSH DE D5
Save DE (byte counter) onto the stack.
592A
Call the get next data byte routine at 593CH. Returns next byte in B.
592D
POP DE D1
Restore DE (byte counter) from the stack.
592E
EX (SP),HL E3
Exchange HL with stack again, restoring the pattern position and saving the updated data position.
592F
Loop back to 5920H to compare the next pattern byte. [LOOP - CONTINUE MATCHING]

5931H - Search Match Found

This section executes when a search pattern match is found. It cleans up the stack, sets the "sector modified" flag to indicate a match was found at this location, and returns to the command loop with the 'R' command to re-read and display the found sector.

5931
POP HL E1
Pop and discard the saved position from the stack (cleanup).
5932
LD HL,5493H 21 93 54
Load HL with 5493H, the address of the secondary mode flags.
5935
SET 4,(HL) CB E6
Set bit 4 of the secondary flags. This indicates a match was found and the sector should be displayed.
5937
LD A,52H 3E 52
Load Register A with 52H (ASCII R for Re-read). This will cause the found sector to be displayed.
5939
Jump to 5716H to process the R command, which re-reads and displays the current sector showing the match.

593CH - Get Next Byte for Search

This routine retrieves the next byte from the data being searched. It handles both alternate display mode (reading from a buffer) and normal mode (reading from disk sectors). The routine advances the position counters and handles sector boundaries.

593C
LD A,(5491H) 3A 91 54
Load Register A with the mode flags from 5491H.
593F
AND 20HAND 00100000 E6 20
Mask with 20H to test bit 5 (alternate display mode).
5941
If bit 5 is clear (not alternate mode), jump to 5951H for normal sector reading.

Alternate display mode - read from memory buffer.

5943
LD A,H 7C
Load Register A with the high byte of position (H).
5944
OR A B7
Test if H is zero.
5945
If H is not zero (position out of buffer range), jump to 59B4H to reset search.
5947
PUSH DE D5
Save DE onto the stack.
5948
LD D,L 55
Copy L (mid position byte) to D.
5949
LD E,C 59
Copy C (low position byte) to E. DE now holds the buffer offset.
594A
LD A,(DE) 1A
Load Register A with the byte at address DE (from the buffer).
594B
POP DE D1
Restore DE from the stack.
594C
LD B,A 47
Copy the data byte to Register B (return value).
594D
INC C 0C
Increment C (low byte of position).
594E
RET NZ C0
If C didn't wrap to zero, return with byte in B.
594F
INC HL 23
C wrapped - increment HL (advance to next page).
5950
RET C9
Return with byte in B and updated position in C,HL.

5951H - Normal Mode Sector Read for Search

This routine reads the next sector from disk during a search operation. It calls the DOS sector read routine and handles various conditions including end-of-file, sector boundaries, and file mode operations. The routine manages the search offset counter and handles multi-sector spanning searches.

5951
Call the DOS sector read routine at 5990H. This reads the next sector and returns the first byte in B, with status flags set.
5954
LD A,(54BEH) 3A BE 54
Load Register A with the search direction flag from 54BEH. Zero indicates forward search.
5957
OR A B7
Test if the search direction flag is zero.
5958
RET Z C8
If zero (forward search without special handling), return with byte in B.

Non-zero direction flag - this is a file mode search requiring additional handling.

5959
LD A,(5491H) 3A 91 54
Load Register A with the mode flags from 5491H.
595C
BIT 6,A CB 77
Test bit 6 (file open flag).
595E
If bit 6 is clear (no file open), jump to 56C1H to return to the display loop.
5961
LD A,(54BFH) 3A BF 54
Load Register A with the search offset counter from 54BFH.
5964
OR A B7
Test if the offset counter is zero.
5965
If offset is zero, jump to 596CH to handle sector boundary.
5967
DEC A 3D
Decrement the offset counter.
5968
LD (54BFH),A 32 BF 54
Store the decremented counter back to 54BFH.
596B
RET C9
Return with byte in B (continue using same sector data).

596CH - Handle File Sector Boundary

This routine handles crossing sector boundaries during file searches. It reads the next sector and determines whether to continue the search, skip sectors, or reset based on the file structure.

596C
LD D,B 50
Save the current data byte (B) into Register D for later comparison.
596D
Call the DOS sector read routine to get the next sector.
5970
LD A,D 7A
Load Register A with the saved byte from D.
5971
CP 20H FE 20
Compare with 20H (32 decimal). This checks if the value indicates a granule continuation.
5973
If A ≥ 20H (not a valid granule pointer), jump to 6576H to handle the end of file condition.
5976
DEC A 3D
Decrement A to test the granule value.
5977
If A is now zero (was 01H, indicating a Data Address Mark), jump to 5982H for special handling.
5979
DEC A 3D
Decrement A again.
597A
If A is now zero (was 02H, indicating end of granule chain), jump to 59B4H to reset search state.
597C
LD D,B 50
Save the new byte (B) into D.
597D
Call routine at 5989H to skip sectors based on granule structure.
5980
Loop back to 5951H to continue reading. [LOOP]

5982H - Handle Data Address Mark

This routine handles a Data Address Mark (DAM) encountered during file search. It calculates the proper offset for continuing the search past the header bytes.

5982
LD D,03H 16 03
Load Register D with 03H, the number of header bytes to skip (typically load address + length).
5984
LD A,B 78
Load Register A with the current data byte from B.
5985
SUB D 92
Subtract the skip count (3) from the current byte value.
5986
LD (54BFH),A 32 BF 54
Store the result as the new search offset counter at 54BFH. This adjusts the position past the header.

5989H - Skip Sectors Loop

This routine skips a specified number of sectors during file search. It repeatedly calls the DOS sector read until the counter in D reaches zero.

5989
Call the DOS sector read routine to read and advance to the next sector.
598C
DEC D 15
Decrement the sector skip counter in D.
598D
If D is not zero (more sectors to skip), loop back to 5989H. [LOOP]
598F
RET C9
Return when all sectors have been skipped.

5990H - DOS Sector Read for Search

This routine performs the actual DOS sector read operation. It calls the NEWDOS/80 file read routine at 444EH with the FCB at 5400H. The routine handles various return conditions including successful read, end of file (error 06H), and break key detection.

5990
PUSH DE D5
Save Register pair DE onto the stack.
5991
LD DE,5400H 11 00 54
Load DE with 5400H, the address of the File Control Block (FCB).
5994
Call the NEWDOS/80 sequential file read routine at 444EH. Returns Z flag if successful, error code in A if failed.
5997
If read was successful (Z flag), call the BREAK key check routine at 0013H. This allows the user to abort the search.
599A
If Z flag still set (no BREAK pressed), jump to 594BH to return the data byte in B.

Either read error occurred or BREAK was pressed. Check error type.

599C
CP 06H FE 06
Compare error code with 06H (NEWDOS/80 End of File error).
599E
If not EOF error, jump to 59ABH to check for other conditions.

End of file - return the last byte from the buffer.

59A0
LD B,00H 06 00
Clear Register B to zero (high byte of offset).
59A2
PUSH HL E5
Save HL onto the stack.
59A3
LD HL,(5403H) 2A 03 54
Load HL with the DMA buffer address from FCB offset 03H-04H.
59A6
ADD HL,BC 09
Add the current offset (BC) to get the address of the last byte read.
59A7
LD A,(HL) 7E
Load Register A with the byte at that address.
59A8
POP HL E1
Restore HL from the stack.
59A9
Jump to 594BH to restore DE, copy byte to B, and return.
59AB
CP 1CH FE 1C
Compare error code with 1CH (BREAK key pressed code).
59AD
If BREAK was pressed, jump to 59B4H to reset and abort the search.
59AF
CP 1DH FE 1D
Compare error code with 1DH (alternate BREAK/abort code).
59B1
If not BREAK, this is a real disk error. Jump to 6578H to display the error message.

59B4H - Reset Search State

This routine resets all search state variables to their initial values. It clears the position counters, offset variables, and prepares for a new search or returning to normal display mode. This is called when the search is aborted or reaches the end of searchable data.

59B4
XOR A AF
Clear Register A to zero.
59B5
LD (54B8H),A 32 B8 54
Store zero into 54B8H (high byte of search position).
59B8
LD H,A 67
Clear Register H to zero.
59B9
LD L,A 6F
Clear Register L to zero. HL is now 0000H.
59BA
LD D,A 57
Clear Register D to zero.
59BB
LD E,A 5F
Clear Register E to zero. DE is now 0000H.
59BC
LD (54BFH),A 32 BF 54
Store zero into 54BFH (search offset counter).
59BF
LD (54C2H),A 32 C2 54
Store zero into 54C2H (byte position within sector).
59C2
LD A,(5491H) 3A 91 54
Load Register A with the mode flags from 5491H.
59C5
AND 08HAND 00001000 E6 08
Mask with 08H to test bit 3 (memory mode).
59C7
If bit 3 is clear (not memory mode), jump to 59CEH.

Memory mode - use file load address as base.

59C9
LD DE,54B2H 11 B2 54
Load DE with 54B2H, the address of the file load address variable.
59CC
LD L,02H 2E 02
Set L to 02H (offset past the load address header).
59CE
LD (54C3H),DE ED 53 C3 54
Store DE into 54C3H-54C4H (search starting position).
59D2
LD (54B6H),HL 22 B6 54
Store HL into 54B6H-54B7H (current search position).
59D5
Load HL with 6EDBH, the address of the "NOT FOUND" message string.
59D8
Call the display string routine at 6245H to show "NOT FOUND".
59DB
LD A,4BH 3E 4B
Load Register A with 4BH (ASCII K command).
59DD
Jump to 571BH to process the K command, returning to the sector prompt.

59E0H - Copy Command Setup (Source Specification)

This routine handles the setup for the Copy command. It displays prompts for the source disk/sector and collects the parameters needed for the copy operation. The routine saves the source parameters for later use when specifying the destination.

59E0
Load HL with 6D28H, the address of the "COPY FROM" prompt string.
59E3
Call routine at 6224H to display the prompt and prepare for input.
59E6
Load HL with 6D0BH, the address of the "DISK" prompt string.
59E9
Call routine at 678FH to display prompt and get disk number input.
59EC
If carry set (invalid input), loop back to 59E6H to re-prompt. [LOOP]
59EE
Call routine at 66EFH to process and validate the disk number.
59F1
LD A,(5499H) 3A 99 54
Load Register A with the source disk number from 5499H.
59F4
LD (549AH),A 32 9A 54
Store the disk number into 549AH (saved source disk).
59F7
LD HL,(54A2H) 2A A2 54
Load HL with the current absolute sector from 54A2H-54A3H.
59FA
LD (54A4H),HL 22 A4 54
Store it into 54A4H-54A5H (saved source sector).
59FD
LD A,(54AEH) 3A AE 54
Load Register A with the byte offset from 54AEH.
5A00
LD (54AFH),A 32 AF 54
Store the byte offset into 54AFH (saved source offset).
5A03
LD HL,(54A8H) 2A A8 54
Load HL with the maximum sector number from 54A8H-54A9H.
5A06
LD (54AAH),HL 22 AA 54
Store it into 54AAH-54ABH (saved source max sector).

5A09H - Copy Command Setup (Destination Specification)

This section prompts for the destination disk and sector for the copy operation. It validates the input and prepares the parameters for the actual copy.

5A09
Load HL with 6D0EH, the address of the "TO DISK" prompt string.
5A0C
Call routine to display prompt and get destination disk number.
5A0F
If carry set (invalid input), loop back to re-prompt. [LOOP]
5A11
Call routine to process and validate the destination disk number.
5A14
Call routine at 66E1H to calculate transfer parameters.
5A17
LD A,(54ADH) 3A AD 54
Load Register A with the high byte of the remaining byte count from 54ADH.
5A1A
LD E,A 5F
Copy to Register E.
5A1B
LD D,00H 16 00
Clear D. DE now holds the sector count.
5A1D
LD A,(54AFH) 3A AF 54
Load Register A with the saved source byte offset from 54AFH.
5A20
LD B,A 47
Copy to Register B.
5A21
LD A,(54AEH) 3A AE 54
Load Register A with the current byte offset from 54AEH.
5A24
LD C,A 4F
Copy to Register C. BC now holds the byte offsets.
5A25
INC DE 13
Increment DE (sector count) to include the partial last sector.
5A26
PUSH BC C5
Save BC (byte offsets) onto the stack.
5A27
Call routine at 6111H to calculate the total transfer size.
5A2A
POP BC C1
Restore BC (byte offsets) from the stack.
5A2B
LD HL,(54ACH) 2A AC 54
Load HL with the remaining byte count from 54ACH-54ADH.
5A2E
PUSH HL E5
Save the byte count onto the stack.
5A2F
LD E,C 59
Copy C (destination offset) to E.
5A30
LD C,B 48
Copy B (source offset) to C.
5A31
LD B,00H 06 00
Clear B.
5A33
LD D,B 50
Clear D. Now BC = source offset, DE = dest offset.
5A34
LD HL,5493H 21 93 54
Load HL with 5493H, address of secondary mode flags.
5A37
BIT 7,(HL) CB 7E
Test bit 7 (reverse copy direction flag).
5A39
If bit 7 is clear (forward copy), jump to 5A57H.

Reverse copy mode - adjust source and destination positions.

5A3B
POP HL E1
Pop byte count into HL.
5A3C
PUSH HL E5
Push it back (we just need to read it).
5A3D
ADD HL,DE 19
Add destination offset to byte count.
5A3E
DEC HL 2B
Decrement to point to last byte.
5A3F
LD A,L 7D
Get low byte of end position.
5A40
LD E,H 5C
Get high byte into E.
5A41
LD HL,(54A2H) 2A A2 54
Load current absolute sector.
5A44
ADD HL,DE 19
Add sector offset.
5A45
LD (54A2H),HL 22 A2 54
Store as new destination sector.
5A48
LD E,A 5F
Copy offset to E.
5A49
POP HL E1
Pop byte count.
5A4A
PUSH HL E5
Push it back.
5A4B
ADD HL,BC 09
Add source offset to byte count.
5A4C
DEC HL 2B
Decrement to point to last byte.
5A4D
LD A,L 7D
Get low byte.
5A4E
LD C,H 4C
Get high byte into C.
5A4F
LD HL,(54A4H) 2A A4 54
Load saved source sector.
5A52
ADD HL,BC 09
Add sector offset.
5A53
LD (54A4H),HL 22 A4 54
Store as new source sector.
5A56
LD C,A 4F
Copy offset to C.

5A57H - Copy Operation Main Loop Setup

This section sets up the buffer addresses and begins the main copy loop. It calculates the source and destination buffer addresses and initiates the byte-by-byte copy process.

5A57
LD A,E 7B
Load Register A with E (destination byte offset).
5A58
LD HL,5300H 21 00 53
Load HL with 5300H, the destination sector buffer address.
5A5B
ADD HL,DE 19
Add destination offset (DE) to get the actual buffer address.
5A5C
EX DE,HL EB
Exchange - DE now points to destination in buffer.
5A5D
LD HL,4200H 21 00 42
Load HL with 4200H, the source sector buffer address.
5A60
ADD HL,BC 09
Add source offset (BC) to get the actual buffer address.
5A61
LD B,C 41
Copy source low offset to B.
5A62
LD C,A 4F
Copy destination low offset to C.
5A63
Call routine at 5AACH to read the source sector into buffer 4200H.
5A66
Call routine at 5AF2H to read the destination sector into buffer 5300H.
5A69
LD A,(5493H) 3A 93 54
Load Register A with secondary mode flags.
5A6C
BIT 7,A CB 7F
Test bit 7 (reverse direction flag).
5A6E
If forward direction, jump to 5A72H.
5A70
INC B 04
Adjust source offset for reverse copy.
5A71
INC C 0C
Adjust destination offset for reverse copy.

5A72H - Copy Operation Byte Transfer Loop

This is the main byte-by-byte copy loop. It transfers data from the source buffer to the destination buffer, handling sector boundaries and direction control.

5A72
LD A,(HL) 7E
Load Register A with the byte from source buffer at (HL).
5A73
LD (DE),A 12
Store the byte into the destination buffer at (DE).
5A74
EX (SP),HL E3
Exchange HL with the top of stack (byte count). HL now has remaining count.
5A75
DEC HL 2B
Decrement the remaining byte count.
5A76
LD A,H 7C
Load high byte of count into A.
5A77
OR L B5
OR with low byte to test if count reached zero.
5A78
If not zero (more bytes to copy), jump to 5A80H to continue.

Copy complete - write the final destination sector.

5A7A
Call routine at 5AD2H to write the destination sector to disk.
5A7D
Jump to 65C6H to complete the copy operation and return to the command loop.
5A80
EX (SP),HL E3
Exchange HL back with stack. HL now points to source buffer again.
5A81
LD A,(5493H) 3A 93 54
Load secondary mode flags.
5A84
BIT 7,A CB 7F
Test bit 7 (reverse direction).
5A86
If reverse direction, jump to 5A9AH.

Forward copy - increment pointers.

5A88
INC HL 23
Increment source buffer pointer.
5A89
INC DE 13
Increment destination buffer pointer.
5A8A
INC B 04
Increment source byte counter.
5A8B
If source didn't wrap past 256, jump to 5A91H.
5A8D
DEC H 25
Wrapped - adjust H to point to next page (actually previous in memory).
5A8E
Call routine to read the next source sector.
5A91
INC C 0C
Increment destination byte counter.
5A92
If destination didn't wrap, jump to 5A98H.
5A94
DEC D 15
Wrapped - adjust D for next page.
5A95
Call routine to write current destination sector and read next.
5A98
Loop back to 5A72H to copy the next byte. [LOOP]

5A9AH - Reverse Copy Pointer Adjustment

This section handles pointer adjustment for reverse direction copying. It decrements the buffer pointers instead of incrementing them.

5A9A
DEC HL 2B
Decrement source buffer pointer (reverse direction).
5A9B
DEC DE 1B
Decrement destination buffer pointer.
5A9C
DEC B 05
Decrement source byte counter.
5A9D
If source didn't underflow, jump to 5AA3H.
5A9F
INC H 24
Underflowed - adjust H to point to previous sector's page.
5AA0
Call routine to read the previous source sector.
5AA3
DEC C 0D
Decrement destination byte counter.
5AA4
If destination didn't underflow, jump to 5AAAH.
5AA6
INC D 14
Underflowed - adjust D for previous sector's page.
5AA7
Call routine to write and read previous destination sector.
5AAA
Loop back to 5A72H to copy the next byte. [LOOP]

5AACH - Read Source Sector for Copy

This routine reads the source sector for the copy operation into the buffer at 4200H. It saves and restores all working registers, handles the sector position update, and accounts for forward or reverse direction.

5AAC
PUSH HL E5
Save HL (source buffer pointer) onto the stack.
5AAD
PUSH DE D5
Save DE (destination buffer pointer) onto the stack.
5AAE
PUSH BC C5
Save BC (byte counters) onto the stack.
5AAF
LD HL,(54A4H) 2A A4 54
Load HL with the source sector number from 54A4H-54A5H.
5AB2
LD DE,(54AAH) ED 5B AA 54
Load DE with the source maximum sector from 54AAH-54ABH.
5AB6
LD BC,4200H 01 00 42
Load BC with 4200H, the source buffer address.
5AB9
LD A,(549AH) 3A 9A 54
Load Register A with the source disk number from 549AH.
5ABC
PUSH HL E5
Save the source sector number.
5ABD
Call routine at 5B16H to perform the disk read.
5AC0
POP HL E1
Restore the source sector number.
5AC1
INC HL 23
Increment to next sector (assume forward direction).
5AC2
LD A,(5493H) 3A 93 54
Load secondary mode flags.
5AC5
BIT 7,A CB 7F
Test bit 7 (reverse direction).
5AC7
If forward direction, jump to 5ACBH.
5AC9
DEC HL 2B
Reverse - undo the increment.
5ACA
DEC HL 2B
Decrement to previous sector.
5ACB
LD (54A4H),HL 22 A4 54
Store the updated source sector number back to 54A4H-54A5H.
5ACE
POP BC C1
Restore BC (byte counters).
5ACF
POP DE D1
Restore DE (destination pointer).
5AD0
POP HL E1
Restore HL (source pointer).
5AD1
RET C9
Return to caller.

5AD2H - Write Destination Sector for Copy

This routine writes the destination sector to disk during copy operations. It saves all working registers, clears the search type flag at 5494H, calls the sector write routine, updates the destination sector number based on the copy direction (forward or reverse), and restores the registers before returning. The routine at 5AD6H contains self-modifying code where the search type flag value is stored.

5AD2
PUSH HL E5
Save Register pair HL (current source buffer pointer) onto the stack for later restoration.
5AD3
PUSH DE D5
Save Register pair DE (current destination buffer pointer) onto the stack.
5AD4
PUSH BC C5
Save Register pair BC (byte offset counters: B=source offset, C=destination offset) onto the stack.
5AD5
LD A,00H 3E 00
Load Register A with 00H. This value will be stored to clear the search type flag. Note: The 00H at address 5AD6H is modified at runtime by the code at 5B11H.
5AD7
LD (5494H),A 32 94 54
Store Register A (00H or modified value) into address 5494H, the search/copy type flag. This clears any previous search state.
5ADA
Call the write sector to disk routine at 5B29H. This writes the destination sector buffer at 5300H to the current destination sector.
5ADD
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current destination absolute sector number from addresses 54A2H-54A3H.
5AE0
INC HL 23
Increment HL to point to the next sector (assuming forward copy direction).
5AE1
LD A,(5493H) 3A 93 54
Load Register A with the secondary mode flags from address 5493H. Bit 7 indicates reverse copy direction.
5AE4
BIT 7,A CB 7F
Test bit 7 of the secondary mode flags. If set, copy is proceeding in reverse direction (high to low addresses).
5AE6
If bit 7 is clear (Z flag set, forward direction), jump to 5AEAH to store the incremented sector number.

Reverse copy direction - need to decrement sector number instead of increment.

5AE8
DEC HL 2B
Decrement HL to undo the earlier INC (now back to original sector number).
5AE9
DEC HL 2B
Decrement HL again to move to the previous sector (reverse direction).
5AEA
LD (54A2H),HL 22 A2 54
Store the updated sector number back to 54A2H-54A3H as the new current destination sector.
5AED
Jump to 5ACEH to restore BC, DE, HL from the stack and return to the caller.

5AEFH - Write and Read Next Destination Sector

This routine handles destination sector boundary crossing during copy operations. It first writes the current destination sector to disk, then reads the next destination sector into the buffer. This is called when the destination byte offset wraps around (crosses a 256-byte sector boundary).

5AEF
Call the write destination sector routine at 5AD2H. This writes the current 5300H buffer contents to disk and advances the destination sector number.

5AF2H - Read Destination Sector for Copy

This routine reads the destination sector into the buffer at 5300H. It sets up the FCB parameters (sector number, buffer address, disk number), performs the read via 5B42H and 6457H, checks for sector overflow beyond the disk's maximum sector, and handles self-modifying code to track the operation type.

5AF2
PUSH HL E5
Save Register pair HL (current source buffer pointer) onto the stack.
5AF3
PUSH DE D5
Save Register pair DE (current destination buffer pointer) onto the stack.
5AF4
PUSH BC C5
Save Register pair BC (byte offset counters) onto the stack.
5AF5
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current destination sector number from addresses 54A2H-54A3H.
5AF8
LD DE,(54A8H) ED 5B A8 54
Load Register pair DE with the maximum sector number for the destination disk from addresses 54A8H-54A9H.
5AFC
LD BC,5300H 01 00 53
Load Register pair BC with 5300H, the address of the destination sector buffer.
5AFF
LD A,(5499H) 3A 99 54
Load Register A with the current disk number from address 5499H. This is the destination disk for the copy operation.
5B02
Call the setup FCB parameters routine at 5B42H. This stores HL to 540AH (sector), BC to 5403H (buffer), and A to 5406H (disk).
5B05
OR A B7
Clear the carry flag by ORing A with itself. This prepares for the SBC instruction that follows.
5B06
SBC HL,DE ED 52
Subtract DE (maximum sector) from HL (current sector) with borrow. If HL ≥ DE, the carry flag is clear (NC condition).
5B08
If no carry (current sector ≥ maximum sector), call the sector overflow handler at 6593H. This handles attempts to access beyond the disk's capacity.
5B0B
Call the read sector from disk routine at 6457H. This reads the sector specified in the FCB into the buffer at 5300H.
5B0E
LD A,(5494H) 3A 94 54
Load Register A with the operation type flag from address 5494H. This tracks what type of operation is in progress.
5B11
LD (5AD6H),A 32 D6 5A
Store Register A into address 5AD6H. This is self-modifying code - it changes the immediate value in the "LD A,00H" instruction at 5AD5H, preserving the operation type across calls.
5B14
Jump to 5ACEH to restore BC, DE, HL from the stack and return to the caller.

5B16H - Read Sector with Overflow Check

This routine reads a sector from disk after setting up the FCB parameters. It checks for sector overflow (attempting to read beyond the disk's maximum sector) but only in standard disk mode (not in memory or file mode). Used by the copy operation to read source sectors.

5B16
Call the setup FCB parameters routine at 5B42H. This stores HL (sector number) to 540AH, BC (buffer address) to 5403H, and A (disk number) to 5406H.
5B19
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H. Bits 3 and 6 indicate memory mode and file open respectively.
5B1C
AND 48HAND 01001000 E6 48
Mask with 48H to isolate bits 3 (memory mode) and 6 (file open). If either is set, skip the overflow check.
5B1E
If NZ (either memory mode or file mode is active), jump to 5B26H to skip the sector overflow check.

Standard disk mode - check for sector overflow before reading.

5B20
OR A B7
Clear the carry flag by ORing A with itself. Prepares for the SBC instruction.
5B21
SBC HL,DE ED 52
Subtract DE (maximum sector from 54A8H) from HL (current sector from 54A2H). If HL ≥ DE, carry is clear.
5B23
If no carry (sector ≥ maximum), call the read overflow error handler at 658EH. This displays an error for attempting to read beyond disk capacity.
5B26
Jump to 6457H to read the sector from disk into the buffer and return to the caller.

5B29H - Write Sector with Overflow Check

This routine writes a sector to disk after setting up the FCB parameters. It loads the current sector number, maximum sector, buffer address, and disk number, then checks for overflow before calling the disk write routine at 6474H.

5B29
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current absolute sector number from addresses 54A2H-54A3H. This is the sector to be written.
5B2C
LD DE,(54A8H) ED 5B A8 54
Load Register pair DE with the maximum sector number from addresses 54A8H-54A9H. This is used for overflow checking.
5B30
LD BC,5300H 01 00 53
Load Register pair BC with 5300H, the address of the sector data buffer containing the data to be written.
5B33
LD A,(5499H) 3A 99 54
Load Register A with the current disk number from address 5499H.
5B36
Call the setup FCB parameters routine at 5B42H. This stores HL, BC, and A into the appropriate FCB fields.
5B39
OR A B7
Clear the carry flag by ORing A with itself. Prepares for the SBC instruction.
5B3A
SBC HL,DE ED 52
Subtract DE (maximum sector) from HL (current sector). If HL ≥ DE, carry is clear indicating overflow.
5B3C
If no carry (sector ≥ maximum), call the write overflow error handler at 6593H.
5B3F
Jump to 6474H to write the sector to disk and return to the caller.

5B42H - Setup FCB Parameters

This utility routine stores the sector number, buffer address, and disk number into the File Control Block (FCB) at 5400H. The FCB is used by NEWDOS/80 for all disk I/O operations. On entry: HL=sector number, BC=buffer address, A=disk number.

5B42
LD (540AH),HL 22 0A 54
Store Register pair HL into addresses 540AH-540BH. This is the sector number field in the FCB (offset 0AH from FCB base at 5400H).
5B45
LD (5403H),BC ED 43 03 54
Store Register pair BC into addresses 5403H-5404H. This is the DMA buffer address field in the FCB (offset 03H), pointing to where sector data will be read/written.
5B49
LD (5406H),A 32 06 54
Store Register A into address 5406H. This is the disk drive number field in the FCB (offset 06H), specifying which physical drive to access (0-3).
5B4C
RET C9
Return to the caller with FCB parameters now configured for the disk operation.

5B4DH - Move Command Setup (Source Specification)

This routine handles the setup for the Move command. It displays prompts for specifying the source disk and sector parameters. The Move command differs from Copy in that it operates on sectors within the same file or disk structure. The routine saves the source parameters for later use when specifying the destination.

5B4D
Load Register pair HL with 6D21H, the address of the "MOVE FROM" prompt string in the message table.
5B50
Call the display prompt routine at 6224H. This displays "MOVE FROM" and positions the cursor for input.
5B53
Load Register pair HL with 6D0BH, the address of the "DISK" prompt string.
5B56
Call the display prompt and get input routine at 678FH. This displays "DISK" and waits for the user to enter a disk number.
5B59
If carry flag is set (invalid input or error), jump back to 5B53H to re-prompt for the disk number. [LOOP]
5B5B
LD A,(5406H) 3A 06 54
Load Register A with the disk number from FCB offset 06H at address 5406H. This was stored by the input parsing routine.
5B5E
LD (549AH),A 32 9A 54
Store the disk number into address 549AH as the saved source disk number for the move operation.
5B61
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current absolute sector number from addresses 54A2H-54A3H.
5B64
LD (54A4H),HL 22 A4 54
Store the sector number into addresses 54A4H-54A5H as the saved source sector number.
5B67
LD HL,(54A8H) 2A A8 54
Load Register pair HL with the maximum sector number for this disk from addresses 54A8H-54A9H.
5B6A
LD (54AAH),HL 22 AA 54
Store the maximum sector into addresses 54AAH-54ABH as the saved source maximum sector.

5B6DH - Move Command Setup (Destination Specification)

This section prompts for the destination disk for the move operation. After validating the input, it calculates the transfer parameters and handles reverse direction if specified.

5B6D
Load Register pair HL with 6D0EH, the address of the "TO DISK" prompt string.
5B70
Call the display prompt and get input routine at 678FH. This displays "TO DISK" and waits for destination disk number input.
5B73
If carry flag is set (invalid input), jump back to 5B6DH to re-prompt. [LOOP]
5B75
Call routine at 66DCH to validate and process the destination disk parameters.
5B78
LD BC,0000H 01 00 00
Load Register pair BC with 0000H. This initializes the byte offset to zero (start at beginning of sectors).
5B7B
LD DE,(54ACH) ED 5B AC 54
Load Register pair DE with the remaining byte count from addresses 54ACH-54ADH. This is the total number of bytes to transfer.
5B7F
Call routine at 6111H to calculate transfer size and validate the operation parameters.
5B82
LD A,(5493H) 3A 93 54
Load Register A with the secondary mode flags from address 5493H.
5B85
BIT 7,A CB 7F
Test bit 7 of the secondary mode flags. Bit 7 indicates reverse direction for the move operation.
5B87
If bit 7 is clear (Z flag set, forward direction), jump to 5BBBH to proceed with forward move.

Reverse direction move - adjust starting positions to end of transfer range.

5B89
LD DE,(54ACH) ED 5B AC 54
Load Register pair DE with the byte count from 54ACH-54ADH again.
5B8D
DEC DE 1B
Decrement DE by 1 to get the offset to the last byte (count - 1).
5B8E
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current destination sector from 54A2H-54A3H.
5B91
ADD HL,DE 19
Add the byte offset (DE) to the sector (HL). This calculates the ending sector for reverse transfer.
5B92
LD (54A2H),HL 22 A2 54
Store the ending sector back to 54A2H-54A3H as the new starting point for reverse move.
5B95
LD HL,(54A4H) 2A A4 54
Load Register pair HL with the saved source sector from 54A4H-54A5H.
5B98
ADD HL,DE 19
Add the byte offset (DE) to the source sector (HL). This calculates the source ending sector.
5B99
LD (54A4H),HL 22 A4 54
Store the ending sector back to 54A4H-54A5H as the new source starting point.
5B9C
Jump to 5BBBH to continue with the move operation.

5B9EH - Zeroize/Fill Command Setup

This routine handles the Zeroize (or Fill) command setup. It displays the appropriate prompt and collects input for specifying the range of sectors to fill with zeros or a specified byte value.

5B9E
Load Register pair HL with 6D1AH, the address of the "ZEROIZE" prompt string in the message table.
5BA1
Call the display prompt routine at 6224H. This displays "ZEROIZE" and positions for input.
5BA4
Jump to 5BB3H to continue with sector input prompts.

5BA6H - Purge Command Setup

This routine handles the Purge command which securely erases sectors by overwriting them. It checks for a special option flag and sets the purge mode if specified.

5BA6
Load Register pair HL with 6D81H, the address of a purge option prompt string.
5BA9
Call routine at 6231H to display the prompt and check response. Returns Z flag if user selected the default option.
5BAC
If Z flag is set (default option selected), jump to 5BB3H to continue with standard input.
5BAE
LD HL,5493H 21 93 54
Load Register pair HL with 5493H, the address of the secondary mode flags.
5BB1
SET 5,(HL) CB EE
Set bit 5 of the secondary mode flags at (HL). Bit 5 indicates purge mode (multiple overwrite passes for secure erasure).

5BB3H - Sector Range Input Loop

This routine collects the sector range input for zeroize/purge operations. It loops until valid input is received, then processes the disk parameters.

5BB3
Call routine at 6792H to get sector range input from the user. This prompts for starting and ending sectors.
5BB6
If carry flag is set (invalid input or error), jump back to 5BB3H to re-prompt. [LOOP]
5BB8
Call routine at 66DCH to validate and process the disk parameters for the operation.

5BBBH - Zeroize/Purge/Move Main Loop Setup

This is the main setup and dispatch point for the zeroize, purge, and move operations. It determines which disk and sector to operate on based on the mode flags, then reads the sector into the buffer.

5BBB
LD A,(5492H) 3A 92 54
Load Register A with the tertiary mode flags from address 5492H.
5BBE
BIT 5,A CB 6F
Test bit 5 of the tertiary mode flags. Bit 5 indicates whether to use source or destination parameters.
5BC0
LD A,(5499H) 3A 99 54
Load Register A with the current disk number from address 5499H.
5BC3
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current destination sector from addresses 54A2H-54A3H.
5BC6
LD DE,(54A8H) ED 5B A8 54
Load Register pair DE with the maximum sector number from addresses 54A8H-54A9H.
5BCA
If Z flag is set (bit 5 was clear, use destination), jump to 5BD6H with current values.

Bit 5 was set - use saved source parameters instead of destination.

5BCC
LD A,(549AH) 3A 9A 54
Load Register A with the saved source disk number from address 549AH.
5BCF
LD HL,(54A4H) 2A A4 54
Load Register pair HL with the saved source sector from addresses 54A4H-54A5H.
5BD2
LD DE,(54AAH) ED 5B AA 54
Load Register pair DE with the saved source maximum sector from addresses 54AAH-54ABH.
5BD6
LD BC,5300H 01 00 53
Load Register pair BC with 5300H, the address of the sector data buffer.
5BD9
Call the read sector with overflow check routine at 5B16H. This reads the current sector into the buffer at 5300H.
5BDC
If NZ flag (read error occurred), jump to 5C30H to advance to next sector and retry.
5BDE
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
5BE1
BIT 1,A CB 4F
Test bit 1 of the primary mode flags. Bit 1 indicates printer output mode.
5BE3
If bit 1 is clear (no printer output), jump to 5BECH to continue with the operation.

Printer mode - output the sector to the printer.

5BE5
LD C,10H 0E 10
Load Register C with 10H (16 decimal). This specifies 16 lines per sector for printer output (16 lines × 16 bytes = 256 bytes).
5BE7
Call the printer output routine at 613AH. This prints the sector contents in hex dump format.
5BEA
Jump to 5C30H to advance to the next sector.

5BECH - Check Operation Mode and Execute

This section determines what operation to perform based on the mode flags. It handles verify mode, purge mode, and zeroize mode differently.

5BEC
LD A,(5492H) 3A 92 54
Load Register A with the tertiary mode flags from address 5492H.
5BEF
BIT 7,A CB 7F
Test bit 7 of the tertiary mode flags. Bit 7 indicates verify mode (check for specific pattern).
5BF1
If bit 7 is clear (not verify mode), jump to 5C1AH to check for zeroize/purge mode.

Verify mode - check for BREAK key and search for pattern.

5BF3
LD A,(3840H) 3A 40 38
Load Register A from address 3840H, the keyboard matrix address for the BREAK key row.
5BF6
AND 08HAND 00001000 E6 08
Mask with 08H to isolate the BREAK key bit.
5BF8
If NZ (BREAK key pressed), jump to 65C6H to abort the operation and return to command loop.
5BFB
LD A,(5494H) 3A 94 54
Load Register A with the search/operation type flag from address 5494H.
5BFE
CP 50H FE 50
Compare Register A with 50H (ASCII P). This checks if it's a pattern search operation.
5C00
If not pattern search (NZ), jump to 5C30H to advance to next sector.
5C02
LD A,(5493H) 3A 93 54
Load Register A with the secondary mode flags from address 5493H.
5C05
BIT 5,A CB 6F
Test bit 5 of the secondary mode flags. Bit 5 indicates a match was found in this sector.
5C07
If bit 5 is clear (no match found), jump to 5C30H to try next sector.

Pattern match found - display the result message.

5C09
Call routine at 65D0H to prepare the display for showing the result.
5C0C
Load Register pair HL with 6EB8H, the address of the "FOUND" message string.
5C0F
Call the display string routine at 6245H to show "FOUND".
5C12
Load Register pair HL with 6DD5H, the address of a location details message showing where the pattern was found.
5C15
Call routine at 6345H to display the location details and wait for user acknowledgment.
5C18
Jump to 5C30H to advance to the next sector.

5C1AH - Zeroize/Purge Sector Execution

This section performs the actual zeroize or purge operation on the current sector. For purge mode, it sets bit 5 indicating multiple passes. It fills the sector buffer with zeros and writes it to disk.

5C1A
BIT 5,A CB 6F
Test bit 5 of Register A (tertiary mode flags loaded at 5BECH). Bit 5 indicates purge mode.
5C1C
If NZ (purge mode active), jump to 5C2DH to skip the zero-fill since purge uses different values.
5C1E
BIT 6,A CB 77
Test bit 6 of Register A. Bit 6 indicates file mode.
5C20
If bit 6 is clear (Z flag, not file mode), call routine at 65AFH to display progress or status.

Fill the sector buffer with zeros.

5C23
LD HL,5300H 21 00 53
Load Register pair HL with 5300H, the starting address of the sector data buffer.
5C26
LD A,00H 3E 00
Load Register A with 00H, the fill byte value (zero).
5C28
LD B,A 47
Copy zero to Register B. B will be the loop counter (256 iterations, since B=0 causes DJNZ to execute 256 times).
5C29
LD (HL),A 77
Store zero (from Register A) into the buffer at address (HL).
5C2A
INC HL 23
Increment HL to point to the next byte in the buffer.
5C2B
Decrement B and jump to 5C29H if B is not zero. This fills 256 bytes with zeros. [LOOP]
5C2D
Call the write sector with overflow check routine at 5B29H. This writes the zeroed buffer to the disk.

5C30H - Advance to Next Sector

This routine advances to the next sector in the sequence (forward or reverse based on mode flags), decrements the remaining count, and loops back until all sectors are processed.

5C30
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current destination sector from addresses 54A2H-54A3H.
5C33
LD DE,(54A4H) ED 5B A4 54
Load Register pair DE with the current source sector from addresses 54A4H-54A5H.
5C37
INC HL 23
Increment HL to advance to the next destination sector (assuming forward direction).
5C38
INC DE 13
Increment DE to advance to the next source sector (assuming forward direction).
5C39
LD A,(5493H) 3A 93 54
Load Register A with the secondary mode flags from address 5493H.
5C3C
BIT 7,A CB 7F
Test bit 7 of the secondary mode flags. Bit 7 indicates reverse direction.
5C3E
If bit 7 is clear (Z flag set, forward direction), jump to 5C44H to store the incremented values.

Reverse direction - need to decrement instead of increment.

5C40
DEC HL 2B
Decrement HL to undo the earlier INC.
5C41
DEC HL 2B
Decrement HL again to move to the previous destination sector.
5C42
DEC DE 1B
Decrement DE to undo the earlier INC.
5C43
DEC DE 1B
Decrement DE again to move to the previous source sector.
5C44
LD (54A2H),HL 22 A2 54
Store the updated destination sector number back to 54A2H-54A3H.
5C47
LD (54A4H),DE ED 53 A4 54
Store the updated source sector number back to 54A4H-54A5H.
5C4B
LD HL,(54ACH) 2A AC 54
Load Register pair HL with the remaining sector count from addresses 54ACH-54ADH.
5C4E
DEC HL 2B
Decrement the remaining count by 1.
5C4F
LD (54ACH),HL 22 AC 54
Store the decremented count back to 54ACH-54ADH.
5C52
LD A,H 7C
Load Register A with the high byte of the remaining count (H).
5C53
OR L B5
OR with the low byte (L). Result is zero only if both H and L are zero.
5C54
If NZ (more sectors to process), jump back to 5BBBH to continue the operation. [MAIN LOOP]
5C57
All sectors processed. Jump to 65C6H to complete the operation and return to the command loop.

5C5AH - "MOD" Command Handler (Sector Modification)

This routine handles the MOD (Modify) command which allows direct editing of sector data at the byte/nibble level. It uses inline parameter verification to confirm "OD" was typed after "M", then enters an interactive editing mode where the user can modify individual bytes using hex input. The cursor position tracks location within the sector buffer.

5C5A
Call the inline parameter processor at 5803H. This verifies that the characters following "M" spell "OD" to confirm the MOD command.

The following bytes are inline data spelling "OD" (the "M" was already matched). A 00H byte terminates the keyword.

5C5D
DEFB 4FH 4F
Inline data: 4FH = ASCII O
5C5E
DEFB 44H 44
Inline data: 44H = ASCII D
5C5F
DEFB 00H 00
Inline data: 00H = terminator byte marking end of keyword

Execution continues here after 5803H validates "MOD" was typed. Now get the starting position.

5C60
Call the get hex address input routine at 5E19H. Returns the entered hex value in DE, carry set on error.
5C63
If carry flag is set (input error or cancel), jump to 56C1H to return to the display loop without making changes.
5C66
EX DE,HL EB
Exchange DE and HL. Now HL contains the starting byte offset within the sector where editing will begin.
5C67
LD B,00H 06 00
Clear Register B to 00H. B serves as the edit mode flags: bit 0 = high/low nibble toggle, bit 1 = sector boundary crossed flag.

5C69H - Modify Mode Main Loop

This is the main loop for the Modify mode. It stores the current edit position, reads a hex nibble from the user, and processes the input to update the sector buffer. The loop continues until the user presses ENTER to confirm or another key to exit.

5C69
LD (5497H),HL 22 97 54
Store Register pair HL into addresses 5497H-5498H. This saves the current edit position (byte offset within sector).
5C6C
PUSH HL E5
Save HL (current edit position) onto the stack for later restoration.
5C6D
LD C,L 4D
Copy the low byte of the position (L) into Register C. This is used for cursor positioning on screen.
5C6E
Call routine at 5FB2H to position the cursor at the edit location on the screen display.
5C71
LD A,0BFH 3E BF
Load Register A with 0BFH, the cursor character (inverse video block on TRS-80) to show the edit position.
5C73
Call routine at 5DBCH to display the cursor and get a keypress. Returns the key code in Register A.
5C76
POP HL E1
Restore HL (edit position) from the stack.
5C77
LD C,A 4F
Copy the key code from Register A into Register C for later processing.
5C78
Call routine at 686DH to convert the key to a hex nibble. Returns carry set if key is a valid hex digit (0-9, A-F), nibble value in A.
5C7B
If carry is clear (key is not a valid hex digit), jump to 5CAEH to check for control keys.

Valid hex digit entered - update the sector buffer with the new nibble value.

5C7D
BIT 1,B CB 48
Test bit 1 of Register B. Bit 1 is the sector boundary crossed flag, set when edit position wraps past 255.
5C7F
RES 1,B CB 88
Clear bit 1 of Register B (reset the boundary flag after checking).
5C81
If bit 1 was set (NZ, sector boundary crossed), jump to 5DA6H to handle sector overflow.

Determine which nibble (high or low) of the byte is being edited.

5C84
LD E,0F0H 1E F0
Load Register E with F0H, a mask to preserve the high nibble and clear the low nibble.
5C86
BIT 0,B CB 40
Test bit 0 of Register B. Bit 0 is the nibble toggle flag: 0=editing high nibble, 1=editing low nibble.
5C88
If bit 0 is set (NZ, editing low nibble), jump to 5C90H to use the current mask.

Editing high nibble - need to shift the input value left by 4 bits.

5C8A
LD E,0FH 1E 0F
Load Register E with 0FH, a mask to preserve the low nibble and clear the high nibble.
5C8C
RLCA 07
Rotate A left (shift the hex nibble value left by 1 bit position).
5C8D
RLCA 07
Rotate A left again (2 bits shifted).
5C8E
RLCA 07
Rotate A left again (3 bits shifted).
5C8F
RLCA 07
Rotate A left again (4 bits shifted). The nibble value is now in the high 4 bits of A.
5C90
LD C,A 4F
Copy the positioned nibble value from Register A into Register C.
5C91
PUSH HL E5
Save HL (edit position offset) onto the stack.
5C92
PUSH DE D5
Save DE (E contains the nibble mask) onto the stack.
5C93
LD DE,(5495H) ED 5B 95 54
Load Register pair DE with the current display position from addresses 5495H-5496H. This is the base offset for the buffer.
5C97
ADD HL,DE 19
Add the display position (DE) to the edit offset (HL). HL now points to the actual byte in the sector buffer.
5C98
POP DE D1
Restore DE (E contains the nibble mask).
5C99
LD A,(HL) 7E
Load Register A with the current byte value from the sector buffer at (HL).
5C9A
AND E A3
AND with the mask (E). This preserves the nibble we're NOT editing and clears the nibble we ARE editing.
5C9B
OR C B1
OR with the new nibble value (C). This inserts the new nibble into the correct position.
5C9C
LD (HL),A 77
Store the modified byte back into the sector buffer at (HL). The byte is now updated.
5C9D
POP HL E1
Restore HL (edit position offset).
5C9E
BIT 0,B CB 40
Test bit 0 of Register B (nibble toggle). Check if we just edited the low nibble.
5CA0
If Z (we edited the high nibble), jump to 5CA7H to toggle to low nibble.

We edited the low nibble - advance to the next byte.

5CA2
INC L 2C
Increment L to move to the next byte position.
5CA3
If NZ (L didn't wrap to 0), jump to 5CA7H to toggle nibble flag.
5CA5
SET 1,B CB C8
L wrapped to 0 (position went past 255). Set bit 1 of B as the sector boundary crossed flag.
5CA7
LD A,B 78
Load Register A with the current mode flags from Register B.
5CA8
XOR 01H EE 01
XOR with 01H to toggle bit 0 (switch between high and low nibble editing).
5CAA
LD B,A 47
Store the toggled flags back into Register B.
5CAB
Jump back to 5C69H to continue the edit loop. [MAIN LOOP]

5CAEH - Process Non-Hex Key Input

This section handles keypresses that are not valid hex digits. It checks for control keys like ENTER (confirm changes), SPACE/TAB (advance position), BACKSPACE (move back), and arrow keys (navigation).

5CAE
RES 1,B CB 88
Clear bit 1 of Register B (reset the sector boundary flag since we're processing a control key).
5CB0
LD A,C 79
Load Register A with the key code from Register C (saved earlier at 5C77H).
5CB1
CP 0DH FE 0D
Compare with 0DH (ASCII carriage return = ENTER key).
5CB3
If ENTER key pressed (Z flag), jump to 5D01H to confirm and save changes.
5CB6
CP 20H FE 20
Compare with 20H (ASCII space).
5CB8
If SPACE key pressed (Z flag), jump to 5CBEH to advance position.
5CBA
CP 09H FE 09
Compare with 09H (ASCII tab = TAB key on TRS-80 is right arrow).
5CBC
If not TAB, jump to 5CC7H to check other keys.

SPACE or TAB key - advance to next position.

5CBE
BIT 0,B CB 40
Test bit 0 of Register B (nibble toggle flag).
5CC0
If Z (on high nibble), jump to 5CA7H to just toggle to low nibble without advancing.
5CC2
INC L 2C
Increment L to advance to the next byte position.
5CC3
If NZ (didn't wrap), jump to 5CA7H to toggle nibble and continue.
5CC5
L wrapped past 255 - jump to 5CE1H to handle position overflow.

5CC7H - Check Backspace and Arrow Keys

This section handles the BACKSPACE key (move cursor backward) and arrow keys for navigation within the sector buffer.

5CC7
CP 08H FE 08
Compare with 08H (ASCII backspace = LEFT ARROW/BACKSPACE).
5CC9
If not BACKSPACE, jump to 5CD6H to check other keys.

BACKSPACE/LEFT ARROW - move cursor backward.

5CCB
BIT 0,B CB 40
Test bit 0 of Register B (nibble toggle flag).
5CCD
If NZ (on low nibble), jump to 5CA7H to toggle back to high nibble of same byte.
5CCF
INC L 2C
Increment L temporarily (this is a trick to test if L is 0).
5CD0
DEC L 2D
Decrement L back. If L was 0, Z flag is now set.
5CD1
If Z (L was 0, at start of buffer), jump to 5CABH to stay at position 0.
5CD3
DEC L 2D
Decrement L to move to the previous byte position.
5CD4
Jump to 5CA7H to toggle nibble (will be on low nibble of previous byte) and continue.

5CD6H - Check Down Arrow Key

This section handles the DOWN ARROW key to move the cursor down by one line (2 bytes in hex display).

5CD6
LD E,02H 1E 02
Load Register E with 02H, the step size for vertical movement (2 bytes = 1 line in hex display).
5CD8
CP 19H FE 19
Compare with 19H (TRS-80 DOWN ARROW key code).
5CDA
If not DOWN ARROW, jump to 5CE7H to check other keys.

DOWN ARROW - move cursor down by 2 bytes.

5CDC
LD A,L 7D
Load Register A with the current position (L).
5CDD
ADD A,E 83
Add the step size (E=2) to move down one line.
5CDE
LD L,A 6F
Store the new position back into L.
5CDF
If no carry (didn't overflow past 255), jump to 5CABH to continue editing.

Position overflowed past 255 - set to end of buffer.

5CE1
LD B,01H 06 01
Load Register B with 01H, setting bit 0 (nibble toggle) so we're on the low nibble.
5CE3
LD L,0FFH 2E FF
Load Register L with FFH (255), the last byte position in the buffer.
5CE5
Jump to 5CABH to continue editing at position 255.

5CE7H - Check Up Arrow and Other Navigation Keys

This section handles UP ARROW, LINE FEED (down by 16 bytes), and begins checking for special command keys.

5CE7
CP 18H FE 18
Compare with 18H (TRS-80 UP ARROW key code).
5CE9
If UP ARROW pressed (Z flag), jump to 5CF7H to move cursor up.
5CEB
LD E,10H 1E 10
Load Register E with 10H (16 decimal), the step size for large movement (16 bytes = one display row).
5CED
CP 0AH FE 0A
Compare with 0AH (ASCII line feed = move down by larger step).
5CEF
If LINE FEED pressed (Z flag), jump to 5CDCH to add 16 to position.
5CF1
LD C,L 4D
Copy L (current position) into Register C for preservation.
5CF2
CP 5BH FE 5B
Compare with 5BH (ASCII [ left bracket).
5CF4
If not [, jump to 5D34H to check for other command keys (Q, Z, etc.).

UP ARROW or [ key - move cursor up by E bytes.

5CF7
LD A,L 7D
Load Register A with the current position (L).
5CF8
SUB E 93
Subtract the step size (E) to move up.
5CF9
LD L,A 6F
Store the new position back into L.
5CFA
If no carry (didn't underflow below 0), jump to 5CABH to continue editing.

Position underflowed below 0 - set to start of buffer.

5CFC
LD B,00H 06 00
Clear Register B (clear nibble toggle, so we're on high nibble).
5CFE
LD L,B 68
Load L with B (00H), the first byte position in the buffer.
5CFF
Jump to 5CABH to continue editing at position 0.

5D01H - Confirm and Save Sector Changes

This routine handles the ENTER key press during Modify mode. It prompts the user to confirm whether to write the changes to disk. If in alternate display mode (bit 5 set), it skips the confirmation. Otherwise, it displays "WRITE CHANGES (Y/N)?" and waits for user response. If 'Y' is pressed, the sector is written to disk.

5D01
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
5D04
BIT 5,A CB 6F
Test bit 5 of the mode flags. Bit 5 indicates alternate display mode.
5D06
If bit 5 is set (NZ, alternate mode), jump to 5D23H to skip confirmation and display completion message.

Standard mode - prompt for write confirmation.

5D08
PUSH HL E5
Save Register pair HL (current edit position) onto the stack.
5D09
PUSH BC C5
Save Register pair BC (mode flags and position) onto the stack.
5D0A
Load Register pair HL with 6DA2H, the address of the "WRITE CHANGES (Y/N)?" prompt string.
5D0D
Call the display string routine at 6245H to show the confirmation prompt.
5D10
Call the get single keypress routine at 620BH. Returns the key code in Register A.
5D13
POP BC C1
Restore Register pair BC from the stack.
5D14
POP HL E1
Restore Register pair HL from the stack.
5D15
CP 59H FE 59
Compare with 59H (ASCII Y for Yes).
5D17
If not 'Y' (NZ), user declined to save. Jump back to 5C69H to continue editing without writing.

User confirmed 'Y' - write the sector to disk.

5D1A
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current absolute sector number from addresses 54A2H-54A3H.
5D1D
LD (540AH),HL 22 0A 54
Store the sector number into the FCB sector field at 540AH-540BH.
5D20
Call the write sector to disk routine at 6474H. This writes the buffer at 5300H to the specified sector.

5D23H - Display Modification Complete Message

This routine displays a completion message after modifications have been made (or skipped). It shows "MODIFICATION COMPLETE" and waits for user acknowledgment before returning to the main display loop with a Re-read command.

5D23
Load Register pair HL with 6DC4H, the address of the "MODIFICATION COMPLETE" message string.
5D26
Call the display string routine at 6245H to show the completion message.
5D29
Load Register pair HL with 6DD5H, the address of a "PRESS ANY KEY" or status message.
5D2C
Call routine at 6345H to display message and wait for keypress.
5D2F
LD A,52H 3E 52
Load Register A with 52H (ASCII R for Re-read). This will cause the sector to be re-displayed with updated contents.
5D31
Jump to 5716H to process the R command and return to the main display loop.

5D34H - Check for Quit Command

This section checks if the user pressed Q to quit the Modify mode without saving. It also handles alternate mode differently, showing an "ABORTED" message.

5D34
CP 51H FE 51
Compare with 51H (ASCII Q for Quit).
5D36
If not Q (NZ), jump to 5D45H to check for other commands.

Q pressed - quit editing without saving.

5D38
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
5D3B
BIT 5,A CB 6F
Test bit 5 (alternate display mode).
5D3D
If bit 5 is set (NZ, alternate mode), jump to 5DA6H to handle quit in alternate mode.
5D40
Load Register pair HL with 6DC8H, the address of the "ABORTED" message string.
5D43
Jump to 5D26H to display the abort message and return to the display loop.

5D45H - Check for Zap Byte Command

This section checks for Z (zap/zero a byte) or A (set to alternate value) commands. These allow quickly setting a byte to 00H or another preset value.

5D45
LD C,00H 0E 00
Load Register C with 00H. This will be the fill value if Z (zero) is pressed.
5D47
CP 5AH FE 5A
Compare with 5AH (ASCII Z for Zero/Zap).
5D49
If Z pressed (Z flag), jump to 5D51H to fill the byte with 00H.
5D4B
INC C 0C
Increment C to 01H. This will be the fill value for the next check.
5D4C
CP 41H FE 41
Compare with 41H (ASCII A).
5D4E
If A pressed (Z flag), jump to 5D51H to fill the byte with 01H.
5D50
INC C 0C
Increment C to 02H for the next potential command check.

5D51H - Zap/Repeat Fill Command Processing

This routine processes the Zap (Z) or Repeat fill (R) command. It echoes the command character, gets additional parameters (end address and optionally fill value), validates the range, and fills the specified bytes. For Zap, it fills with 00H. For Repeat fill, it prompts for a fill value. The syntax is "ZT<end>" for Zap or "RT<end>,<value>" for Repeat fill.

5D51
PUSH HL E5
Save Register pair HL (current edit position) onto the stack.
5D52
PUSH BC C5
Save Register pair BC (B=mode flags, C=command type: 0=Zap, 1=Repeat) onto the stack.
5D53
Call the echo character to buffer routine at 5DFDH. This displays the command letter on screen.
5D56
Call the get character routine at 5DF7H to get the next input character.
5D59
CP 54H FE 54
Compare with 54H (ASCII T for "TO", indicating end address follows).
5D5B
If not T (NZ), jump to 5DAAH to display error message.
5D5E
Call the get hex value routine at 5E33H to get the end address of the fill range. Returns value in DE.
5D61
If carry set (input error), jump to 5DAAH to display error.
5D63
PUSH DE D5
Save Register pair DE (end address from hex input) onto the stack.
5D64
LD E,00H 1E 00
Initialize Register E with 00H. E will hold the fill value (default is 00H for Zap command).
5D66
DEC C 0D
Decrement C (command type). If C was 0 (Zap), it becomes FFH (NZ). If C was 1 (Repeat), it becomes 0 (Z).
5D67
If NZ (was Zap command), jump to 5D72H to skip fill value input and use default 00H.

Repeat fill command - need to get the fill value from user.

5D69
CP 2CH FE 2C
Compare last input character (A) with 2CH (ASCII comma ,). Comma separates end address from fill value.
5D6B
If not comma (NZ), jump to 5DA9H to handle error (missing fill value).
5D6D
Call the get hex value routine to get the fill value. Returns value in E (low byte of DE).
5D70
If carry set (input error), jump to 5DA9H to handle error.
5D72
CP 0DH FE 0D
Compare last character with 0DH (ASCII carriage return = ENTER). Input should end with ENTER.
5D74
If not ENTER (NZ), jump to 5DAAH to display error (invalid termination).
5D76
LD A,E 7B
Load Register A with the fill value from Register E.
5D77
LD (5D9CH),A 32 9C 5D
Store the fill value into address 5D9CH. This is self-modifying code that sets the fill byte used at 5D9BH.
5D7A
POP DE D1
Restore Register pair DE (end address) from the stack.
5D7B
POP BC C1
Restore Register pair BC (B=mode flags, C=command type) from the stack.
5D7C
POP HL E1
Restore Register pair HL (start position) from the stack.
5D7D
LD A,E 7B
Load Register A with E (low byte of end address).
5D7E
SUB L 95
Subtract L (start position) from A (end position). Result is the byte count - 1.
5D7F
LD C,A 4F
Copy the difference to Register C. C will be the fill byte counter.
5D80
If carry set (end < start, invalid range), jump to 5DA6H to display error.
5D83
INC C 0C
Increment C to get the actual byte count (difference + 1).
5D84
EX DE,HL EB
Exchange DE and HL. Now DE=start position, HL=end position.
5D85
LD HL,(5495H) 2A 95 54
Load Register pair HL with the sector buffer base address from 5495H-5496H.
5D88
ADD HL,DE 19
Add the start offset (DE) to the buffer base. HL now points to the first byte to fill in the sector buffer.
5D89
BIT 0,B CB 40
Test bit 0 of Register B (nibble toggle flag: 0=high nibble, 1=low nibble).
5D8B
If Z (starting on high nibble), jump to 5D9AH to fill complete bytes.

Starting on low nibble - need to preserve the high nibble of the first byte.

5D8D
LD A,(HL) 7E
Load Register A with the current byte from the buffer at (HL).
5D8E
AND 0F0HAND 11110000 E6 F0
Mask with F0H to preserve the high nibble and clear the low nibble.
5D90
LD (HL),A 77
Store the byte with cleared low nibble back to the buffer.
5D91
LD A,(5D9CH) 3A 9C 5D
Load Register A with the fill value from address 5D9CH.
5D94
AND 0FHAND 00001111 E6 0F
Mask with 0FH to isolate the low nibble of the fill value.
5D96
OR (HL) B6
OR with the current byte (preserved high nibble). This combines the fill nibble with the preserved nibble.
5D97
EX DE,HL EB
Exchange DE and HL. DE now points to the buffer, HL holds the position offset.
5D98
Jump to 5D9DH to store the combined byte and continue filling.

5D9AH - Fill Bytes Loop

This is the main fill loop that writes the fill value to consecutive bytes in the sector buffer. It continues until the byte count in C reaches zero, then returns to the modify mode.

5D9A
EX DE,HL EB
Exchange DE and HL. DE now points to the buffer position, HL holds the offset counter.
5D9B
LD A,00H 3E 00
Load Register A with 00H. Note: The 00H at address 5D9CH is self-modified by 5D77H to contain the actual fill value.
5D9D
LD (DE),A 12
Store the fill value (A) into the sector buffer at address (DE).
5D9E
INC DE 13
Increment DE to point to the next byte in the buffer.
5D9F
INC L 2C
Increment L (position offset counter) to track progress.
5DA0
DEC C 0D
Decrement C (remaining byte count).
5DA1
If C is not zero (NZ, more bytes to fill), loop back to 5D9BH. [FILL LOOP]
5DA3
All bytes filled. Jump to 5C67H to return to Modify mode with updated position.

5DA6H - Error Handler and Recovery

This routine handles errors and boundary conditions during Modify mode. It displays an error message, waits for the user to press * to acknowledge, then returns to the edit loop. This is called when the user tries to edit beyond sector boundaries or when an invalid operation is attempted.

5DA6
PUSH HL E5
Save Register pair HL (current edit position) onto the stack.
5DA7
PUSH BC C5
Save Register pair BC (mode flags and counter) onto the stack.
5DA8
PUSH AF F5
Save Register A and flags onto the stack.
5DA9
POP AF F1
Restore Register A and flags from the stack (effectively discards the saved value).
5DAA
Load Register pair HL with 6DDBH, the address of the error message string (likely "ERROR - PRESS * TO CONTINUE").
5DAD
Call routine at 6255H to display the error message on screen.
5DB0
Call the get single keypress routine at 620BH. Returns the key code in Register A.
5DB3
CP 2AH FE 2A
Compare with 2AH (ASCII * asterisk).
5DB5
If not * (NZ), loop back to 5DB0H to wait for the correct key. [LOOP]
5DB7
POP BC C1
Restore Register pair BC from the stack.
5DB8
POP HL E1
Restore Register pair HL from the stack.
5DB9
Jump back to 5C69H to resume the edit loop.

5DBCH - Display Cursor and Wait for Keypress

This routine displays a cursor character at the current screen position, waits for a keypress (with cursor blinking), and returns the key code. It calculates the screen address from the buffer position and handles cursor blinking by alternating the character display. Entry: A=cursor character, B=mode flags, C=buffer position. Exit: A=key code pressed.

5DBC
LD (5DE1H),A 32 E1 5D
Store Register A (cursor character 0BFH) into address 5DE1H. This is self-modifying code that sets the cursor character used in the display routine.
5DBF
LD H,00H 26 00
Clear Register H to zero. H will be the high byte of the screen row offset.
5DC1
LD D,H 54
Copy H (00H) to Register D.
5DC2
LD E,H 5C
Copy H (00H) to Register E. DE is now 0000H.
5DC3
LD A,C 79
Load Register A with the buffer position from Register C.
5DC4
RRA 1F
Rotate A right through carry. This divides by 2 and puts the low bit into carry.
5DC5
RL E CB 13
Rotate E left through carry. This captures the low bit of the position (nibble selector).
5DC7
AND 07HAND 00000111 E6 07
Mask with 07H to get the column within the hex display (0-7).
5DC9
LD L,A 6F
Copy the column to Register L.
5DCA
ADD A,A 87
Double A (column × 2).
5DCB
ADD A,E 83
Add E (nibble offset) to get column × 2 + nibble.
5DCC
ADD A,A 87
Double A again ((column × 2 + nibble) × 2).
5DCD
ADD A,L 85
Add original column. This calculates the screen column offset.
5DCE
LD E,A 5F
Store the column offset in Register E.
5DCF
BIT 0,B CB 40
Test bit 0 of Register B (nibble toggle: 0=high, 1=low).
5DD1
If Z (on high nibble), jump to 5DD4H.
5DD3
INC E 1C
On low nibble - increment E to point to the second hex digit.
5DD4
LD A,C 79
Load Register A with the buffer position (C).
5DD5
AND 0F0HAND 11110000 E6 F0
Mask with F0H to get the row number × 16.
5DD7
LD L,A 6F
Store row × 16 in Register L.
5DD8
ADD HL,HL 29
Double HL (row × 32).
5DD9
ADD HL,HL 29
Double HL again (row × 64 = screen row offset since each row is 64 characters).
5DDA
ADD HL,DE 19
Add the column offset (DE) to get the total screen offset.
5DDB
LD DE,3C08H 11 08 3C
Load DE with 3C08H. This is the base screen address plus an offset for the hex display area (3C00H + 08H).
5DDE
ADD HL,DE 19
Add the base address to get the final screen memory address.
5DDF
LD C,(HL) 4E
Load Register C with the original character at the screen position (to restore after cursor blink).
5DE0
LD (HL),00H 36 00
Store 00H at the screen position. Note: The 00H at 5DE1H is modified by the code at 5DBCH to be the cursor character.
5DE2
Call routine at 5DECH to wait for keypress with timeout. Returns Z if timeout, NZ with key in A.
5DE5
LD (HL),C 71
Restore the original character at the screen position.
5DE6
If Z (timeout, no key), call 5DECH again to continue waiting (cursor blink cycle).
5DE9
If still Z (still no key), jump back to 5DE0H to show cursor again. [BLINK LOOP]
5DEB
RET C9
Return with the key code in Register A.

5DECH - Wait for Keypress with Timeout

This routine waits for a keypress with a timeout counter. If no key is pressed before the timeout expires, it returns with Z flag set (for cursor blinking). If a key is pressed, it returns with NZ and the key code in A.

5DEC
LD D,00H 16 00
Load Register D with 00H. D will be the timeout counter (256 iterations).
5DEE
Call routine at 6205H to scan keyboard. Returns A=key code if pressed (NZ), A=0 if no key (Z).
5DF1
OR A B7
Test if A is zero (no key pressed).
5DF2
RET NZ C0
If NZ (key was pressed), return immediately with key code in A.
5DF3
DEC D 15
Decrement the timeout counter D.
5DF4
If D is not zero (NZ), loop back to 5DEEH to check keyboard again. [TIMEOUT LOOP]
5DF6
RET C9
Timeout expired. Return with Z flag set (A=0).

5DF7H - Get Character from Input

This routine gets a character from user input. It waits for a keypress, checks if it's a printable character (ASCII 20H or higher), and optionally echoes it to a buffer. If the key is below 20H (control character), it returns with carry set.

5DF7
Call the get single keypress routine at 620BH. Returns the key code in Register A.
5DFA
CP 20H FE 20
Compare with 20H (ASCII space). Characters below 20H are control characters.
5DFC
RET C D8
If carry set (character < 20H, control character), return immediately with carry flag set.

5DFDH - Echo Character to Command Buffer

This routine stores a character into the command line echo buffer area. It calculates the buffer position, checks for overflow, and stores the character. The buffer is located in video memory at 4000H.

5DFD
PUSH HL E5
Save Register pair HL onto the stack.
5DFE
PUSH DE D5
Save Register pair DE onto the stack.
5DFF
LD HL,(54B0H) 2A B0 54
Load Register pair HL with the current buffer pointer from addresses 54B0H-54B1H.
5E02
LD DE,4000H 11 00 40
Load DE with 4000H, the start of video memory (used as boundary check).
5E05
OR A B7
Clear carry flag for subtraction.
5E06
SBC HL,DE ED 52
Subtract 4000H from the buffer pointer. If result is negative, buffer is valid.
5E08
If carry (buffer pointer < 4000H, invalid), jump to 5E0DH.
5E0A
XOR A AF
Clear A (buffer overflow - don't store character).
5E0B
Jump to 5E16H to skip storing and return.
5E0D
ADD HL,DE 19
Add 4000H back to restore the original pointer value.
5E0E
LD (HL),A 77
Store the character (A) into the buffer at (HL).
5E0F
LD DE,0040H 11 40 00
Load DE with 0040H (64 decimal), the screen width.
5E12
ADD HL,DE 19
Add 64 to advance to the next row position (for vertical display of typed characters).
5E13
LD (54B0H),HL 22 B0 54
Store the updated buffer pointer back to 54B0H-54B1H.
5E16
POP DE D1
Restore Register pair DE from the stack.
5E17
POP HL E1
Restore Register pair HL from the stack.
5E18
RET C9
Return to the caller.

5E19H - Get Hex Address Input

This routine gets a hexadecimal address value from user input. It first gets a character, then parses up to 4 hex digits into a 16-bit value in Register pair DE. If the input is invalid or the user presses a control key, carry is set on return. Used by the MOD command to get the starting edit position.

5E19
Call the get character from input routine at 5DF7H. Returns the first character in A, carry set if control character.

5E1CH - Parse Hex Digits into DE

This routine parses hexadecimal digits from user input into a 16-bit value. It accumulates digits into Register pair DE, shifting previous digits left by 4 bits for each new digit entered. Entry: Called after first character is in A. Exit: DE=parsed value, carry set on error.

5E1C
PUSH HL E5
Save Register pair HL onto the stack.
5E1D
PUSH BC C5
Save Register pair BC onto the stack.
5E1E
LD DE,0000H 11 00 00
Initialize Register pair DE to 0000H. DE will accumulate the parsed hex value.
5E21
Call routine at 685AH to convert character to hex nibble and accumulate. This shifts DE left 4 bits and adds the new nibble.
5E24
If carry set (invalid hex digit), jump to 5E46H to return with error.
5E26
Call the get next character routine to get another input character.
5E29
Call routine at 685AH to convert and accumulate the second hex digit.
5E2C
Jump to 5E46H to restore registers and return.

5E2EH - Get Hex Byte with Validation

This routine gets a hex byte value from input with additional validation. It calls the parse routine and then checks for proper termination. Used for getting search patterns and other byte values.

5E2E
Call the parse hex digits routine at 5E1CH to get a hex value into DE.
5E31
Jump to 5E36H to check result and return.

5E33H - Get Hex Value with Full Parsing

This routine gets a complete hex value from input, handling up to 4 digits. It's the main entry point for hex input when a full address or value is expected.

5E33
Call the get hex address input routine at 5E19H. This gets the first character and begins parsing.
5E36
RET C D8
If carry is set (error in input), return immediately to caller with error indication.

5E37H - Check Input Termination

This routine checks if the input was properly terminated with ENTER (0DH) or a comma (2CH). It's called after parsing to validate that the user completed the input correctly. Returns: Z flag if terminated with ENTER, carry clear if comma (more input follows), carry set if invalid terminator.

5E37
PUSH HL E5
Save Register pair HL onto the stack.
5E38
PUSH BC C5
Save Register pair BC onto the stack.
5E39
Call the get character routine to get the terminating character.
5E3C
CP 0DH FE 0D
Compare with 0DH (ASCII carriage return = ENTER).
5E3E
If ENTER (Z flag), jump to 5E46H to return success with Z flag set.
5E40
CP 2CH FE 2C
Compare with 2CH (ASCII comma ,).
5E42
SCF 37
Set the carry flag (assume invalid terminator).
5E43
If not comma (NZ), jump to 5E46H with carry set (error).
5E45
OR A B7
Clear carry flag (comma is valid, more input expected). Also clears Z flag.
5E46
POP BC C1
Restore Register pair BC from the stack.
5E47
POP HL E1
Restore Register pair HL from the stack.
5E48
RET C9
Return to caller. Z flag set if ENTER, carry clear if comma, carry set if invalid.

5E49H - Password Entry and Checksum Calculation

This routine handles password entry for protected operations. It displays a password prompt, collects up to 8 characters of input, clears the entry area on screen with spaces, and then calculates a 16-bit checksum of the entered password combined with stored data. The checksum algorithm uses a complex series of rotations and XOR operations to create a hash value. This is used for disk copy protection verification.

5E49
Load Register pair HL with 6EE6H, the address of the password prompt string in the message table.
5E4C
Call routine at 634EH to display the password prompt and collect input. Returns B=number of characters entered.
5E4F
LD C,B 48
Copy B (character count) into Register C.
5E50
LD B,00H 06 00
Clear Register B to 00H. BC now holds the character count as a 16-bit value.
5E52
ADD HL,BC 09
Add BC to HL to point past the entered characters to the start of the fill area.
5E53
LD B,08H 06 08
Load Register B with 08H (8 decimal). This is the number of positions to clear with spaces.
5E55
LD (HL),20H 36 20
Store 20H (ASCII space) at address (HL) to clear the password display area.
5E57
INC HL 23
Increment HL to point to the next position.
5E58
Decrement B and jump back to 5E55H if not zero. [CLEAR LOOP] Clears 8 characters.

Password display cleared. Now calculate the checksum hash.

5E5A
LD HL,5447H 21 47 54
Load Register pair HL with 5447H, pointing to the password buffer in the data area.
5E5D
PUSH DE D5
Save Register pair DE onto the stack.
5E5E
PUSH BC C5
Save Register pair BC onto the stack.
5E5F
LD DE,0FFFFH 11 FF FF
Initialize Register pair DE with FFFFH. DE will accumulate the checksum hash value.
5E62
LD B,08H 06 08
Load Register B with 08H (8 decimal). Process 8 characters for the checksum.

5E64H - Checksum Calculation Loop

This is the main checksum calculation loop. It processes each byte of the password buffer through a complex series of rotations and XOR operations to generate a pseudo-random hash. The algorithm is designed to make it difficult to reverse-engineer the expected password from the stored checksum.

5E64
PUSH BC C5
Save the loop counter (B) onto the stack.
5E65
LD A,E 7B
Load Register A with the low byte of the hash (E).
5E66
AND 07HAND 00000111 E6 07
Mask with 07H to isolate the lowest 3 bits of the hash.
5E68
LD C,A 4F
Copy the masked value to Register C for later use.
5E69
LD A,E 7B
Load Register A with E again (low byte of hash).
5E6A
RLCA 07
Rotate A left through carry (1 bit).
5E6B
RLCA 07
Rotate A left again (2 bits total).
5E6C
RLCA 07
Rotate A left again (3 bits total).
5E6D
XOR C A9
XOR A with C (the low 3 bits). This mixes the rotated and unrotated values.
5E6E
RLCA 07
Rotate A left again (4 bits from original position).
5E6F
LD C,A 4F
Save the intermediate result in C.
5E70
AND 0F0HAND 11110000 E6 F0
Mask with F0H to isolate the high nibble.
5E72
LD B,A 47
Save the high nibble in B.
5E73
LD A,C 79
Reload A with the intermediate value from C.
5E74
RLCA 07
Rotate A left (5 bits from original).
5E75
AND 1FHAND 00011111 E6 1F
Mask with 1FH to isolate the low 5 bits.
5E77
XOR B A8
XOR with B (the saved high nibble). More bit mixing.
5E78
XOR D AA
XOR with D (the high byte of the running hash).
5E79
LD E,A 5F
Store the result as the new low byte of the hash (E).
5E7A
LD A,C 79
Reload A with the intermediate value from C.
5E7B
AND 0FHAND 00001111 E6 0F
Mask with 0FH to isolate the low nibble.
5E7D
LD B,A 47
Save the low nibble in B.
5E7E
LD A,C 79
Reload A with the intermediate value.
5E7F
RLCA 07
Rotate A left (1 bit).
5E80
RLCA 07
Rotate A left (2 bits).
5E81
RLCA 07
Rotate A left (3 bits).
5E82
RLCA 07
Rotate A left (4 bits = nibble swap).
5E83
XOR B A8
XOR with B (the saved low nibble). This mixes the swapped nibbles.
5E84
POP BC C1
Restore the loop counter from the stack.
5E85
XOR (HL) AE
XOR with the current password character from the buffer at (HL).
5E86
LD D,A 57
Store the result as the new high byte of the hash (D).
5E87
LD (HL),20H 36 20
Store 20H (space) to clear the password character from the buffer for security.
5E89
DEC HL 2B
Decrement HL to point to the previous character (processing right to left).
5E8A
Decrement B and jump back to 5E64H if not zero. [CHECKSUM LOOP]

5E8CH - Display Checksum Result

After calculating the checksum, this section converts the 16-bit hash value in DE to hexadecimal ASCII and displays it. The checksum is shown as a 4-digit hex number.

5E8C
INC HL 23
Increment HL to point back to the start of the output area.
5E8D
LD B,04H 06 04
Load Register B with 04H. This is the number of hex digits to display (4 digits for 16-bit value).
5E8F
LD A,E 7B
Load Register A with E (low byte of checksum hash).
5E90
Call routine at 6674H to convert byte to 2 hex ASCII characters and store at (HL). HL is advanced.
5E93
LD A,D 7A
Load Register A with D (high byte of checksum hash).
5E94
Call routine at 6674H to convert the high byte to hex ASCII.
5E97
LD HL,5440H 21 40 54
Load Register pair HL with 5440H, the address of the password/checksum display buffer.
5E9A
Call routine at 62BAH to display the buffer contents on screen.
5E9D
Jump to 65C3H to return to the command loop.

5EA0H - Filespec Entry and Validation

This routine handles filename input with validation. It displays a prompt for the filespec, collects up to 8 characters for the filename, pads with spaces if needed, then collects up to 3 characters for the extension. It calculates a checksum of the entered filespec for validation purposes.

5EA0
LD B,08H 06 08
Load Register B with 08H (8 decimal). This is the maximum filename length (8 characters).
5EA2
Load Register pair HL with 6D60H, the address of the filename prompt string.
5EA5
Call routine at 6339H to display prompt and get filename input. Returns B=characters remaining (8 - entered).
5EA8
LD C,B 48
Copy B (remaining characters) to Register C.
5EA9
LD B,00H 06 00
Clear Register B. BC now holds the offset to the end of entered filename.
5EAB
ADD HL,BC 09
Add BC to HL to point past the entered filename characters.
5EAC
LD A,09H 3E 09
Load Register A with 09H (9 decimal = 8 + 1 for the slash separator).
5EAE
SUB C 91
Subtract C (remaining) from 9. Result is number of padding spaces needed.
5EAF
LD B,A 47
Copy the padding count to Register B for the fill loop.
5EB0
LD (HL),20H 36 20
Store 20H (ASCII space) at (HL) to pad the filename.
5EB2
INC HL 23
Increment HL to point to the next position.
5EB3
Decrement B and loop back to 5EB0H if not zero. [PAD FILENAME LOOP]
5EB5
EX DE,HL EB
Exchange DE and HL. DE now points past the padded filename.
5EB6
Load Register pair HL with 6D64H, the address of the extension prompt string (or separator).
5EB9
LD B,03H 06 03
Load Register B with 03H (3 decimal). This is the maximum extension length.
5EBB
DEC DE 1B
Decrement DE to point to the position for the extension.
5EBC
Call routine at 633CH to get extension input. Returns B=characters remaining.
5EBF
LD C,B 48
Copy B (remaining) to Register C.
5EC0
LD B,00H 06 00
Clear Register B. BC now holds remaining extension characters.
5EC2
ADD HL,BC 09
Add BC to HL to point past the entered extension.
5EC3
LD A,04H 3E 04
Load Register A with 04H (4 = 3 + 1 for terminator).
5EC5
SUB C 91
Subtract C from 4. Result is number of padding spaces needed for extension.
5EC6
LD B,A 47
Copy the padding count to B.
5EC7
LD (HL),20H 36 20
Store 20H (space) at (HL) to pad the extension.
5EC9
INC HL 23
Increment HL to next position.
5ECA
Decrement B and loop if not zero. [PAD EXTENSION LOOP]

5ECCH - Filespec Checksum Calculation

This section calculates a checksum of the entered filespec for validation. It XORs all 11 characters (8 filename + 3 extension) together with rotation to create a hash value.

5ECC
LD HL,5440H 21 40 54
Load Register pair HL with 5440H, the address of the filespec buffer.
5ECF
LD B,0BH 06 0B
Load Register B with 0BH (11 decimal). Process 11 characters (8 filename + 3 extension).
5ED1
XOR A AF
Clear Register A to 00H. A will accumulate the checksum.
5ED2
XOR (HL) AE
XOR Register A with the character at (HL). This adds the character to the checksum.
5ED3
INC HL 23
Increment HL to point to the next character.
5ED4
RLCA 07
Rotate A left. This spreads the bits for better hash distribution.
5ED5
Decrement B and loop if not zero. [CHECKSUM LOOP]
5ED7
If NZ (checksum is not zero), jump to 5EDAH.
5ED9
INC A 3C
If checksum was zero, increment A to 01H (avoid zero checksum).
5EDA
POP HL E1
Restore Register pair HL from the stack.
5EDB
LD B,02H 06 02
Load Register B with 02H. This specifies 2 hex digits to display.
5EDD
Jump to 5E94H to convert and display the checksum as 2 hex digits.

5EDFH - Raw Track Read Command Setup

This routine sets up and initiates a raw track read operation for disk analysis. It prompts for track/sector parameters, sets the file mode flag in the secondary mode flags at 5493H, configures the FCB (File Control Block) at 5400H with the maximum sector count and starting sector, then calls NEWDOS/80's directory search routine. This allows SUPERZAP to read raw track data directly from the floppy disk controller for analyzing disk format and copy protection.

5EDF
Call routine at 6792H to prompt for and get sector parameters from the user. This routine displays prompts and parses the user's input for track/sector selection.
5EE2
If carry flag is set (invalid input or user error), jump back to 5EDFH to re-prompt for valid parameters. [INPUT VALIDATION LOOP]
5EE4
LD HL,5493H 21 93 54
Load Register pair HL with 5493H, the address of the secondary mode flags byte. This byte tracks various operation modes.
5EE7
SET 6,(HL) CB F6
Set bit 6 of the byte at (HL). Bit 6 of 5493H indicates raw track/file mode is active, which changes how sector I/O is performed.
5EE9
LD HL,(54A8H) 2A A8 54
Load Register pair HL with the 16-bit value at addresses 54A8H-54A9H. This is the maximum sector number for the current disk, representing the disk capacity limit.
5EEC
LD (540CH),HL 22 0C 54
Store HL into addresses 540CH-540DH. This is FCB offset 0CH (the record count/extent field), setting the maximum sectors to read.
5EEF
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the 16-bit value at addresses 54A2H-54A3H. This is the current absolute sector number that was entered or calculated.
5EF2
LD (540AH),HL 22 0A 54
Store HL into addresses 540AH-540BH. This is FCB offset 0AH (the sector number field), setting the starting sector for the read operation.
5EF5
LD DE,5400H 11 00 54
Load Register pair DE with 5400H, the base address of the File Control Block (FCB). NEWDOS/80 disk routines use this FCB for all file and sector operations.
5EF8
Call NEWDOS/80 routine at 4436H. This is the @FSPEC (File Specification) or directory search routine. It searches the directory for the file matching the FCB. Returns Z flag if found, error code in A if not found.
5EFB
If Z flag is set (file/sector found successfully), jump to 5F05H to continue with the raw track read operation.

File not found or error occurred - check if it's a recoverable error.

5EFD
CP 03H FE 03
Compare the error code in Register A with 03H. Error codes 00H-02H are fatal disk errors (drive not ready, write protect, etc.).
5EFF
If carry set (error code < 03H, fatal error), jump to 5F63H to display the error and abort the operation.
5F01
CP 08H FE 08
Compare the error code with 08H. Error codes 03H-07H are recoverable file errors (file not found, directory full, etc.).
5F03
If no carry (error code >= 08H, fatal hardware error), jump to 5F63H to display the error and abort.

5F05H - Raw Track Read Initialization

This routine initializes the WD1771 floppy disk controller for a raw track read operation. It saves the current disk select byte from the DOS workspace at 4309H, disables interrupts for precise timing, calls the drive select routine, then restores the select byte. Raw track reads require uninterrupted execution to capture every byte as it streams off the disk.

5F05
LD A,(4309H) 3A 09 43
Load Register A with the byte at 4309H. This is the NEWDOS/80 disk select byte which contains the currently selected drive number and density settings.
5F08
PUSH AF F5
Push AF (disk select byte and flags) onto the stack. This saves the current disk controller state for restoration after the raw read completes.
5F09
DI F3
Disable all maskable interrupts. This is critical - the raw track read loop must execute without any interruption to capture data at disk speed (250 kbps for single density).
5F0A
Call routine at 67B5H to select the disk drive and seek to the target track. This prepares the FDC hardware for the read operation.
5F0D
POP AF F1
Pop the saved disk select byte back into Register A.
5F0E
LD (4309H),A 32 09 43
Restore the original disk select byte to 4309H. This ensures DOS workspace remains consistent even though we're doing direct hardware access.
5F11
Call routine at 5FA2H to output the disk select byte to the hardware at port 37E1H, physically selecting the drive.
5F14
Call routine at 5FA9H to perform a short timing delay and read the FDC status register. This ensures the controller is ready.
5F17
LD HL,37ECH 21 EC 37
Load Register pair HL with 37ECH. This is the WD1771 FDC command/status register address (memory-mapped I/O on TRS-80).
5F1A
LD (HL),0E4H 36 E4
Write E4H to the FDC command register at (HL). E4H is the Read Track command (E0H base + 04H for head load delay). This starts the raw track read operation.
5F1C
LD DE,37EFH 11 EF 37
Load Register pair DE with 37EFH. This is the WD1771 FDC data register address where raw bytes will be read from.
5F1F
LD BC,7000H 01 00 70
Load Register pair BC with 7000H. This is the destination buffer address where captured raw track data will be stored. The buffer extends from 7000H upward.
5F22
Call the timing delay routine again to wait for the Read Track command to initialize and data to start arriving.
5F25
NOP 00
No operation. This provides a small additional timing delay for FDC synchronization before entering the tight capture loop.

5F26H - Wait for FDC Busy

This short loop waits for the FDC to transition from "just busy" (status=01H) to "busy with data ready" (status has DRQ bit set). This synchronizes the capture loop with the actual data stream from the disk.

5F26
LD A,01H 3E 01
Load Register A with 01H. This is the BUSY bit mask - when status equals exactly 01H, the FDC is busy but no data is available yet.
5F28
CP (HL) BE
Compare A (01H) with the FDC status register at (HL=37ECH). Z flag set if status is exactly 01H (busy, no data).
5F29
If Z (status still 01H, waiting for data), loop back to 5F28H. [BUSY WAIT LOOP] Exits when DRQ or other status bits become set.

5F2BH - Raw Track Data Capture Loop

This is the critical high-speed data capture loop. It reads raw bytes from the FDC data register at 37EFH as fast as possible and stores them into the buffer at 7000H. The loop must complete each iteration within the byte time of the disk (32 microseconds for single density) or data will be lost. Multiple DRQ checks handle timing variations.

5F2B
LD A,(DE) 1A
Load Register A with the byte from (DE=37EFH), the FDC data register. This reads one raw byte from the disk data stream.
5F2C
LD (BC),A 02
Store the captured byte into the buffer at address (BC). BC starts at 7000H and increments with each byte.
5F2D
INC BC 03
Increment BC to point to the next buffer location for the next captured byte.
5F2E
BIT 1,(HL) CB 4E
Test bit 1 of the FDC status at (HL=37ECH). Bit 1 is DRQ (Data Request) - set when another byte is ready to read.
5F30
If NZ (DRQ is set, more data ready), jump back to 5F2BH to capture the next byte immediately. [DATA CAPTURE LOOP]
5F32
BIT 1,(HL) CB 4E
Test DRQ again - handles case where data arrives between the previous test and the branch.
5F34
If DRQ now set, jump to capture the byte.
5F36
BIT 1,(HL) CB 4E
Test DRQ a third time - provides additional timing margin for slow data arrival.
5F38
If DRQ set, jump to capture.
5F3A
BIT 0,(HL) CB 46
Test bit 0 of FDC status. Bit 0 is BUSY - cleared when the Read Track operation completes.
5F3C
If Z (BUSY clear, operation complete), jump to 5F46H to finish and process results.
5F3E
BIT 1,(HL) CB 4E
Still busy - check DRQ one more time in case data arrived during the BUSY check.
5F40
If DRQ set, jump to capture the data.
5F42
BIT 7,(HL) CB 7E
Test bit 7 of FDC status. Bit 7 is NOT READY - set if the drive becomes not ready (door open, disk removed).
5F44
If Z (drive still ready), jump back to 5F2EH to continue checking for data. Otherwise fall through to completion.

5F46H - Track Read Completion and Error Check

This section handles completion of the raw track read. It checks for CRC errors in the captured data, marks error locations in the buffer, sends a Force Interrupt command to reset the FDC, re-enables interrupts, and saves the final buffer position for later analysis.

5F46
LD A,(4311H) 3A 11 43
Load Register A from address 4311H. This is a secondary disk controller status location that may contain additional error information.
5F49
RLCA 07
Rotate A left. This moves bit 7 (error flag) into the carry flag for testing.
5F4A
If no carry (bit 7 was clear, no error), jump to 5F50H to continue without error marking.

Error detected during read - mark the error location in the buffer.

5F4C
DEC DE 1B
Decrement DE (was pointing to FDC data register 37EFH). This is repurposed to point to the last buffer location.
5F4D
LD A,80H 3E 80
Load Register A with 80H. This is an error marker byte that will be visible when analyzing the captured data.
5F4F
LD (DE),A 12
Store the error marker at (DE) to flag where the error occurred in the data stream.
5F50
LD A,(HL) 7E
Load Register A with the final FDC status from (HL=37ECH). This captures any error bits before resetting the controller.
5F51
LD (HL),0D0H 36 D0
Write D0H to the FDC command register at (HL). D0H is the Force Interrupt command which immediately terminates any operation and resets the controller to idle state.
5F53
EI FB
Enable interrupts. The critical timing section is complete, normal system operation can resume.

5F54H - Save Buffer Position and Check Errors

This section saves the final buffer position, extracts error bits from the FDC status, and determines whether to display results or an error message. The buffer position indicates how many bytes were captured from the raw track read.

5F54
LD (5F7CH),BC ED 43 7C 5F
Store Register pair BC into addresses 5F7CH-5F7DH. BC contains the final buffer pointer (end of captured data). This address minus 7000H gives the byte count.
5F58
AND 0F8HAND 11111000 E6 F8
AND Register A (FDC status from 5F50H) with F8H. This isolates error bits 3-7 (CRC error, seek error, lost data, write fault, not ready).
5F5A
LD C,A 4F
Copy the masked error bits to Register C for further analysis.
5F5B
If Z (no error bits set), jump to 5F69H to display successful results.

Error bits present - determine which specific error occurred.

5F5D
XOR A AF
Clear Register A to 00H. A will be used as an error code counter.
5F5E
INC A 3C
Increment A to count which error bit is set (A=1 for bit 3, A=2 for bit 4, etc.).
5F5F
RRC C CB 09
Rotate Register C right through carry. This shifts the error bits, putting the lowest set bit into carry.
5F61
If no carry (this bit was 0), loop back to 5F5EH to check the next bit. [ERROR BIT SCAN LOOP] Exits when carry is set (found the error bit).

5F63H - Display Disk Error

This routine displays a disk error message based on the error code in Register A, then returns to the error handler to allow the user to retry or abort.

5F63
Call routine at 64BCH to display the disk error message. The error code in A selects which message to display from the error message table.
5F66
Jump to 6582H, the error handler. This routine displays "PRESS ANY KEY" and returns to the main command loop.

5F69H - Display Track Read Results

This routine displays the results of a successful raw track read operation. It shows the buffer start address (7000H), the buffer end address (from 5F7CH), allowing the user to see how much data was captured.

5F69
Load Register pair HL with 6EFBH, the address of a results label string (such as "START=" or "FROM ").
5F6C
Call routine at 6255H to display the label string at (HL) on the screen.
5F6F
LD DE,7000H 11 00 70
Load Register pair DE with 7000H, the buffer start address where raw track data was stored.
5F72
Call routine at 665BH to convert DE to hex ASCII and display the start address.
5F75
Load Register pair HL with 6EA7H, the address of another label string (such as "END=" or "TO ").
5F78
Call routine at 6255H to display the end address label.
5F7B
LD DE,0000H 11 00 00
Load Register pair DE with 0000H. Note: The 0000H at address 5F7CH is self-modified by the code at 5F54H to contain the actual end address.
5F7E
DEC DE 1B
Decrement DE. This adjusts from "next byte to write" to "last byte written" for display purposes.
5F7F
Call routine at 665BH to convert and display the end address.
5F82
Jump to 65C3H to return to the main command loop.

5F85H - FDC Status Check with Retry

This routine checks the FDC status and handles busy/not ready conditions with automatic retry. It's used during drive initialization to wait for the drive to become ready.

5F85
Call the timing delay and status read routine at 5FA9H. Returns with FDC status in Register A.
5F88
RRCA 0F
Rotate A right through carry. This puts bit 0 (BUSY) into the carry flag.
5F89
If carry set (FDC is busy), jump to 5F8DH to handle the busy condition.
5F8B
XOR A AF
Clear Register A to 00H, indicating ready status (not busy).
5F8C
RET C9
Return with A=00H indicating FDC is ready.

5F8DH - Handle FDC Busy Condition

This section handles the case where the FDC is busy. It checks if the controller is simply completing an operation or if it needs to be reset with a Force Interrupt command.

5F8D
RLCA 07
Rotate A left to restore the original bit position.
5F8E
RLCA 07
Rotate A left again. Now bit 7 (NOT READY) is in carry.
5F8F
If carry set (drive not ready), jump to 5F96H to send Force Interrupt command.
5F91
Call routine at 5FA2H to re-select the drive by outputting the select byte to the hardware.
5F94
Jump back to 5F85H to retry the status check. [RETRY LOOP]
5F96
LD A,0D0H 3E D0
Load Register A with D0H, the Force Interrupt command for the WD1771 FDC.
5F98
LD (37ECH),A 32 EC 37
Write the Force Interrupt command to the FDC command register at 37ECH. This aborts any pending operation and resets the controller.
5F9B
Jump back to 5F85H to check status again after the reset.

5F9DH - Check FDC Not Ready

This short routine checks if the FDC is reporting "not ready" status, which indicates the drive door is open or no disk is inserted.

5F9D
LD A,(37ECH) 3A EC 37
Load Register A with the current FDC status from the command/status register at 37ECH.
5FA0
RLCA 07
Rotate A left. This puts bit 7 (NOT READY) into the carry flag.
5FA1
RET C D8
If carry set (drive not ready), return immediately with carry flag indicating the error condition.

5FA2H - Output Drive Select Byte

This routine outputs the current drive select byte to the disk controller hardware. It reads the select byte from the DOS workspace at 4309H and writes it to the drive select latch at 37E1H.

5FA2
LD A,(4309H) 3A 09 43
Load Register A with the drive select byte from NEWDOS/80 workspace at 4309H. This byte contains drive number (bits 0-1), side select, and motor on bits.
5FA5
LD (37E1H),A 32 E1 37
Write the select byte to address 37E1H, the drive select latch (memory-mapped I/O). This physically selects the drive and turns on the motor.
5FA8
RET C9
Return to the caller.

5FA9H - Timing Delay and Read FDC Status

This routine provides a short timing delay (approximately 30 microseconds) then reads the FDC status register. The delay allows the FDC time to update its status after a command or operation.

5FA9
LD A,06H 3E 06
Load Register A with 06H. This is the delay loop counter - 6 iterations provides approximately 30 microseconds of delay.
5FAB
DEC A 3D
Decrement the delay counter in Register A.
5FAC
If A is not zero (NZ), loop back to 5FABH. [TIMING DELAY LOOP] Each iteration takes approximately 5 microseconds.
5FAE
LD A,(37ECH) 3A EC 37
Load Register A with the FDC status register contents from address 37ECH.
5FB1
RET C9
Return with the FDC status in Register A.

5FB2H - Initialize Sector Display Screen

This routine initializes the screen for displaying sector contents. It sets up the cursor position pointer at 54B0H, clears the command line area, and prepares the video memory starting at 3C00H for the hex/ASCII dump display. The display shows 16 rows of 16 bytes each (256 bytes total per sector).

5FB2
LD HL,3C06H 21 06 3C
Load Register pair HL with 3C06H. This is the screen position for command input (row 0, column 6 in video memory which starts at 3C00H).
5FB5
LD (54B0H),HL 22 B0 54
Store HL into addresses 54B0H-54B1H. This saves the current cursor position for the command echo buffer.
5FB8
Call routine at 62A7H to clear the command line area on screen, preparing for new input.
5FBB
LD HL,3C00H 21 00 3C
Load Register pair HL with 3C00H, the start of TRS-80 video memory. This is where the sector display will begin.
5FBE
LD DE,(5495H) ED 5B 95 54
Load Register pair DE with the 16-bit value at addresses 5495H-5496H. This is the display offset into the sector buffer (5300H + offset = current display position).
5FC2
LD A,10H 3E 10
Load Register A with 10H (16 decimal). This is the row counter - 16 rows of 16 bytes each will be displayed.
5FC4
PUSH BC C5
Save Register pair BC onto the stack. BC holds the current edit position from the MOD command.
5FC5
EX AF,AF' 08
Exchange AF with the alternate AF' register. This preserves the row counter (A=10H) in AF' while using A for other purposes.

5FC6H - Format Display Row Address

This section calculates and displays the address prefix for each row of the hex dump. It shows the offset within the sector at the left margin.

5FC6
INC L 2C
Increment L (low byte of screen position). Advance past the first 4 character positions.
5FC7
INC L 2C
Increment L again (2 positions).
5FC8
INC L 2C
Increment L again (3 positions).
5FC9
INC L 2C
Increment L again (4 positions). HL now points to column 4 of the current row for the hex data area.
5FCA
LD A,(5495H) 3A 95 54
Load Register A with the low byte of the display offset from 5495H.
5FCD
NEG ED 44
Negate A (A = 0 - A). This calculates the two's complement for offset calculation.
5FCF
ADD A,E 83
Add E (low byte of current data pointer) to A. This calculates the relative offset within the current display page.
5FD0
LD C,A 4F
Copy the calculated offset to Register C for later use when formatting the address display.
5FD1
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
5FD4
AND 28HAND 00101000 E6 28
Mask with 28H to isolate bits 3 and 5. Bit 3 = memory mode, bit 5 = alternate display mode.
5FD6
If Z (neither memory mode nor alternate mode), jump to 5FE0H to skip the high byte display.

Memory or alternate mode - display the high byte of the address.

5FD8
DEC L 2D
Decrement L to move screen position back 2 characters for the high byte.
5FD9
DEC L 2D
Decrement L again (2 positions back).
5FDA
LD A,(54B5H) 3A B5 54
Load Register A with the byte at 54B5H. This is the high byte of the display address (page number in memory mode).
5FDD
Call routine at 61EFH to convert byte in A to 2 hex ASCII characters and store at (HL), advancing HL by 2.
5FE0
LD A,C 79
Load Register A with C (the low byte offset calculated earlier).
5FE1
Call routine at 61EFH to convert the low byte offset to hex ASCII and display it.
5FE4
LD C,08H 0E 08
Load Register C with 08H (8 decimal). This is the byte pair counter - 8 pairs of bytes per row (16 bytes total).
5FE6
INC L 2C
Increment L to add a space between address and hex data.
5FE7
INC L 2C
Increment L again (2-character space).

5FE8H - Format Hex Bytes and ASCII Display

This is the main formatting loop that displays each row of the hex dump. For each row, it shows 8 pairs of hex bytes in the left portion of the screen, and the corresponding ASCII characters in the right portion. Non-printable characters are displayed as periods.

5FE8
PUSH HL E5
Save HL (current hex display position) onto the stack.
5FE9
LD A,L 7D
Load Register A with L (low byte of screen position).
5FEA
ADD 28H C6 28
Add 28H (40 decimal) to A. This calculates the position for the ASCII display area (40 columns to the right).
5FEC
LD L,A 6F
Store the ASCII display position back into L.
5FED
EX (SP),HL E3
Exchange HL with the top of stack. Now HL=hex position (from stack), ASCII position is saved on stack.
5FEE
LD B,02H 06 02
Load Register B with 02H. This is the bytes per pair counter - 2 bytes are displayed with a space between pairs.
5FF0
LD A,(DE) 1A
Load Register A with the byte from (DE), the sector data buffer. DE points to the current byte being displayed.
5FF1
Call routine at 61EFH to convert the byte to 2 hex ASCII characters and store at (HL) on screen.

Now determine if this byte is printable ASCII for the right-side display.

5FF4
PUSH BC C5
Save BC (counters) onto the stack.
5FF5
LD C,3FH 0E 3F
Load Register C with 3FH (63 decimal). This is the default printable range limit (characters 21H-5FH are printable in standard ASCII).
5FF7
LD A,(436CH) 3A 6C 43
Load Register A from address 436CH. This is a system flag byte that may indicate lowercase support.
5FFA
BIT 4,A CB 67
Test bit 4 of the system flags. Bit 4 indicates lowercase display enabled.
5FFC
If Z (no lowercase support), jump to 6000H with C=3FH.
5FFE
LD C,5FH 0E 5F
Lowercase enabled - load C with 5FH (95 decimal). Extends printable range to include lowercase letters (21H-7FH).
6000
LD A,(DE) 1A
Reload Register A with the byte from (DE) for the printability check.
6001
SUB 21H D6 21
Subtract 21H (first printable character) from A. If A was < 21H, this will set carry.
6003
CP C B9
Compare A with C (printable range limit). If A ≥ C (non-printable high character), carry is clear.
6004
POP BC C1
Restore BC (counters) from the stack.
6005
LD A,(DE) 1A
Reload Register A with the original byte from (DE) for potential display.
6006
INC DE 13
Increment DE to point to the next byte in the sector buffer.
6007
If carry set (character is printable), jump to 600BH to display the actual character.
6009
LD A,2EH 3E 2E
Character not printable - load A with 2EH (ASCII . period) as a placeholder.
600B
EX (SP),HL E3
Exchange HL with top of stack. Now HL = ASCII display position.
600C
LD (HL),A 77
Store the ASCII character (or period) at the screen position (HL).
600D
INC HL 23
Increment HL to the next ASCII display position.
600E
EX (SP),HL E3
Exchange back - HL = hex position, ASCII position saved on stack.
600F
Decrement B and jump back to 5FF0H if not zero. [BYTE PAIR LOOP] Processes 2 bytes per iteration.
6011
INC HL 23
Increment HL to add a space between byte pairs in the hex display.
6012
DEC C 0D
Decrement C (byte pair counter).
6013
If C not zero (more pairs to display), jump back to 5FEEH. [PAIR LOOP]
6015
POP HL E1
Pop the ASCII position off the stack (no longer needed).
6016
EX AF,AF' 08
Exchange AF with AF' to retrieve the row counter.
6017
DEC A 3D
Decrement the row counter (A).
6018
If A not zero (more rows to display), jump back to 5FC5H. [ROW LOOP]

601AH - Check Display Mode and Show Status

After displaying the 16 rows of hex/ASCII dump, this section checks the display mode flags and adds status information at the bottom of the screen. It shows disk number, track, sector, and granule information depending on the active mode (file mode, memory mode, or standard disk mode).

601A
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
601D
BIT 5,A CB 6F
Test bit 5 of the mode flags. Bit 5 indicates alternate display mode (raw display without status).
601F
If bit 5 is set (NZ, alternate mode), jump to 60EAH to skip status display and return.
6022
BIT 3,A CB 5F
Test bit 3 of the mode flags. Bit 3 indicates memory mode (viewing RAM/ROM instead of disk).
6024
If bit 3 is clear (Z, not memory mode), jump to 6032H to display standard disk status.

Memory mode - display "M" indicator at start of first line.

6026
LD HL,3C00H 21 00 3C
Load Register pair HL with 3C00H, the start of video memory (first character position).
6029
LD DE,444DH 11 4D 44
Load Register pair DE with 444DH. E=4DH (ASCII M), D=44H (ASCII D). This spells "MD" for Memory Display.
602C
LD (HL),E 73
Store E (ASCII M) at the screen position (HL=3C00H).
602D
INC HL 23
Increment HL to the next screen position.
602E
LD (HL),D 72
Store D (ASCII D) at position 3C01H, completing the "MD" indicator.
602F
Jump to 60EAH to restore BC and return (no further status needed for memory mode).

6032H - Display Disk Number Status

This section displays the disk drive number on the status line at the top of the screen. It sets up the display parameters and calls the status formatting routine.

6032
LD BC,68FEH 01 FE 68
Load Register pair BC with 68FEH. B=68H points to the format string table, C=FEH is the format code for disk number display.
6035
LD DE,3C00H 11 00 3C
Load Register pair DE with 3C00H, the screen position for the disk number display (top-left corner).
6038
LD A,(5406H) 3A 06 54
Load Register A with the current disk number from FCB offset 06H at address 5406H. This is 0-3 for drives 0-3.
603B
LD L,A 6F
Copy the disk number to Register L.
603C
LD H,00H 26 00
Clear Register H. HL now contains the disk number as a 16-bit value (0-3).
603E
Call routine at 60ECH to format and display the disk number using the format string at B and code in C.

6041H - Check for File Mode Status

This section loads the current sector number and checks if file mode is active. In file mode, additional information about granules and file position is displayed. Otherwise, track and sector information is shown.

6041
LD HL,(54A2H) 2A A2 54
Load Register pair HL with the current absolute sector number from addresses 54A2H-54A3H.
6044
PUSH HL E5
Save the sector number onto the stack for later use in status display.
6045
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from 5491H.
6048
BIT 6,A CB 77
Test bit 6 of the mode flags. Bit 6 indicates file mode is active (viewing a file rather than raw disk).
604A
If bit 6 is clear (Z, not file mode), jump to 60ACH to display standard track/sector status.

604CH - Calculate File Position for Status

When in file mode, this section calculates the current position within the file by traversing the granule allocation chain. It determines which granule contains the current sector and calculates the offset within the file.

604C
LD A,(549DH) 3A 9D 54
Load Register A with the byte at 549DH. This is the sectors per granule value for the current disk format.
604F
Call routine at 6896H to convert sectors per granule to a bit mask or multiplier for position calculations.
6052
PUSH AF F5
Save the conversion result (AF) onto the stack.
6053
EX DE,HL EB
Exchange DE and HL. DE now contains the screen position from earlier, HL is free for calculations.
6054
LD BC,0000H 01 00 00
Initialize Register pair BC to 0000H. BC will accumulate the file byte offset.
6057
LD A,08H 3E 08
Load Register A with 08H (8 decimal). This is the granule chain loop limit (maximum 8 granule pointers to check per extent).
6059
LD HL,540EH 21 0E 54
Load Register pair HL with 540EH, pointing to the FCB granule chain at offset 0EH. This contains up to 8 granule numbers for the file.
605C
EX AF,AF' 08
Exchange AF with AF' to save the loop counter while using A for data.

605DH - Traverse Granule Chain

This loop traverses the granule allocation chain in the FCB to calculate the file position. It checks each granule entry to see if the current sector falls within that granule, accumulating the byte offset as it goes.

605D
LD A,(HL) 7E
Load Register A with the granule number from the FCB chain at (HL).
605E
CP 0FEH FE FE
Compare with FEH. Granule values >= FEH indicate end of file or deleted granule.
6060
If no carry (granule >= FEH, end of chain), jump to 6089H to finish position calculation.
6063
INC HL 23
Increment HL to point to the sector count byte for this granule entry.
6064
LD A,(HL) 7E
Load Register A with the sector count for this granule.
6065
EX DE,HL EB
Exchange DE and HL. HL now has the working value, DE points to FCB.
6066
OR A B7
Clear carry flag by ORing A with itself (also tests if A is zero).
6067
SBC HL,BC ED 42
Subtract the accumulated count (BC) from the current sector (HL) with borrow.
6069
If carry (current sector < accumulated count), jump to 6089H - sector is in a previous granule.
606B
INC H 24
Increment H to test if HL high byte is non-zero.
606C
DEC H 25
Decrement H back. Z flag is set only if H was (and still is) zero.
606D
If NZ (H > 0, more than 256 sectors remaining), jump to 6074H to continue accumulating.
606F
AND 1FHAND 00011111 E6 1F
Mask the sector count with 1FH (31 decimal) to get sectors in last granule.
6071
CP L BD
Compare sector count with L (low byte of remaining sectors).
6072
If no carry (sector count >= remaining), jump to 608DH - found the correct granule.
6074
ADD HL,BC 09
Add BC back to HL to restore the original sector number.
6075
INC A 3C
Increment A (sector count from this granule entry).
6076
ADD A,C 81
Add C (low byte of accumulated count) to A.
6077
LD C,A 4F
Store the new low byte back into C.
6078
If no carry from addition, jump to 607BH.
607A
INC B 04
Carry occurred - increment B (high byte of accumulated count).
607B
EX DE,HL EB
Exchange back - HL points to FCB, DE has sector value.
607C
INC HL 23
Increment HL to point to the next granule entry in the FCB chain.
607D
EX AF,AF' 08
Exchange AF with AF' to get the loop counter.
607E
CP 05H FE 05
Compare loop counter with 05H. At entry 5, there's a 2-byte pointer to the next extent.
6080
If not at entry 5, jump to 6086H to continue normally.
6082
LD C,(HL) 4E
Load C with the low byte of the extent pointer.
6083
INC HL 23
Increment HL past the low byte.
6084
LD B,(HL) 46
Load B with the high byte of the extent pointer.
6085
INC HL 23
Increment HL to point to the next granule entry.
6086
DEC A 3D
Decrement the loop counter.
6087
If counter not zero, jump back to 605CH to process the next granule entry. [GRANULE CHAIN LOOP]

6089H - Complete File Position Calculation

This section completes the file position calculation and proceeds to display the track/sector status line.

6089
POP AF F1
Pop AF from the stack (the sectors-per-granule conversion result saved at 6052H).
608A
Jump to 60B5H to continue with track/sector display.

608DH - Calculate Exact File Offset

When the correct granule is found, this section calculates the exact byte offset within the file based on the granule position and sector offset.

608D
LD A,(DE) 1A
Load Register A with the byte from (DE), the granule entry sector count.
608E
AND 0E0HAND 11100000 E6 E0
Mask with E0H to isolate the high 3 bits (granule type flags or high sector bits).
6090
DEC DE 1B
Decrement DE to point back to the granule number byte.
6091
RLCA 07
Rotate A left (1 bit).
6092
RLCA 07
Rotate A left again (2 bits).
6093
RLCA 07
Rotate A left again (3 bits). The high 3 bits are now in the low 3 bit positions.
6094
ADD A,L 85
Add L (sector offset within granule) to A.
6095
LD L,A 6F
Store the combined offset back into L.
6096
PUSH HL E5
Save the calculated offset onto the stack.
6097
LD A,(DE) 1A
Load Register A with the granule number from (DE).
6098
LD L,A 6F
Copy granule number to L.
6099
LD A,(549CH) 3A 9C 54
Load Register A with the byte at 549CH. This is the sectors per track value.
609C
Call routine at 687DH to multiply or convert the granule number to a sector offset.
609F
POP DE D1
Pop the saved offset into DE.
60A0
ADD HL,DE 19
Add DE (granule offset) to HL (sector conversion). HL now has the total sector number.
60A1
LD A,(549DH) 3A 9D 54
Load Register A with the sectors per granule from 549DH.
60A4
Call the conversion routine again.
60A7
POP AF F1
Pop the saved AF (original conversion result).
60A8
LD E,A 5F
Copy A to E.
60A9
LD D,00H 16 00
Clear Register D. DE now contains the offset value from A as a 16-bit value (D=00H, E=offset).
60AB
ADD HL,DE 19
Add DE (final offset adjustment) to HL (accumulated sector position). HL now contains the complete file sector position.
60AC
LD DE,3D00H 11 00 3D
Load Register pair DE with 3D00H. This is the screen position for sector status (row 4 of video memory, which starts at 3C00H with 64 bytes per row).
60AF
LD BC,6907H 01 07 69
Load Register pair BC with 6907H. B=69H points to the format string table base, C=07H is the format code for "SEC=" display.
60B2
Call routine at 60ECH to format and display the sector number from HL using the format string specified by BC.

60B5H - Display Track Number Status

This section displays the track number on the status line. It retrieves the sector number from the stack, checks if file mode is active, and calculates the track number based on sectors per track.

60B5
LD BC,690AH 01 0A 69
Load Register pair BC with 690AH. B=69H is the format string table base, C=0AH is the format code for "TRK=" display.
60B8
POP HL E1
Pop the absolute sector number from the stack (saved at 6044H).
60B9
LD A,(5491H) 3A 91 54
Load Register A with the primary mode flags from address 5491H.
60BC
BIT 6,A CB 77
Test bit 6 of the mode flags. Bit 6 indicates file mode is active.
60BE
If bit 6 is set (NZ, file mode), jump to 60DEH to display the track number at a different screen location.

Standard disk mode - calculate and display track number from absolute sector.

60C0
LD A,(549BH) 3A 9B 54
Load Register A with the byte at 549BH. This is the sectors per track value for the current disk format (typically 10 or 18).
60C3
Call routine at 6896H to divide HL by sectors per track. Returns quotient (track number) in A, remainder (sector within track) in HL.
60C6
PUSH AF F5
Save AF (track number in A) onto the stack.
60C7
LD (54A0H),A 32 A0 54
Store the track number into address 54A0H for later reference by other routines.
60CA
LD A,L 7D
Load Register A with L (the sector within track from the division remainder).
60CB
LD (549EH),A 32 9E 54
Store the sector-within-track into address 549EH for later reference.
60CE
LD BC,6901H 01 01 69
Load Register pair BC with 6901H. C=01H is the format code for sector-within-track display.
60D1
LD DE,3E00H 11 00 3E
Load Register pair DE with 3E00H. This is the screen position for sector-within-track (row 8 of video memory).
60D4
Call routine at 60ECH to display the sector-within-track number.
60D7
POP AF F1
Pop the saved track number back into Register A.
60D8
LD L,A 6F
Copy the track number to Register L.
60D9
LD H,00H 26 00
Clear Register H. HL now contains the track number as a 16-bit value.
60DB
LD BC,6904H 01 04 69
Load Register pair BC with 6904H. C=04H is the format code for track number display.

60DEH - Display Track Number and Search Type

This section displays the track number at screen position 3F00H (bottom status row), then displays the current search/operation type indicator at position 3FC1H.

60DE
LD DE,3F00H 11 00 3F
Load Register pair DE with 3F00H. This is the screen position for track number display (row 12 of video memory, near bottom of screen).
60E1
Call routine at 60ECH to format and display the track number from HL using format code in C.
60E4
LD A,(5494H) 3A 94 54
Load Register A with the search/operation type flag from address 5494H. This indicates the current mode (F=Find, L=List, etc.).
60E7
LD (3FC1H),A 32 C1 3F
Store the operation type character directly to screen position 3FC1H. This shows the current command mode indicator at the bottom right of the display.

60EAH - Restore Registers and Return

This is the common exit point for the sector display routine. It restores the BC register pair that was saved at the beginning and returns to the caller.

60EA
POP BC C1
Pop Register pair BC from the stack. BC was saved at 5FC4H and contains the edit position from the MOD command.
60EB
RET C9
Return to the caller with the sector display complete.

60ECH - Format and Display Status Value

This is a general-purpose routine for formatting and displaying numeric status values on the screen. It takes a 16-bit value in HL, a screen position in DE, and a format string address in BC. It calculates three screen positions (base, +64, +128 for multi-line display), copies a 3-character label from the format string to the base position, then displays the value in three formats: as a formatted string, in decimal, and in hexadecimal with an "H" suffix.

60EC
PUSH HL E5
Save Register pair HL (the numeric value to display) onto the stack.
60ED
LD HL,0080H 21 80 00
Load Register pair HL with 0080H (128 decimal). This is the offset for the third display line (2 rows × 64 bytes per row in TRS-80 video memory).
60F0
ADD HL,DE 19
Add DE (base screen position) to HL. HL now points to screen position + 128 (two rows below base).
60F1
EX (SP),HL E3
Exchange HL with top of stack. The third-line position is saved on stack, HL now has the numeric value again.
60F2
PUSH HL E5
Save the numeric value onto the stack (needed later for decimal display).
60F3
PUSH HL E5
Save the numeric value a third time (needed for formatted string display).
60F4
LD HL,0040H 21 40 00
Load Register pair HL with 0040H (64 decimal). This is the offset for the second display line (1 row × 64 bytes).
60F7
ADD HL,DE 19
Add DE (base screen position) to HL. HL now points to screen position + 64 (one row below base).
60F8
EX (SP),HL E3
Exchange HL with top of stack. The second-line position is saved, HL has numeric value.
60F9
PUSH HL E5
Save the numeric value onto the stack (for label copy source address calculation).
60FA
LD H,B 60
Copy B (high byte of format string address, typically 69H) to Register H.
60FB
LD L,C 69
Copy C (low byte of format string address) to Register L. HL now points to the format string (e.g., "SEC", "TRK", "DSK" at addresses like 6901H, 6904H, etc.).
60FC
LD BC,0003H 01 03 00
Load Register pair BC with 0003H. This is the label length - copy 3 characters for the status label.
60FF
LDIR ED B0
Block copy BC (3) bytes from (HL) to (DE). This copies the 3-character label (like "SEC" or "TRK") to the screen at the base position. DE advances to base+3.
6101
POP DE D1
Pop DE from the stack. DE now contains the numeric value (was pushed at 60F9H).
6102
Call routine at 68AFH to format and display the value in a special format (possibly with leading zeros or spacing). Screen position in HL (from LDIR), value in DE.
6105
POP DE D1
Pop DE from the stack. DE now contains the second-line screen position (base + 64, pushed at 60F8H).
6106
Call routine at 668AH to display the value in decimal at screen position DE. The numeric value is retrieved from the stack inside this routine.
6109
POP DE D1
Pop DE from the stack. DE now contains the third-line screen position (base + 128, pushed at 60F1H).
610A
POP HL E1
Pop HL from the stack. HL now contains the numeric value (original value pushed at 60ECH).
610B
Call routine at 6665H to convert HL to hexadecimal ASCII and display at screen position DE. Returns with HL pointing past the hex digits.
610E
LD (HL),48H 36 48
Store 48H (ASCII H) at the current screen position (HL). This adds the "H" suffix to indicate hexadecimal notation.
6110
RET C9
Return to the caller. The status value has been displayed in three formats on three consecutive lines.

6111H - Boundary Range Check

This routine checks if the current position falls within a specified boundary range. It compares values at 5499H and 549AH, then checks if the current sector (54A2H) is within range of the target sector (54A4H). If within range, it sets bit 7 of the secondary mode flags at 5493H. This is used during search operations to determine if a match has been found within the current sector.

6111
LD HL,549AH 21 9A 54
Load Register pair HL with 549AH, pointing to the boundary comparison high byte.
6114
LD A,(5499H) 3A 99 54
Load Register A with the byte at 5499H, the boundary comparison low byte.
6117
CP (HL) BE
Compare A with the byte at (HL=549AH). Checks if the two boundary bytes match.
6118
RET NZ C0
If NZ (boundary bytes don't match), return immediately - not in range.
6119
PUSH DE D5
Save Register pair DE onto the stack (contains position offset from caller).
611A
LD HL,(54A4H) 2A A4 54
Load Register pair HL with the target sector number from addresses 54A4H-54A5H.
611D
LD DE,(54A2H) ED 5B A2 54
Load Register pair DE with the current sector number from addresses 54A2H-54A3H.
6121
OR A B7
Clear the carry flag by ORing A with itself.
6122
SBC HL,DE ED 52
Subtract DE (current sector) from HL (target sector) with borrow. Result = target - current.
6124
If carry (target < current, searching backwards), jump to 612DH to handle reverse range check.

Forward search - target ≥ current sector.

6126
POP HL E1
Pop the saved DE value into HL (position offset).
6127
RET NZ C0
If NZ (target != current sector), return - not on the target sector yet.

On the target sector - check byte position within sector.

6128
LD A,B 78
Load Register A with B (high byte of position or search parameter from caller).
6129
CP C B9
Compare A (B) with C (low byte of position). Checks position against boundary.
612A
RET NC D0
If no carry (B ≥ C, position not past boundary), return - not yet at boundary.
612B
Jump to 6134H to set the boundary flag.

612DH - Reverse Range Check

This section handles the reverse search case where the target sector is before the current sector. It recalculates the range to determine if the current position is within the search boundary.

612D
ADD HL,DE 19
Add DE back to HL. This restores HL to the target sector (undoing the previous SBC).
612E
POP BC C1
Pop the saved position offset into BC (was pushed as DE at 6119H).
612F
ADD HL,BC 09
Add BC (position offset) to HL (target sector). HL = target + offset.
6130
OR A B7
Clear the carry flag.
6131
SBC HL,DE ED 52
Subtract DE (current sector) from HL (target + offset). Checks if current is within range.
6133
RET C D8
If carry (current sector is past the adjusted target), return - out of range.

6134H - Set Boundary Flag

This section sets bit 7 of the secondary mode flags to indicate that the boundary condition has been met. This flag signals to the calling code that the search target has been found.

6134
LD HL,5493H 21 93 54
Load Register pair HL with 5493H, the address of the secondary mode flags byte.
6137
SET 7,(HL) CB FE
Set bit 7 of the byte at (HL). Bit 7 indicates boundary/target found.
6139
RET C9
Return to the caller with the boundary flag set.

613AH - Print Sector Display to Printer

This routine prints the current sector display to the printer. It first refreshes the screen display, then outputs each character of the first row (64 characters) to the printer, converting TRS-80 graphics characters to printable ASCII. The user can press H to halt, P to pause, or let it continue for multiple pages.

613A
PUSH BC C5
Save Register pair BC onto the stack. BC contains the page counter from the caller.
613B
Call routine at 5FB8H to refresh the sector display on screen, showing the current sector contents in hex/ASCII format.
613E
Call routine at 6379H to output a carriage return to the printer, starting a new line.
6141
POP BC C1
Restore Register pair BC (page counter) from the stack.
6142
LD HL,3C00H 21 00 3C
Load Register pair HL with 3C00H, the start of video memory. This is where the sector display begins.
6145
LD B,40H 06 40
Load Register B with 40H (64 decimal). This is the number of characters per row to print.

6147H - Print Row Character Loop

This loop reads each character from video memory and outputs it to the printer. TRS-80 graphics characters (codes 00H-1FH and 80H-BFH) are converted to printable ASCII by adding 40H to codes below 20H.

6147
LD A,(HL) 7E
Load Register A with the character from video memory at (HL).
6148
CP 20H FE 20
Compare A with 20H (ASCII space). Characters below 20H are TRS-80 graphics characters that need conversion.
614A
INC HL 23
Increment HL to point to the next character in video memory.
614B
If no carry (character ≥ 20H, already printable), jump to 614FH to output it directly.
614D
ADD 40H C6 40
Add 40H to A. This converts TRS-80 graphics codes (00H-1FH) to printable characters (40H-5FH, which are @, A-Z, etc.).
614F
Call routine at 62C8H to output character A to the printer.
6152
Decrement B and jump back to 6147H if not zero. [PRINT ROW LOOP] Prints all 64 characters of the row.
6154
Call routine at 6248H to output a newline to the printer after the row.

6157H - Check for User Interrupt

After printing each row, this section checks if the user has pressed a key to halt or pause the printing. H halts completely, P pauses until Enter is pressed.

6157
Call routine at 6205H to scan the keyboard for a keypress. Returns A=key code if pressed, or 0 if no key.
615A
CP 48H FE 48
Compare A with 48H (ASCII H for Halt).
615C
If not H (NZ), jump to 6164H to check for other keys.

User pressed H - halt printing and return to command loop.

615E
Call routine at 6374H to flush the printer buffer and finalize output.
6161
Jump to 65B4H to return to the command loop, aborting the print operation.
6164
CP 50H FE 50
Compare A with 50H (ASCII P for Pause).
6166
If not P (NZ), jump to 616FH to continue printing.

6168H - Pause and Wait for Enter

When the user presses P, this loop waits for them to press Enter before resuming the print operation.

6168
Call routine at 620BH to wait for a keypress. Returns the key code in A.
616B
CP 0DH FE 0D
Compare A with 0DH (ASCII carriage return = Enter).
616D
If not Enter (NZ), loop back to 6168H to wait. [PAUSE LOOP]

616FH - Continue Printing or Finish

This section decrements the page counter and either continues printing the next row or finishes the print job with extra newlines.

616F
DEC C 0D
Decrement Register C (the row counter for the current page).
6170
If C not zero (more rows to print), jump back to 6145H. [PAGE LOOP]

Finished printing all rows - add blank lines and finalize.

6172
Call routine at 6248H to output a blank line to the printer.
6175
Call routine at 6248H again to output a second blank line for spacing.
6178
Jump to 6374H to flush the printer buffer and return to the caller.

617BH - Initialize Edit Buffers

This routine initializes the edit buffers for sector operations. It calculates the buffer size based on the value at 54B4H, sets up the source buffer at 4200H and destination buffer at 5300H, stores the buffer address in the FCB, and fills the destination buffer with FFH bytes while reading keyboard input. This allows the user to enter data while the buffer is being initialized.

617B
LD HL,(54B4H) 2A B4 54
Load Register pair HL with the 16-bit value at addresses 54B4H-54B5H. This is the buffer size or page value used for calculations.
617E
Call routine at 61BFH to calculate the buffer parameters based on HL. Returns B=byte count.
6181
LD HL,4200H 21 00 42
Load Register pair HL with 4200H, the source buffer address. This buffer holds the original sector data for comparison during Copy operations.
6184
LD (5403H),HL 22 03 54
Store HL into addresses 5403H-5404H. This is FCB offset 03H, storing the source buffer address for disk operations.
6187
LD HL,5300H 21 00 53
Load Register pair HL with 5300H, the destination buffer address. This is the main edit buffer where sector data is displayed and modified.
618A
LD C,00H 0E 00
Load Register C with 00H. C serves as a secondary counter or flag for the fill loop.
618C
LD DE,5400H 11 00 54
Load Register pair DE with 5400H, the FCB base address. This is passed to the keyboard routine for reference.
618F
Jump to 6195H to start the fill/input loop, skipping the first fill iteration.

6191H - Fill Buffer with FFH

This loop fills the destination buffer at 5300H with FFH bytes. The FFH value represents "empty" or "uninitialized" data in the TRS-80 disk format.

6191
LD (HL),0FFH 36 FF
Store FFH at the buffer position (HL). FFH is the default fill byte representing empty/uninitialized data.
6193
DEC C 0D
Decrement Register C (secondary counter). This tracks additional operations during the fill.
6194
INC HL 23
Increment HL to point to the next buffer position.
6195
Decrement B and jump back to 6191H if not zero. [BUFFER FILL LOOP] Fills B bytes with FFH.

6197H - Keyboard Input During Fill

After filling the buffer, this section reads keyboard input using the ROM routine at 0013H. Characters are stored into the buffer, allowing the user to enter data. Special keys (BREAK, CLEAR) are handled separately.

6197
LD B,C 41
Copy C (secondary counter) to B. B becomes the input character counter.
6198
Call ROM routine at 0013H. This is the TRS-80 keyboard input routine that waits for and returns a character in A. Z flag set if no special key.
619B
If NZ (special key pressed like BREAK or CLEAR), jump to 61A2H to handle it.
619D
LD (HL),A 77
Store the input character A into the buffer at (HL).
619E
INC HL 23
Increment HL to point to the next buffer position.
619F
Decrement B and loop back to 6198H if not zero. [INPUT LOOP] Reads up to B characters.
61A1
RET C9
Return to the caller with the buffer filled and input complete.

61A2H - Handle Special Keys

This section handles special keys returned by the ROM keyboard routine. Key code 1CH indicates BREAK was pressed (fill remaining buffer with FFH and show error), while 1DH indicates CLEAR was pressed (return to a specific menu).

61A2
CP 1CH FE 1C
Compare A with 1CH. This is the BREAK key code returned by the ROM routine.
61A4
If not BREAK (NZ), jump to 61B7H to check for other special keys.

BREAK pressed - fill remaining buffer with FFH and show abort message.

61A6
LD (HL),0FFH 36 FF
Store FFH at the current buffer position (HL) to fill remaining space.
61A8
INC HL 23
Increment HL to the next position.
61A9
Decrement B and loop if not zero. [BREAK FILL LOOP] Fills remaining buffer with FFH.
61AB
Load Register pair HL with 6ECBH, the address of an abort/break message string.
61AE
Call routine at 6245H to display the message with a newline.
61B1
Load Register pair HL with 6DD5H, the address of a prompt or continuation message.
61B4
Jump to 6345H to display the message and wait for a keypress before returning.
61B7
CP 1DH FE 1D
Compare A with 1DH. This is the CLEAR key code.
61B9
If not CLEAR (NZ), jump to 6578H to handle as an unknown/error key.
61BC
CLEAR was pressed - jump to 56A9H to return to the main menu.

61BFH - Calculate Buffer Parameters from Input Value

This routine calculates sector and offset values from an input address in HL. It compares HL against the limit value at 54B2H, computes the sector number and byte offset within sector, and sets up the FCB fields for file positioning. On entry: HL = input address value. On exit: FCB at 540AH contains sector number, 5405H contains byte offset, bit 5 of 5401H is set to indicate special buffer mode.

61BF
LD DE,(54B2H) ED 5B B2 54
Load DE with the buffer limit value from 54B2H. This is the comparison/boundary value for range checking.
61C3
OR A B7
Clear the Carry flag by ORing A with itself. Prepares for the SBC instruction.
61C4
SBC HL,DE ED 52
Subtract DE (buffer limit) from HL with borrow. HL = HL - DE. If HL was less than DE, Carry is set.
61C6
LD BC,0100H 01 00 01
Load BC with 0100H. B = 01H (page/sector multiplier), C = 00H (initial offset). This is the default for when HL ≥ DE.
61C9
If no carry (HL ≥ DE, input is at or beyond limit), jump to 61D4H to continue with default BC values.

HL was less than DE (input below limit). Set up alternative calculation.

61CB
LD H,C 61
Load H with C (which is 00H). Start building result with H = 0.
61CC
LD L,C 69
Load L with C (00H). Now HL = 0000H.
61CD
LD B,E 43
Load B with E (low byte of the limit). B now holds the page value from the limit.
61CE
LD E,C 59
Load E with C (00H). E is now 0.
61CF
LD (54B4H),DE ED 53 B4 54
Store DE to 54B4H, the buffer size/page value location. This records the calculated page info.
61D3
INC B 04
Increment B (the page counter). Adjusts for the calculation.
61D4
LD DE,0002H 11 02 00
Load DE with 0002H. This is an adjustment value for the sector calculation.
61D7
ADD HL,DE 19
Add 2 to HL. This adjusts the offset for sector boundary alignment.
61D8
If no carry (no overflow), jump to 61DBH to continue.
61DA
INC C 0C
Increment C if there was a carry (overflow into next page). C tracks the high byte of the sector number.
61DB
LD A,L 7D
Load A with L, the low byte of the adjusted value. This becomes the byte offset within sector.
61DC
LD L,H 6C
Load L with H. Shift the high byte down to become the low byte of sector number.
61DD
LD H,C 61
Load H with C (the overflow counter). HL now contains the sector number.
61DE
LD (540AH),HL 22 0A 54
Store HL to 540AH, the sector number field in the FCB. This is the calculated sector.
61E1
LD (5405H),A 32 05 54
Store A to 5405H, the byte offset field in the FCB. This is the position within the sector.
61E4
LD HL,5401H 21 01 54
Load HL with 5401H, the address of the FCB mode/attribute flags.
61E7
SET 5,(HL) CB EE
Set bit 5 of the FCB flags, indicating special buffer mode is active. This tells the I/O routines to use the calculated buffer position.
61E9
RET C9
Return to caller. Buffer parameters are now set up in the FCB.

61EAH - Convert DE to Hex ASCII at (HL)

This routine converts the 16-bit value in DE to 4 hex ASCII characters, storing them at the address in HL. It calls the byte conversion routine twice - once for D (high byte) and once for E (low byte). On entry: DE = 16-bit value to convert, HL = destination buffer address. On exit: HL points past the 4 stored characters.

61EA
LD A,D 7A
Load A with D, the high byte of the value to convert.
61EB
Call the byte to hex routine at 61EFH. Converts A (high byte) to 2 hex ASCII chars at (HL), advances HL by 2.
61EE
LD A,E 7B
Load A with E, the low byte of the value to convert. Fall through to convert this byte as well.

61EFH - Convert Byte A to 2 Hex ASCII Characters at (HL)

This routine converts the byte in A to two hex ASCII characters, storing them at the address in HL. It converts the high nibble first, then the low nibble. On entry: A = byte to convert, HL = destination address. On exit: HL points past the 2 stored characters (HL = HL + 2).

61EF
PUSH AF F5
Save A onto the stack. We need the original value for the low nibble later.
61F0
RRCA 0F
Rotate A right. First of 4 rotations to move high nibble to low nibble position.
61F1
RRCA 0F
Rotate A right again.
61F2
RRCA 0F
Rotate A right again.
61F3
RRCA 0F
Rotate A right a fourth time. The high nibble is now in the low nibble position (bits 0-3).
61F4
Call the nibble to hex routine at 61F8H to convert and store the high nibble as an ASCII character.
61F7
POP AF F1
Restore the original A value. The low nibble is now ready for conversion. Fall through to convert it.

61F8H - Convert Low Nibble of A to Hex ASCII and Store at (HL)

This routine converts the low nibble (bits 0-3) of A to a hex ASCII character ('0'-'9' or 'A'-'F') and stores it at the address in HL, then increments HL. On entry: A = value with nibble to convert in bits 0-3, HL = destination address. On exit: Character stored at (HL), HL = HL + 1.

61F8
AND 0FHAND 00001111 E6 0F
Mask A with 0FH to isolate the low nibble (bits 0-3). A is now 00H-0FH.
61FA
CP 0AH FE 0A
Compare A with 0AH (10 decimal). Check if nibble is 0-9 or A-F.
61FC
If A < 0AH (nibble is 0-9), jump to 6200H to skip the letter adjustment.
61FE
ADD A,07H C6 07
Add 7 to A. This adjusts for the gap between '9' (39H) and 'A' (41H) in ASCII. A is now 11H-16H.
6200
ADD A,30H C6 30
Add 30H ('0') to A. Converts nibble value to ASCII character. Result is '0'-'9' (30H-39H) or 'A'-'F' (41H-46H).
6202
LD (HL),A 77
Store the hex ASCII character at the destination address (HL).
6203
INC HL 23
Increment HL to point to the next buffer position.
6204
RET C9
Return to caller. One hex character has been stored.

6205H - Non-Blocking Keyboard Scan

This routine performs a non-blocking keyboard scan by calling ROM routine 002BH. It preserves DE and converts any lowercase letters to uppercase. On entry: None. On exit: A = key code if key pressed (converted to uppercase), A = 0 if no key, DE preserved.

6205
PUSH DE D5
Save DE onto the stack. DE is preserved through the ROM call.
6206
CALL 002BH CD 2B 00
Call ROM routine at 002BH. This is the TRS-80 ROM keyboard scan routine. Returns A = key code, or A = 0 if no key pressed. This is non-blocking.
6209
Jump to 620FH to restore DE and convert lowercase to uppercase.

620BH - Blocking Keyboard Wait

This routine waits for a keypress by calling ROM routine 0049H. It preserves DE and converts any lowercase letters to uppercase. This is a blocking call - execution pauses until a key is pressed. On entry: None. On exit: A = key code (converted to uppercase), DE preserved.

620B
PUSH DE D5
Save DE onto the stack. DE is preserved through the ROM call.
620C
CALL 0049H CD 49 00
Call ROM routine at 0049H. This is the TRS-80 ROM wait for key routine. Blocks until a key is pressed, returns key code in A.

620FH - Restore DE and Convert Lowercase to Uppercase

This is the common exit point for keyboard routines. It restores DE from the stack and converts any lowercase letter in A to uppercase. On entry: A = key code from keyboard. On exit: A = key code (uppercase if was lowercase letter), DE restored.

620F
POP DE D1
Restore DE from the stack.

6210H - Convert Lowercase to Uppercase

This routine converts a lowercase letter (a-z) in A to uppercase (A-Z). If A is not a lowercase letter, it is returned unchanged. On entry: A = character to convert. On exit: A = uppercase character (if was lowercase) or original character.

6210
CP 61H FE 61
Compare A with 61H, the ASCII code for a. Check if character is at or above lowercase 'a'.
6212
RET C D8
If carry set (A < 61H, character is below 'a'), return immediately. Not a lowercase letter.
6213
CP 7BH FE 7B
Compare A with 7BH, one past the ASCII code for z. Check if character is at or below 'z'.
6215
RET NC D0
If no carry (A >= 7BH, character is above 'z'), return immediately. Not a lowercase letter.
6216
SUB 20H D6 20
Subtract 20H from A. This converts lowercase to uppercase (e.g., 'a' 61H becomes 'A' 41H).
6218
RET C9
Return with A containing the uppercase character.

6219H - Clear Command Line and Display String with Newlines

This routine clears the command line area on screen, then displays the string pointed to by HL, followed by 3 carriage returns (newlines) to the printer. It's used to prepare the display for new prompts or messages.

6219
Call the clear command line routine at 62A7H. This clears the bottom command line area of the screen by outputting a "home cursor" control code (1FH), preparing the screen for new output.
621C
Call the display string with newline routine. This displays the string at (HL) and outputs one carriage return to the printer. Register HL must point to the string to display.
621F
LD B,03H 06 03
Load Register B with 3, the number of additional newlines to output. Combined with the one from 6245H, this produces a total of 3 blank lines.
6221
Jump to the newline output loop at 624AH. This outputs B carriage returns (0DH characters) to the printer, creating vertical spacing.

6224H - Display String and Prompt for Y/N Confirmation

This routine displays a string at (HL), then displays the standard Y/N prompt from 6D11H and calls the confirmation input routine. On exit: Z flag set if user entered Y, NZ if N. If Z flag is set, execution jumps to 54C5H (main command handler).

6224
Call the display string with newline routine. Register HL points to the message to display before the Y/N prompt (e.g., "WRITE CHANGES").
6227
Load HL with 6D11H, the address of the Y/N prompt string (contains " (Y/N)?" or similar confirmation prompt text).
622A
Call the Y/N confirmation loop at 6231H. This displays the prompt and waits for the user to enter either Y or N. Returns with Z flag set if Y, NZ if N.
622D
If Z flag is set (user entered Y for Yes), jump to 54C5H, the main command handler entry point. This executes the confirmed action.
6230
RET C9
Return to caller. If we reach here, the user entered N for No, so the Z flag is clear (NZ). The caller can check this to handle the rejection.

6231H - Y/N Confirmation Input Loop

This routine repeatedly displays the prompt string at (HL), collects keyboard input, and loops until the user enters either Y (59H) or N (4EH). The routine gives the user 3 attempts, re-displaying the prompt each time. On entry: HL = prompt string address. On exit: A = key pressed (59H for Y or 4EH for N), Z flag set if Y, NZ if N.

[LOOP START] - Y/N input loop. Prompts user up to 3 times for valid input.

6231
PUSH HL E5
Save HL (the prompt string address) onto the stack. This preserves the prompt address since the input routine at 634EH will modify HL.
6232
Call the display prompt and collect input routine. This displays the string at HL and waits for keyboard input. Returns with A containing the key pressed (converted to uppercase).
6235
POP HL E1
Restore HL to point to the prompt string address again, in case we need to re-prompt.
6236
DEC B 05
Decrement Register B, the retry counter. B was set to 64 (40H) by the input routine at 6354H, but we use it here to track prompt attempts.
6237
If B is not zero (more retries available), jump back to 6231H to re-display the prompt and try again. This allows multiple attempts for valid input.

After the loop, check if the user entered a valid response (Y or N).

6239
CP 4EH FE 4E
Compare A (the key pressed) with 4EH, the ASCII code for N. If equal, Z flag is set.
623B
RET Z C8
If Z flag is set (user pressed N), return immediately. The Z flag indicates the response, but note: Z=set means "No" here, which will be inverted by the next check.
623C
CP 59H FE 59
Compare A with 59H, the ASCII code for Y. If equal, Z flag is set.
623E
If Z flag is not set (user pressed neither Y nor N), jump back to 6231H to re-prompt. Invalid keys cause the loop to repeat.

[LOOP END] - User entered Y. Clear carry and return with Z flag set.

6240
OR A B7
OR A with itself. This clears the Carry flag and preserves the Z flag (which is currently set from the CP 59H comparison). A still contains 59H (Y).
6241
RET C9
Return to caller with Z flag set (indicating Y was pressed) and A = 59H. The caller can check Z to determine the user's response.

6242H - Flush Printer and Display String with Newline

This routine flushes the printer buffer, then displays the string at (HL) followed by a newline. Used when printer output needs to be synchronized before displaying new content.

6242
Call the flush printer buffer routine at 6374H. This ensures any pending printer output is sent before continuing.

6245H - Display String with Single Newline

This routine displays the string pointed to by HL, then outputs one carriage return (0DH) to the printer. On entry: HL = string address. The string display routine at 6255H is called first.

6245
Call the display string routine at 6255H. This outputs each character of the string at (HL) until a terminator is reached.
6248
LD B,01H 06 01
Load Register B with 1, the number of newlines to output. This is used as a loop counter for the carriage return output loop.

[LOOP START] - Newline output loop. Outputs B carriage returns to printer.

624A
LD A,0DH 3E 0D
Load A with 0DH, the ASCII code for carriage return (newline character for the printer).
624C
Call the character output routine at 62C8H. This outputs the carriage return character A to the printer with appropriate handling.
624F
Decrement B and jump to 624AH if B is not zero. This loops to output multiple newlines when B > 1.

[LOOP END] - All newlines output.

6251
RET C9
Return to caller. The string has been displayed and B newlines have been output to the printer.

6252H - Flush Printer and Display Compressed String

This routine flushes the printer buffer before displaying a compressed string. It's an entry point that ensures printer synchronization before string output.

6252
Call the flush printer buffer routine to ensure any pending output is sent before displaying new content.

6255H - Display Compressed String

This is the main compressed string display routine. SUPERZAP uses a sophisticated string compression system where common words are stored in tables at 696BH (short words) and 6A23H (longer words). Strings contain special control codes (60H and above) that index into these word tables. The high bit of each character in the tables marks the end of a word. On entry: HL points to the compressed string. Register C tracks state: bit 0 indicates if a space should precede the next word.

6255
PUSH BC C5
Save BC onto the stack to preserve the caller's values. BC will be used internally by this routine.
6256
LD C,00H 0E 00
Initialize Register C to 0. Bit 0 of C is the space flag: when set, a space will be output before the next word to separate it from the previous word.
6258
Jump to 6264H to begin fetching characters from the string. This skips the terminator check on first entry.

[LOOP START] - Main character processing loop. Each character is checked for control codes or terminators.

625A
CP 03H FE 03
Compare A (the current character) with 03H, the ETX (End of Text) control code. This marks the end of the string.
625C
If A is not 03H (not end of string), jump to 6260H to continue processing this character.
625E
POP BC C1
Restore BC from the stack. The string display is complete.
625F
RET C9
Return to caller. The entire compressed string has been output.
6260
Call the character output filter at 629FH. This outputs the character in A (unless it's 08H, the backspace control that resets the space flag).
6263
INC HL 23
Advance HL to point to the next character in the string.
6264
LD A,(HL) 7E
Load A with the current character from the string at (HL).
6265
CP 60H FE 60
Compare A with 60H (96 decimal). Characters 60H and above are compressed word tokens that index into word tables.
6267
If A < 60H (a literal character or control code), jump back to 625AH to output it directly.

Character is 60H or above - it's a compressed word token. Decode and output the word from the table.

6269
SUB 5FH D6 5F
Subtract 5FH (95) from A. This converts the token to a 1-based word index. Token 60H becomes index 1, 61H becomes 2, etc.
626B
LD B,A 47
Copy the word index to B. B will count down as we scan through the word table to find the correct entry.
626C
PUSH HL E5
Save HL (the current string position) onto the stack. HL will be modified to point into the word tables.
626D
Load HL with 696BH, the address of the first word table. This table contains shorter, more common words.
6270
SUB 38H D6 38
Subtract 38H (56) from A. If the result is negative (carry set), the word is in the first table. Otherwise, it's in the second table.
6272
If carry is set (original index was < 57), jump to 6279H to search the first word table at 696BH.
6274
LD B,A 47
The index is for the second table. Update B with the adjusted index (original - 56).
6275
Load HL with 6A23H, the address of the second word table. This table contains longer words.
6278
INC B 04
Increment B to adjust for the table change. The DJNZ loop decrements before comparing, so we need to compensate.

[INNER LOOP START] - Scan through word table to find the entry at index B. Words end with high bit set.

6279
BIT 7,(HL) CB 7E
Test bit 7 of the byte at (HL). In compressed words, the high bit is set on the last character of each word.
627B
INC HL 23
Advance HL to the next byte in the word table.
627C
If bit 7 was 0 (not end of word), loop back to 6279H to continue scanning past this word.

Found end of a word. Check if this is the word we're looking for.

627E
LD A,(HL) 7E
Load A with the first byte of the next word (or 00H if end of table).
627F
OR A B7
Test if A is zero. A zero byte marks the end of the word table.
6280
If A is zero (end of table reached without finding word), jump to 629CH to restore HL and continue with the main string.
6282
Decrement B and jump to 6279H if B is not zero. Continue scanning until we've skipped B-1 words to reach our target.

[INNER LOOP END] - Found the target word. Now output it character by character.

6284
INC HL 23
Advance HL past the end marker of the previous word to the first character of our target word.
6285
CP 08H FE 08
Compare A (first char of word) with 08H, the backspace control code. This special code suppresses the inter-word space.
6287
If A is 08H (backspace), jump to 628FH to skip the space handling and begin outputting the word.
6289
DEC HL 2B
Back up HL by one so we can re-read this character after potentially outputting a space.
628A
BIT 0,C CB 41
Test bit 0 of C, the space flag. If set, a space should be output before this word.
628C
If the space flag is set (NZ), call 62C6H to output a space character (20H) before the word.
628F
SET 0,C CB C1
Set bit 0 of C to enable the space flag. The next word will be preceded by a space (unless overridden by 08H).

[WORD OUTPUT LOOP] - Output each character of the word until high bit is set.

6291
LD A,(HL) 7E
Load A with the current character of the word from the table at (HL).
6292
AND 7FHAND 01111111 E6 7F
Mask off bit 7 to get the actual ASCII character. The high bit is used only as an end-of-word marker.
6294
Call the character output filter to output this character (A) to the display/printer.
6297
BIT 7,(HL) CB 7E
Test bit 7 of the original byte at (HL). If set, this was the last character of the word.
6299
INC HL 23
Advance HL to the next character in the word table.
629A
If bit 7 was 0 (not end of word), loop back to 6291H to output the next character.

[WORD OUTPUT LOOP END] - Word complete. Restore string position and continue.

629C
POP HL E1
Restore HL to point to the current position in the original string (where the token was).
629D
Jump back to 6263H to advance HL and continue processing the next character in the string.

629FH - Character Output Filter

This routine filters character output. If the character is 08H (backspace control code), it resets the space flag in C and returns without output. Otherwise, it outputs the character via the main character output routine at 62C8H. On entry: A = character to output, C = flags (bit 0 = space flag). On exit: Character output to display/printer (unless A was 08H).

629F
CP 08H FE 08
Compare A with 08H, the backspace/suppress-space control code. This code prevents a space from being output before the next word.
62A1
If A is not 08H (a normal printable character), jump to 62C8H to output the character.
62A4
RES 0,C CB 81
Reset bit 0 of C, clearing the space flag. The next word will not be preceded by a space.
62A6
RET C9
Return without outputting anything. The 08H code is consumed silently.

62A7H - Clear Command Line Area

This routine clears the command line area on the screen by first outputting a "home to command line" code (1CH) followed by a "clear to end of line" code (1FH). Used to prepare the screen for new prompts or messages.

62A7
Call 62B6H to output 1CH, which moves the cursor to the command line home position at the bottom of the screen.
62AA
LD A,1FH 3E 1F
Load A with 1FH, the control code for clear to end of line. This erases all characters from cursor to the right edge.
62AC
Jump to 62C8H to output the clear control code. Execution continues there.

62AEH - Output "Turn On Expanded Print" Control

Outputs control code 0EH to enable expanded (double-width) printing on compatible printers.

62AE
LD A,0EH 3E 0E
Load A with 0EH, the printer control code for expanded print on (double-width characters).
62B0
Jump to 62C8H to output the control code to the printer.

62B2H - Output "Turn Off Expanded Print" Control

Outputs control code 0FH to disable expanded (double-width) printing on compatible printers.

62B2
LD A,0FH 3E 0F
Load A with 0FH, the printer control code for expanded print off (return to normal width).
62B4
Jump to 62C8H to output the control code to the printer.

62B6H - Output "Home to Command Line" Control

Outputs control code 1CH to position the cursor at the command line area (bottom of screen).

62B6
LD A,1CH 3E 1C
Load A with 1CH, the control code for home cursor to command line. On the TRS-80, this positions the cursor at the start of the command input area.
62B8
Jump to 62C8H to output the control code.

62BAH - Output Buffer Contents (B bytes from HL)

Outputs B bytes from the buffer at (HL) to the character output routine. On entry: HL = buffer address, B = byte count. On exit: HL points past the last byte output, B = 0.

[LOOP START] - Output B bytes from buffer at (HL).

62BA
LD A,(HL) 7E
Load A with the current byte from the buffer at (HL).
62BB
INC HL 23
Advance HL to point to the next byte in the buffer.
62BC
Call the character output routine to output the byte in A.
62BF
Decrement B and jump back to 62BAH if B is not zero. Continue until all bytes are output.

[LOOP END]

62C1
RET C9
Return to caller. All B bytes have been output.

62C2H - Output Single Character from (HL) and Advance

Outputs one character from (HL) and advances HL. Used for inline string output where HL tracks position.

62C2
LD A,(HL) 7E
Load A with the character at (HL).
62C3
INC HL 23
Advance HL to the next position.
62C4
Jump to 62C8H to output the character in A.

62C6H - Output Space Character

Outputs a space character (20H). Called by the compressed string routine to insert spaces between words.

62C6
LD A,20H 3E 20
Load A with 20H, the ASCII code for space.

62C8H - Main Character Output Routine

This is the central character output routine for SUPERZAP. It handles both screen and printer output, managing column tracking, line wrapping, and special control codes. The routine uses several workspace variables: 5483H (current column position), 5484H (line width), 5480H (output mode flags where bit 6 = printer output enabled), 5481H (lines per page), 5482H (current line count). On entry: A = character to output. All registers are preserved.

62C8
PUSH HL E5
Save HL onto the stack. All registers will be preserved through this routine.
62C9
PUSH DE D5
Save DE onto the stack.
62CA
PUSH BC C5
Save BC onto the stack.
62CB
PUSH AF F5
Save AF onto the stack. A contains the character to output.
62CC
LD HL,5483H 21 83 54
Load HL with 5483H, the address of the current column position variable. This tracks horizontal position for line wrapping.
62CF
CP 0EH FE 0E
Compare A with 0EH. Characters 0EH and above get special handling for screen/printer output.
62D1
If A >= 0EH (printable or high control), jump to 62D7H to output via the display/printer routine.
62D3
CP 0AH FE 0A
Compare A with 0AH (line feed). Characters 0AH-0DH are line control codes.
62D5
If A >= 0AH (line feed, vertical tab, form feed, or carriage return), jump to 62FDH to handle line ending.

Character is 00H-09H (low control code). Output directly then handle column tracking.

62D7
Call the device output routine at 63E8H. This outputs character A to the screen and/or printer depending on mode flags.
62DA
CP 20H FE 20
Compare A with 20H (space). Characters 20H and above are printable and advance the column.
62DC
If A >= 20H (printable character), jump to 62FAH to decrement the column counter.

Character is a control code (00H-1FH). Handle special cases.

62DE
CP 08H FE 08
Compare A with 08H (backspace). Backspace moves the column position left.
62E0
If A is not 08H (not backspace), jump to 62EEH to check for other control codes.

Handle backspace (08H) - move column position left if possible.

62E2
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H. This is the maximum column number (e.g., 64 or 80).
62E5
DEC A 3D
Decrement A to get max column - 1. Column positions are counted down from line width.
62E6
CP (HL) BE
Compare A (max column - 1) with the current column position at (HL=5483H). Check if we're at start of line.
62E7
INC (HL) 34
Increment the column counter at (HL). Moving left means increasing the "remaining columns" count.
62E8
If no carry (column was not at leftmost position), jump to 6322H to exit. Backspace handled successfully.
62EA
LD (HL),01H 36 01
We're at the start of the line. Set column to 1 (can't go further left). This prevents wrapping backwards.
62EC
Jump to 6322H to exit.

Check for cursor positioning codes (1CH-38H range).

62EE
SUB 1CH D6 1C
Subtract 1CH from A. Codes 1CH-38H are cursor positioning controls that reset column position.
62F0
CP 1DH FE 1D
Compare result with 1DH (29 decimal). Check if original code was in the 1CH-38H range.
62F2
If A >= 1DH (original code was 39H or above, not a positioning code), jump to 6322H to exit without column change.
62F4
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H. Cursor positioning resets to the start of a line.
62F7
LD (HL),A 77
Store the line width as the new column position at (HL=5483H). This resets position to start of line.
62F8
Jump to 6322H to exit.

Handle printable characters (20H and above) - decrement column counter.

62FA
DEC (HL) 35
Decrement the column counter at (HL=5483H). Each printed character uses one column.
62FB
If column counter is not zero (still room on line), jump to 6322H to exit.

Column counter reached zero - end of line. Handle auto line wrap.

62FD
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H.
6300
CP (HL) BE
Compare line width with current column at (HL). If equal, we're at the start of a line.
6301
LD A,20H 3E 20
Load A with 20H (space character). This may be output to fill the line.
6303
If Z flag is set (column equals line width, meaning we're at line start), call 63E8H to output a space. This handles empty line case.
6306
LD A,0DH 3E 0D
Load A with 0DH (carriage return). This ends the current line.
6308
Call 63E8H to output the carriage return to screen/printer.
630B
Call 63B5H to handle end of line processing. This resets the column counter and handles page breaks for printer.

Check if user pressed BREAK key to pause printing.

630E
LD A,(3840H) 3A 40 38
Load A from address 3840H, the keyboard matrix row containing ENTER, CLEAR, BREAK, arrow keys, and SPACE.
6311
AND 04HAND 00000100 E6 04
Mask with 04H to isolate bit 2, the BREAK key.
6313
If bit 2 is clear (BREAK not pressed), jump to 6322H to exit normally and continue printing.

BREAK key is pressed - pause printing and wait for ENTER to resume.

6315
LD BC,0000H 01 00 00
Load BC with 0000H. This is a delay/debounce parameter for the ROM wait routine at 0060H.
6318
CALL 0060H CD 60 00
Call ROM routine at 0060H. This provides a brief delay to debounce the keyboard and allow the user to release the BREAK key.

[LOOP START] - Wait for ENTER key to resume printing.

631B
LD A,(3840H) 3A 40 38
Load A from 3840H, the keyboard matrix row, to check for key presses.
631E
AND 01HAND 00000001 E6 01
Mask with 01H to isolate bit 0, the ENTER key.
6320
If bit 0 is clear (ENTER not pressed), loop back to 631BH to keep waiting for the user to press ENTER.

[LOOP END] - ENTER pressed. Resume printing.

6322
POP AF F1
Restore AF from the stack. A contains the original character.
6323
POP BC C1
Restore BC from the stack.
6324
POP DE D1
Restore DE from the stack.
6325
POP HL E1
Restore HL from the stack.
6326
RET C9
Return to caller with all registers preserved.

6327H - Output Padding Spaces

This routine outputs padding spaces to align output. It calculates how many spaces are needed based on the difference between line width and current position, then outputs that many spaces. On entry: B = alignment parameter. On exit: Spaces output to current position, or returns immediately if already past alignment point.

6327
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H (e.g., 64 or 80 columns).
632A
SUB B 90
Subtract B (the alignment parameter) from the line width. A now contains the target column.
632B
LD B,A 47
Copy the target column to B.
632C
LD A,(5483H) 3A 83 54
Load A with the current column position from 5483H.
632F
SUB B 90
Subtract target column from current position. A = number of spaces needed to reach target.
6330
RET C D8
If carry is set (current position is past target), return immediately. No padding needed.
6331
RET Z C8
If Z flag is set (current position equals target), return. Already at the right position.
6332
LD B,A 47
Copy the space count to B for the loop counter.

[LOOP START] - Output B spaces.

6333
Call 62C6H to output a space character (20H).
6336
Decrement B and loop back to 6333H if not zero. Continue until all padding spaces are output.

[LOOP END]

6338
RET C9
Return to caller. Output is now aligned to the target column.

6339H - Display Prompt and Get Filename

This routine displays a prompt string at (HL), then collects filename input from the user into the buffer at 5440H. The input is limited by the value in B (maximum characters). On entry: HL = prompt string address, B = maximum input length. On exit: HL = 5440H (input buffer address).

6339
LD DE,5440H 11 40 54
Load DE with 5440H, the address of the input buffer where the filename will be stored.
633C
PUSH BC C5
Save BC onto the stack. B contains the maximum input length (usually 8 for filename, 3 for extension).
633D
PUSH DE D5
Save DE (the buffer address 5440H) onto the stack.
633E
Call the display compressed string routine to show the prompt at (HL) to the user.
6341
POP HL E1
Pop the buffer address into HL. Now HL = 5440H (the input buffer).
6342
POP BC C1
Restore BC. B = maximum input length.
6343
Jump to 6356H to begin collecting keyboard input into the buffer.

6345H - Display String and Wait for Keypress

This routine displays the string at (HL), then waits for the user to press ENTER. It loops until ENTER is pressed. Used for "Press ENTER to continue" prompts.

6345
Call the display compressed string routine to show the message at (HL).

[LOOP START] - Wait for user to press ENTER.

6348
Call 6351H to get keyboard input. Returns with Z flag set if ENTER was pressed.
634B
If Z flag is not set (user pressed something other than ENTER), loop back to 6348H to keep waiting.

[LOOP END] - User pressed ENTER.

634D
RET C9
Return to caller. User has acknowledged by pressing ENTER.

634EH - Display Prompt and Collect Input

This routine displays a prompt string at (HL), then collects keyboard input into the buffer at 5440H. Maximum input length is 64 characters (40H). On entry: HL = prompt string address. On exit: A = first character of input, Z flag set if first char is ENTER (0DH), HL = 5440H.

634E
Call the display compressed string routine to show the prompt at (HL).
6351
LD HL,5440H 21 40 54
Load HL with 5440H, the address of the input buffer.
6354
LD B,40H 06 40
Load B with 40H (64 decimal), the maximum input length.
6356
CALL 0040H CD 40 00
Call ROM routine at 0040H. This is the TRS-80 ROM line input routine that collects characters from the keyboard into the buffer at (HL), maximum B characters.
6359
PUSH HL E5
Save HL (the input buffer address) onto the stack.
635A
PUSH BC C5
Save BC onto the stack.
635B
INC B 04
Increment B. The loop will process B+1 characters (the input plus any remaining buffer positions).

[LOOP START] - Convert all characters in buffer to uppercase.

635C
LD A,(HL) 7E
Load A with the current character from the input buffer at (HL).
635D
Call the lowercase to uppercase conversion routine at 6210H. If A is a lowercase letter (61H-7AH), it's converted to uppercase.
6360
LD (HL),A 77
Store the converted character back to the buffer at (HL).
6361
INC HL 23
Advance HL to the next buffer position.
6362
Decrement B and loop back to 635CH if not zero. Process all characters in the buffer.

[LOOP END] - All characters converted to uppercase.

6364
POP BC C1
Restore BC from the stack.
6365
POP HL E1
Restore HL to point to the start of the input buffer (5440H).
6366
LD A,(HL) 7E
Load A with the first character of the input.
6367
CP 0DH FE 0D
Compare A with 0DH (ENTER). Sets Z flag if the user just pressed ENTER without typing anything.
6369
RET C9
Return to caller. A = first character, Z flag set if input was empty (just ENTER), HL = buffer address.

636AH - Disable Printer Output Mode

This routine flushes the printer buffer, then clears the output mode flags at 5480H to disable printer output. Printer output is controlled by bit 6 of 5480H.

636A
PUSH AF F5
Save AF onto the stack to preserve the caller's registers.
636B
Call the flush printer buffer routine to output any pending data.
636E
XOR A AF
Set A to 0 by XORing it with itself.
636F
LD (5480H),A 32 80 54
Store 0 to 5480H, clearing all output mode flags. This disables printer output (bit 6).
6372
POP AF F1
Restore AF from the stack.
6373
RET C9
Return to caller. Printer output is now disabled.

6374H - Flush Printer Buffer

This routine flushes any pending output and prepares for new output. It sets the output device to printer mode (22H stored at self-modifying location 63ECH) and initializes column position. If the current column is not at line start, a newline is output first.

6374
PUSH AF F5
Save AF onto the stack.
6375
LD A,22H 3E 22
Load A with 22H, the code for printer output mode. This value will be stored in the self-modifying location at 63ECH.
6377
Jump to 637CH to continue the initialization.

6379H - Output Carriage Return to Printer

This routine initializes for screen output mode (00H) and ensures the cursor is at the start of a line.

6379
PUSH AF F5
Save AF onto the stack.
637A
LD A,00H 3E 00
Load A with 00H, the code for screen-only output mode.
637C
PUSH AF F5
Save the output mode code (22H or 00H) onto the stack.
637D
PUSH HL E5
Save HL onto the stack.
637E
LD HL,5483H 21 83 54
Load HL with 5483H, the address of the current column position variable.
6381
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H.
6384
CP (HL) BE
Compare line width with current column. If equal, cursor is at start of line.
6385
If NZ (not at start of line), call 6248H to output a newline. This ensures output starts on a fresh line.
6388
POP HL E1
Restore HL from the stack.
6389
POP AF F1
Pop the output mode code into A.
638A
CP 22H FE 22
Compare A with 22H. Sets Z flag if this is printer mode initialization.
638C
LD (63ECH),A 32 EC 63
Store the output mode code to 63ECH. This is a self-modifying location checked by the output routine to determine where to send characters.
638F
LD A,(5485H) 3A 85 54
Load A with the printer line width from 5485H.
6392
If Z flag is set (printer mode), jump to 6397H to use the printer line width.
6394
LD A,(5486H) 3A 86 54
Load A with the screen line width from 5486H. Used when not in printer mode.
6397
LD (5484H),A 32 84 54
Store the line width to 5484H, the active line width variable.
639A
LD (5483H),A 32 83 54
Store the same value to 5483H, resetting the column position to start of line.
639D
POP AF F1
Restore AF from the stack.
639E
RET C9
Return to caller. Output mode and column position are initialized.

639FH - Enable Printer Output Mode

This routine enables printer output by setting bit 6 of the output mode flags at 5480H. When bit 6 is set, characters are sent to both screen and printer.

639F
LD A,(5480H) 3A 80 54
Load A with the current output mode flags from 5480H.
63A2
SET 6,A CB F7
Set bit 6 of A, the printer output enable flag. When set, output goes to the printer.
63A4
LD (5480H),A 32 80 54
Store the updated flags back to 5480H. Printer output is now enabled.
63A7
RET C9
Return to caller.

63A8H - Disable Printer Output Mode

This routine disables printer output by clearing bit 6 of the output mode flags at 5480H. Output will go to screen only.

63A8
LD A,(5480H) 3A 80 54
Load A with the current output mode flags from 5480H.
63AB
RES 6,A CB B7
Reset bit 6 of A, clearing the printer output enable flag.
63AD
Jump to 63A4H to store the updated flags and return. Printer output is now disabled.

63AFH - Check if Line Counter at Page Boundary

This routine checks if the current line counter (at 5482H) equals 60 (3CH), which indicates a page boundary for printer pagination. On exit: Z flag set if at page boundary (line counter = 3CH).

63AF
LD A,(5482H) 3A 82 54
Load A with the current line counter from 5482H. This tracks lines printed on the current page.
63B2
CP 3CH FE 3C
Compare A with 3CH (60 decimal), the lines per page value. Sets Z flag if at page boundary.
63B4
RET C9
Return to caller. Z flag indicates if we're at a page boundary.

63B5H - Handle End of Line for Printer

This routine handles end-of-line processing for the printer. It checks the output mode, manages page breaks (outputting extra carriage returns at page boundaries), and resets the column position. The self-modifying location at 63ECH determines the current output mode (22H = printer, 00H = screen).

63B5
LD A,(63ECH) 3A EC 63
Load A with the output mode code from 63ECH. This is a self-modifying location set by the initialization routines.
63B8
CP 22H FE 22
Compare A with 22H (printer mode indicator). Z flag set if in printer mode.
63BA
If Z flag is set (printer mode), jump to 63D6H to just reset column position. Printer pagination is handled differently.

Screen mode - check for page boundary and handle form feed.

63BC
LD A,(5482H) 3A 82 54
Load A with the current line counter from 5482H.
63BF
DEC A 3D
Decrement A. Check if we've reached the last line of the page.
63C0
If A is not zero (not at page boundary), jump to 63D3H to update line counter and continue.

At page boundary (line 1). Check if lines-per-page is configured.

63C2
LD A,(5481H) 3A 81 54
Load A with the lines per page setting from 5481H. If 0, page breaks are disabled.
63C5
OR A B7
Test if A is zero. Sets Z flag if lines-per-page is 0 (pagination disabled).
63C6
If Z flag is set (pagination disabled), jump to 63D1H to reset line counter to 60 and continue.

Pagination enabled - output 6 carriage returns for page break.

63C8
LD B,06H 06 06
Load B with 6, the number of carriage returns to output for a page break.

[LOOP START] - Output B carriage returns.

63CA
LD A,0DH 3E 0D
Load A with 0DH, the carriage return character.
63CC
Call the device output routine to send the carriage return.
63CF
Decrement B and loop back to 63CCH if not zero. Output 6 blank lines total.

[LOOP END] - Page break complete.

63D1
LD A,3CH 3E 3C
Load A with 3CH (60 decimal), resetting the line counter to the lines per page value.
63D3
LD (5482H),A 32 82 54
Store A to the line counter at 5482H. This decrements with each line or resets at page boundary.
63D6
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H.
63D9
LD (5483H),A 32 83 54
Store the line width to the column position at 5483H, resetting cursor to start of new line.
63DC
RET C9
Return to caller. Line/page handling complete.

63DDH - Output Multiple Newlines Until Page Boundary

This routine outputs newlines until the line counter reaches a page boundary (60 lines). Register C specifies the maximum number of newlines to output. Used to advance to a new page or create vertical spacing. On entry: C = maximum newline count.

[LOOP START] - Output newlines until page boundary or C reaches zero.

63DD
Call 63AFH to check if we're at a page boundary (line counter = 60). Returns Z flag set if at boundary.
63E0
RET Z C8
If Z flag is set (at page boundary), return immediately. No more newlines needed.
63E1
Call 6248H to output a single newline (carriage return).
63E4
DEC C 0D
Decrement C, the remaining newline count.
63E5
If C is not zero (more newlines allowed), loop back to 63DDH to check boundary and output another newline.

[LOOP END] - Maximum count reached or page boundary found.

63E7
RET C9
Return to caller. Either C newlines output or page boundary reached.

63E8H - Device Output Dispatcher

This routine outputs a character to the current output device(s). It uses a clever self-modifying dispatch mechanism to handle the return path. The routine at 6427H captures the return address and patches it into jump targets at 6434H and 6442H, allowing different return paths depending on how the output completes. On entry: A = character to output.

63E8
Call the output setup routine at 6427H. This saves the return address and patches it into the self-modifying jump targets. After setup, it jumps to a DOS output routine at 0000H (patched).
63EB
After returning from the DOS call, jump to 640FH to handle printer output. This is the "continue to printer" path.

63EDH - Screen Output with Character Filtering

This routine outputs a character to the screen with filtering for non-printable characters. Characters above a configurable threshold (stored at 4370H) are replaced with a period (2EH). Control characters are handled specially. On entry: A = character to output.

63ED
PUSH AF F5
Save AF onto the stack. A contains the character to output.
63EE
LD HL,4370H 21 70 43
Load HL with 4370H, the address of the character filter threshold. Characters above this value are replaced.
63F1
CP (HL) BE
Compare A with the filter threshold at (4370H). If A > threshold, the character is non-printable.
63F2
If carry set (A < threshold), jump to 63F8H. Character is within printable range.
63F4
If Z flag set (A = threshold), jump to 63F8H. Character equals the limit, still printable.
63F6
LD A,2EH 3E 2E
Character exceeds threshold. Replace with 2EH (period/dot). This makes unprintable graphics characters visible as dots.
63F8
CP 20H FE 20
Compare A with 20H (space). Check if character is a printable ASCII character.
63FA
If A >= 20H (printable character), jump to 6404H to output via ROM.

Character is a control code (00H-1FH). Check if it should be displayed.

63FC
CP 0EH FE 0E
Compare A with 0EH. Codes 0EH-1FH are displayable control characters.
63FE
If A >= 0EH, jump to 6407H to skip screen output. These are printer-only control codes.
6400
CP 0AH FE 0A
Compare A with 0AH (line feed). Codes 0AH-0DH are line control characters.
6402
If A < 0AH (codes 00H-09H), jump to 6407H to skip screen output. These low controls don't display.
6404
CALL 003BH CD 3B 00
Call ROM routine at 003BH. This is the TRS-80 ROM display character routine that outputs A to the screen.
6407
POP AF F1
Restore AF. A contains the original character (unfiltered) for printer output.
6408
LD HL,5480H 21 80 54
Load HL with 5480H, the address of the output mode flags.
640B
BIT 6,(HL) CB 76
Test bit 6 of the flags, the printer enable flag.
640D
If bit 6 is clear (printer disabled), jump to 6444H to exit without printer output.

Printer output is enabled. Continue to send character to printer.

640F
CP 0DH FE 0D
Compare A with 0DH (carriage return). CR needs special handling for printer.
6411
If not carriage return, jump to 6422H to output the character directly to printer.

Handle carriage return - check if line has content before sending CR.

6413
LD HL,5483H 21 83 54
Load HL with 5483H, the address of the column position counter.
6416
LD A,(5484H) 3A 84 54
Load A with the line width from 5484H.
6419
SUB (HL) 96
Subtract current column from line width. A = number of characters printed on this line.
641A
If Z (line is empty, no chars printed), jump to 6420H to still output CR.
641C
AND 3FHAND 00111111 E6 3F
Mask with 3FH (63). Check lower 6 bits for position within 64-character boundary.
641E
If result is zero (on 64-character boundary), jump to 6444H to skip CR. Printer auto-wraps at boundaries.
6420
LD A,0DH 3E 0D
Load A with 0DH, the carriage return character.
6422
CALL 0033H CD 33 00
Call ROM routine at 0033H. This is the TRS-80 ROM printer output routine that sends A to the printer.
6425
Jump to 6444H to restore registers and return.

6427H - Output Setup with Self-Modifying Return Path

This routine implements a sophisticated dispatch mechanism using self-modifying code. It captures the return address from the stack and patches it into two jump targets (6434H and 6442H), allowing the output routines to return to different points depending on the execution path. This technique avoids multiple returns and simplifies control flow.

6427
EX (SP),HL E3
Exchange HL with top of stack. HL now contains the return address (63EBH when called from 63E8H), and the original HL is on the stack.
6428
LD (6434H),HL 22 34 64
Store the return address to 6434H. This is a self-modifying location - the JP at 6433H will jump to this address.
642B
POP HL E1
Pop the original HL value back from the stack.
642C
PUSH HL E5
Push HL back onto the stack for later restoration.
642D
PUSH DE D5
Save DE onto the stack.
642E
PUSH BC C5
Save BC onto the stack.
642F
PUSH IX DD E5
Save IX onto the stack.
6431
PUSH IY FD E5
Save IY onto the stack. All index registers preserved for the DOS call.
6433
JP 0000H C3 00 00
Jump to address stored at 6434H-6435H. This is self-modifying - the actual address was patched by the LD at 6428H. Jumps back to 63EBH (after the CALL).

6436H - Alternate Return Path Setup

This routine provides an alternate entry for setting up return path. It patches the address into 6442H instead of 6434H, creating a different return destination.

6436
PUSH HL E5
Push HL onto the stack temporarily.
6437
LD (6442H),HL 22 42 64
Store HL to 6442H, the second self-modifying location. The JP at 6441H will jump to this address.
643A
POP IY FD E1
Pop the value into IY (restoring from stack).
643C
POP IX DD E1
Pop IX from the stack.
643E
POP BC C1
Pop BC from the stack.
643F
POP DE D1
Pop DE from the stack.
6440
POP HL E1
Pop HL from the stack.
6441
JP 0000H C3 00 00
Jump to address stored at 6442H-6443H. This is self-modifying - the actual address was patched earlier.

6444H - Common Exit - Restore Registers and Return

This is the common exit point for the output routines. It restores all saved registers (IY, IX, BC, DE, HL) and returns to the caller.

6444
POP IY FD E1
Restore IY from the stack.
6446
POP IX DD E1
Restore IX from the stack.
6448
POP BC C1
Restore BC from the stack.
6449
POP DE D1
Restore DE from the stack.
644A
POP HL E1
Restore HL from the stack.
644B
RET C9
Return to caller. All registers have been restored to their entry values.

644CH - Read File with Raw Mode Flag Set

This routine sets the raw/track mode flag (bit 6 of 5493H), calls the main file read routine at 6457H, then clears the flag. This wraps the file read operation with raw mode enabled for track-level access.

644C
LD HL,5493H 21 93 54
Load HL with 5493H, the address of the secondary mode flags.
644F
SET 6,(HL) CB F6
Set bit 6 of the flags at (HL), enabling raw/track mode for the file operation.
6451
Call the main file read routine at 6457H. This performs the actual file/sector read operation.
6454
RES 6,(HL) CB B6
Reset bit 6 of the flags at (HL), clearing raw/track mode. HL still points to 5493H.
6456
RET C9
Return to caller with raw mode flag cleared.

6457H - Main File Read Setup

This routine prepares for and executes a DOS file operation. It sets up the FCB flags, calls the DOS @FSPEC routine at 4436H, and handles any errors. On entry: None (uses FCB at 5400H). On exit: Carry set on error, Z flag set if operation succeeded without error code.

6457
XOR A AF
Set A to 0 by XORing with itself. This will be the read operation flag.
6458
Call the FCB setup routine at 6497H. This initializes FCB fields and sets up the self-modifying return path.
645B
CALL 4436H CD 36 44
Call NEWDOS/80 @FSPEC routine at 4436H. This is the file specification/directory search DOS call.
645E
Call the error check routine at 64BCH. This examines the DOS return status and handles any errors.
6461
If carry set (error occurred), jump to 64B3H to store the sector info and exit via self-modifying jump.
6463
If NZ (non-zero error code but not critical), jump to 6471H to exit with registers restored.

Operation succeeded. Determine the operation type indicator character.

6465
CP 06H FE 06
Compare A with 06H. Check if this was a specific file operation type.
6467
LD A,50H 3E 50
Load A with 50H, ASCII for P. This indicates "Protected" or "Password" file mode.
6469
If Z (operation type was 06H), jump to 646DH to store 'P' as the type indicator.
646B
LD A,20H 3E 20
Load A with 20H, ASCII for space. This indicates normal file mode (no special status).
646D
LD (5494H),A 32 94 54
Store the operation type indicator at 5494H. This character ('P' or space) shows the file's status.
6470
CP A BF
Compare A with itself. This always sets the Z flag and clears carry, indicating success.
6471
POP DE D1
Restore DE from the stack (pushed by the setup routine at 6497H).
6472
POP HL E1
Restore HL from the stack.
6473
RET C9
Return to caller. Flags indicate success (Z, NC) or error type.

6474H - Write Sector to Disk

This routine writes a sector to disk. It sets up the FCB for a write operation (80H flag), checks the operation type, and calls the DOS write routine. On exit: Carry set on error.

6474
LD A,80H 3E 80
Load A with 80H, the write operation flag. Bit 7 set indicates a write rather than read.
6476
Call the FCB setup routine at 6497H. Sets up the FCB with the write flag.
6479
LD A,(5494H) 3A 94 54
Load A with the operation type indicator from 5494H. This was set during the read operation.
647C
CP 20H FE 20
Compare A with 20H (space). Check if this is a normal (unprotected) file.
647E
If Z (normal file), jump to 6489H to proceed with the write operation.
6480
CP 50H FE 50
Compare A with 50H ('P'). Check if file is password protected.
6482
If NZ (neither space nor 'P'), jump to 65AAH to display an error message. Invalid operation type.

Password-protected file. Set the protection bit before writing.

6485
EX DE,HL EB
Exchange DE and HL. HL now points to the FCB.
6486
SET 0,(HL) CB C6
Set bit 0 of the FCB byte at (HL). This sets the write-protect flag for the operation.
6488
EX DE,HL EB
Exchange DE and HL back to original positions.
6489
CALL 443CH CD 3C 44
Call NEWDOS/80 DOS routine at 443CH. This is the write sector DOS call.
648C
EX DE,HL EB
Exchange DE and HL. HL now points to FCB for flag cleanup.
648D
RES 0,(HL) CB 86
Reset bit 0 of the FCB byte. Clear the write-protect flag after operation.
648F
EX DE,HL EB
Exchange DE and HL back.
6490
Call the error check routine to examine the write operation result.
6493
If carry set (error), jump to 64B3H to handle the error and exit.
6495
Jump to 6471H to restore registers and return normally.

6497H - FCB Setup with Self-Modifying Return Path

This routine sets up the FCB (File Control Block) for a disk operation and configures the self-modifying return address. It captures the return address from the stack, patches it into 64BAH, and initializes FCB fields. On entry: A = operation flag (00H = read, 80H = write). On exit: FCB prepared, self-modifying jump target set.

6497
EX (SP),HL E3
Exchange HL with top of stack. HL now contains the return address, original HL is on stack.
6498
PUSH DE D5
Save DE onto the stack for later restoration.
6499
LD (64BAH),HL 22 BA 64
Store the return address to 64BAH, the self-modifying jump target. The JP at 64B9H will use this.
649C
LD E,A 5F
Copy the operation flag (00H read or 80H write) from A to E for safekeeping.
649D
LD HL,5491H 21 91 54
Load HL with 5491H, the address of the primary mode flags.
64A0
LD A,(HL) 7E
Load A with the current mode flags from 5491H.
64A1
AND 7FHAND 01111111 E6 7F
Mask off bit 7, clearing any previous error/status flag.
64A3
OR E B3
OR in the operation flag from E. This sets bit 7 for write operations (80H).
64A4
LD (HL),A 77
Store the updated flags back to 5491H.
64A5
LD HL,5401H 21 01 54
Load HL with 5401H, the address of FCB byte 1 (mode/attribute flags).
64A8
RES 7,(HL) CB BE
Reset bit 7 of FCB byte 1. Clear any previous special flag.
64AA
DEC HL 2B
Decrement HL to point to 5400H, the FCB base address (byte 0, drive spec).
64AB
EX DE,HL EB
Exchange DE and HL. DE now points to FCB base (5400H).
64AC
LD HL,(540AH) 2A 0A 54
Load HL with the sector number from FCB bytes 0AH-0BH.
64AF
XOR A AF
Set A to 0.
64B0
LD (5405H),A 32 05 54
Store 0 to 5405H, the byte offset field. Start at beginning of sector.
64B3
LD (540AH),HL 22 0A 54
Store HL back to the sector number field at 540AH (may be updated by caller).
64B6
LD (54A6H),HL 22 A6 54
Also store sector number to 54A6H, a secondary location for tracking.
64B9
JP 0000H C3 00 00
Jump to address at 64BAH-64BBH. This is self-modifying - the actual address was patched by the LD at 6499H.

64BCH - Check DOS Error Status

This routine checks the result of a DOS operation. It examines flags and the error code in A, returning appropriate status or jumping to error display. On entry: Flags from DOS call, A = error code. On exit: Z set if no error, Carry set for critical errors, NZ for warnings.

64BC
If NZ (error flag set from DOS), jump to 64C0H to examine the error code.
64BE
XOR A AF
Set A to 0. Clear any error code, sets Z flag.
64BF
RET C9
Return with Z set and Carry clear, indicating success.
64C0
If Z flag set (error code is 0), jump to 64C5H to display error message.
64C2
CP 06H FE 06
Compare error code with 06H. Code 06H is a special "not found" or "end of file" condition.
64C4
RET Z C8
If error code is 06H, return with Z set. This is not a critical error (e.g., EOF).

64C5H - Display DOS Error Message

This routine displays a DOS error message based on the error code. It saves registers, clears the command line, displays drive/sector status, looks up the error message in the error table at 6BEDH, and prompts for user response. On entry: A = DOS error code, flags from error check. On exit: May jump to retry, skip, or exit based on user input.

64C5
PUSH HL E5
Save HL onto the stack.
64C6
PUSH DE D5
Save DE onto the stack.
64C7
PUSH BC C5
Save BC onto the stack.
64C8
PUSH AF F5
Save AF onto the stack. A contains the DOS error code.
64C9
Call the clear command line routine to prepare the display area for the error message.
64CC
Call the display drive/sector status routine at 65D0H. Shows which drive and sector caused the error.
64CF
LD A,(5491H) 3A 91 54
Load A with the primary mode flags from 5491H.
64D2
BIT 7,A CB 7F
Test bit 7, the write operation flag. Was this a write or read operation?
64D4
If bit 7 is clear (read operation), jump to 64E7H to display read error message.

Write operation error. Select appropriate write error messages.

64D6
LD DE,6E30H 11 30 6E
Load DE with 6E30H, address of write error message suffix.
64D9
Load HL with 6D0EH, address of error message prefix ("WRITE" or similar).
64DC
POP AF F1
Pop AF to get the error code back into A.
64DD
CP 09H FE 09
Compare error code with 09H. Check for write-protect error.
64DF
PUSH AF F5
Push AF back onto the stack for later use.
64E0
If error code ≥ 09H, jump to 64F2H to display the error message.
64E2
LD DE,6E34H 11 34 6E
Load DE with 6E34H, address of alternate write error suffix (for codes < 09H).
64E5
Jump to 64F2H to display the error message.

Read operation error. Set up read error messages.

64E7
LD A,45H 3E 45
Load A with 45H, ASCII for E. This is the "Error" type indicator.
64E9
LD (5494H),A 32 94 54
Store 'E' to the operation type indicator at 5494H.
64EC
LD DE,6E2CH 11 2C 6E
Load DE with 6E2CH, address of read error message suffix.
64EF
Load HL with 6D0BH, address of read error message prefix.
64F2
Call the display compressed string routine. Display the error prefix message from (HL).
64F5
EX DE,HL EB
Exchange DE and HL. HL now points to the suffix message.
64F6
Call display string with newline. Display the error suffix message.

Now look up the specific error message in the error table at 6BEDH.

64F9
POP BC C1
Pop BC. B now contains the error code (was pushed as AF, so A went into high byte position).
64FA
Load HL with 6BEDH, the address of the error message table. Each entry has error code followed by message.

[LOOP START] - Search error table for matching error code.

64FD
LD A,(HL) 7E
Load A with the error code from the current table entry.
64FE
CP B B8
Compare table error code with B (the actual error code we're looking for).
64FF
INC HL 23
Advance HL past the error code byte to the message text.
6500
If Z (error codes match), jump to 652EH to display this error message.

No match. Skip past this error message to the next entry.

6502
LD A,(HL) 7E
Load A with the current byte of the message.
6503
OR A B7
Test if A is zero (end of message marker).
6504
If not zero (not end of message), loop back to 64FDH to check next byte.

Found end of message (00H). Check for end of table (03H).

6506
LD A,(HL) 7E
Load A with the byte after the zero terminator.
6507
CP 03H FE 03
Compare with 03H, the end of table marker.
6509
INC HL 23
Advance HL.
650A
If not end of table, loop to skip any padding and find next entry.
650C
LD A,(HL) 7E
Load the next byte.
650D
OR A B7
Test if zero (true end of table).
650E
If not zero, continue searching from 64FDH.

[LOOP END] - Error code not found in table. Display numeric code.

6510
LD A,(5491H) 3A 91 54
Load A with the mode flags from 5491H.
6513
AND 48HAND 01001000 E6 48
Mask with 48H. Check bits 6 and 3 (raw mode flags).
6515
If zero (normal mode), jump to 651FH to display generic error with code number.
6517
LD A,B 78
Load A with B (the error code).
6518
OR 0C0HOR 11000000 F6 C0
OR with C0H to set bits 7 and 6. This creates a DOS error display code.
651A
CALL 4409H CD 09 44
Call NEWDOS/80 routine at 4409H. This is a DOS error message display routine.
651D
Jump to 6536H to output newline and continue with user prompt.
651F
Load HL with 6E38H, address of "ERROR #" message prefix.
6522
Call display compressed string to show "ERROR #".
6525
LD E,B 58
Copy error code B to E for conversion.
6526
Call numeric conversion routine at 68A7H. Converts E to displayable format.
6529
Call buffer display routine to output the converted number.
652C
Jump to 6536H to continue with newline and prompt.

Found matching error code. Display the error message text.

652E
LD A,(HL) 7E
Load A with the current message byte.
652F
OR A B7
Test if zero (end of message).
6530
INC HL 23
Advance HL past this byte.
6531
If not zero, loop to skip to end of message (we need to find the compressed message after it).
6533
Call display compressed string. Display the error message starting at (HL).
6536
Call output newline routine. Move to next line after the error message.

Check mode flags to determine appropriate user prompt.

6539
LD A,(5492H) 3A 92 54
Load A with flags from 5492H (additional mode flags).
653C
OR A B7
Test if any flags are set.
653D
If NZ (flags set), jump to 6553H for special handling.
653F
LD A,(5493H) 3A 93 54
Load A with secondary mode flags from 5493H.
6542
BIT 6,A CB 77
Test bit 6, the raw/track mode flag.
6544
If raw mode is active, jump to 656FH to restore registers and return.
6546
BIT 1,A CB 4F
Test bit 1 of mode flags.
6548
If bit 1 set, jump to 6558H to display retry prompt.
654A
Load HL with 6D90H, address of "PRESS ANY KEY" message.
654D
Call display and wait for key routine. Show message and wait for any keypress.
6550
Jump to 56C1H, the main command loop entry point.
6553
AND 0E0HAND 11100000 E6 E0
Mask A with E0H to check upper 3 bits.
6555
If upper bits are zero, jump to 6582H for "press any key" handling.

Display retry prompt and get user response (R=retry, S=skip, X=exit).

6558
Load HL with 6E71H, address of "RETRY/SKIP/EXIT" prompt.
655B
Call display prompt and collect input. Show prompt and get user response.
655E
Decrement B and loop back to 6558H if not zero. Allow multiple attempts for valid input.
6560
CP 58H FE 58
Compare A with 58H, ASCII for X (exit).
6562
If user pressed X, jump to 65B4H to exit/abort the operation.
6565
CP 52H FE 52
Compare A with 52H, ASCII for R (retry).
6567
SCF 37
Set the Carry flag. This will be used as a retry indicator.
6568
If user pressed R, jump to 656FH to return with Carry set (retry).
656A
CP 53H FE 53
Compare A with 53H, ASCII for S (skip).
656C
If not S (invalid key), loop back to 6558H to re-prompt.
656E
OR A B7
Clear the Carry flag (user chose Skip). OR A with itself clears carry.
656F
POP BC C1
Restore BC from the stack.
6570
POP DE D1
Restore DE from the stack.
6571
POP HL E1
Restore HL from the stack.
6572
RET C9
Return to caller. Carry set = retry requested, Carry clear = skip/continue.

6573H - Display Error from DE

Entry point that exchanges DE and HL, then displays an error message. Used when the message address is in DE instead of HL.

6573
EX DE,HL EB
Exchange DE and HL. The message address moves from DE to HL.
6574
Jump to 657FH to display the message and wait for keypress.

6576H - Display Unknown Key Error

Entry point for handling unknown/invalid key presses. Displays DOS error code 01 (with C0H prefix) and waits for user acknowledgment.

6576
LD A,01H 3E 01
Load A with 01H, error code for "unknown key" or general input error.
6578
OR 0C0HOR 11000000 F6 C0
OR with C0H to set bits 7 and 6. This formats the code for DOS error display.
657A
CALL 4409H CD 09 44
Call NEWDOS/80 routine at 4409H to display the formatted error message.
657D
Jump to 6582H to flush printer and wait for keypress.

657FH - Display Message and Wait for Any Key

Displays a message from (HL) with printer flush, then waits for any keypress before returning to the main command loop.

657F
Call flush printer and display string with newline. Displays message at (HL).
6582
Call the flush printer buffer routine to ensure all output is sent.
6585
Load HL with 6D89H, address of "PRESS ANY KEY" continuation message.
6588
Call display and wait for keypress. Shows message and waits for user.
658B
Jump to 54C5H, the main command handler. Returns to command loop after error acknowledged.

658EH - Display "INVALID" Error

Entry point for displaying "INVALID" error message from 6E20H.

658E
Load HL with 6E20H, address of "INVALID" error message.
6591
Jump to 657FH to display message and wait for key.

6593H - Display "BEYOND" Error

Entry point for displaying "BEYOND" (out of range) error message from 6E26H.

6593
Load HL with 6E26H, address of "BEYOND" error message (sector beyond disk limit).
6596
Jump to 657FH to display message and wait for key.

6598H - Display Message and Return with Carry Set

Displays error message from 6E0AH, then returns with Carry flag set to indicate error to caller.

6598
Load HL with 6E0AH, address of an error message.
659B
Call display string with newline to show the message.
659E
SCF 37
Set the Carry flag to indicate an error condition to the caller.
659F
RET C9
Return with Carry set. Caller can check C flag for error status.

65A0H - Display Error Message from 6E0FH

Entry point for displaying error message from 6E0FH, returns with Carry set.

65A0
Load HL with 6E0FH, address of another error message.
65A3
Jump to 659BH to display message and return with Carry set.

65A5H - Display Error Message from 6E14H

Entry point for displaying error message from 6E14H, returns with Carry set.

65A5
Load HL with 6E14H, address of another error message.
65A8
Jump to 659BH to display message and return with Carry set.

65AAH - Display "ILLEGAL OPERATION" Error

Entry point for displaying "ILLEGAL OPERATION" (or similar) error from 6E3DH. Used when an invalid operation is attempted.

65AA
Load HL with 6E3DH, address of "ILLEGAL" operation error message.
65AD
Jump to 657FH to display message and wait for key.

65AFH - Display Error Message from 6E59H

Entry point for displaying error message from 6E59H.

65AF
Load HL with 6E59H, address of an error message.
65B2
Jump to 657FH to display message and wait for key.

65B4H - Display "ABORTED" Message

Entry point for displaying "ABORTED" message from 6E85H. Used when user chooses to exit/abort an operation.

65B4
Load HL with 6E85H, address of "ABORTED" message.
65B7
Jump to 657FH to display message and wait for key.

65B9H - Display Error Message from 6DE7H

Entry point for displaying error message from 6DE7H.

65B9
Load HL with 6DE7H, address of an error message.
65BC
Jump to 657FH to display message and wait for key.

65BEH - Display Error Message from 6EE9H

Entry point for displaying error message from 6EE9H.

65BE
Load HL with 6EE9H, address of an error message.
65C1
Jump to 657FH to display message and wait for key.

65C3H - Main Return to Command Loop

Entry point that outputs a newline, displays a message from 6C2DH, and returns to command loop.

65C3
Call output newline routine.
65C6
Load HL with 6C2DH, address of a completion/status message.
65C9
Jump to 657FH to display message and return to command loop.

65CBH - Add A to HL (HL = HL + A)

This utility routine adds the value in A to the 16-bit value in HL. Used for table indexing and address calculations. On entry: A = offset to add, HL = base address. On exit: HL = HL + A.

65CB
ADD A,L 85
Add L to A. A = A + L. If overflow, Carry is set.
65CC
LD L,A 6F
Store result back to L. L = A + original L.
65CD
RET NC D0
If no carry (no overflow), return. HL is now HL + original A.
65CE
INC H 24
Carry occurred, so increment H to propagate the carry to the high byte.
65CF
RET C9
Return with HL = original HL + original A.

65D0H - Display Drive and Sector Status

This routine displays the current drive number, sector number, track, and sector-within-track for error messages and status displays. It retrieves values from the FCB and mode flags, formats them, and outputs to the display. Uses label strings from 6E8DH (drive), 6E90H (track), 6E93H (sector), 6E96H (absolute sector), and 6E9BH.

65D0
LD A,(5406H) 3A 06 54
Load A with the current disk number from FCB byte 6 at 5406H. This is the drive number (0-3).
65D3
Load HL with 6E8DH, address of the "DRIVE" label string.
65D6
Call 660AH to display the drive label and number. A contains drive number, HL contains label.
65D9
Load HL with 6E9BH, address of another status label string.
65DC
LD DE,(54A6H) ED 5B A6 54
Load DE with the sector number from 54A6H. This was saved during the file operation setup.
65E0
LD A,(5491H) 3A 91 54
Load A with the primary mode flags from 5491H.
65E3
AND 48HAND 01001000 E6 48
Mask with 48H to check bits 6 and 3 (memory mode and raw mode flags).
65E5
If either flag is set (special mode), jump to 6604H to display only the sector number without track breakdown.

Normal disk mode - display sector as track + sector-within-track.

65E7
Load HL with 6E96H, address of the "SECTOR" (absolute) label string.
65EA
PUSH DE D5
Save DE (the sector number) onto the stack.
65EB
Call 660DH to display the label and value. DE contains value to display, HL contains label.
65EE
POP HL E1
Pop the sector number into HL for division.
65EF
LD A,(549BH) 3A 9B 54
Load A with sectors per track from 549BH. Used to calculate track and sector-within-track.
65F2
Call the division routine at 6896H. Divides HL by A. Returns quotient in DE (track), remainder in A (sector within track).
65F5
EX DE,HL EB
Exchange DE and HL. HL now contains the track number.
65F6
PUSH AF F5
Save AF (A contains sector within track).
65F7
Load HL with 6E90H, address of the "TRACK" label string.
65FA
Call 660DH to display track label and number. DE contains track number.
65FD
POP AF F1
Restore AF. A = sector within track.
65FE
LD E,A 5F
Copy sector-within-track to E.
65FF
LD D,00H 16 00
Set D to 0. DE now contains sector within track as a 16-bit value.
6601
Load HL with 6E93H, address of the "SEC" (sector within track) label string.
6604
Call 660DH to display the label and sector value.
6607
Jump to 6248H to output a newline and return. Status display complete.

660AH - Display Label with 8-bit Value

Entry point that expands an 8-bit value in A to 16-bit in DE, then displays it with a label. On entry: A = 8-bit value, HL = label string address.

660A
LD E,A 5F
Copy the 8-bit value from A to E.
660B
LD D,00H 16 00
Set D to 0. DE now contains the value as a 16-bit number.

660DH - Display Label with Numeric Value and Decimal Conversion

This routine displays a label string, converts a value to decimal, and outputs it with leading zero suppression. It also shows the value in hex format. On entry: DE = value to display, HL = label string address. Uses buffer at 5487H for conversion.

660D
PUSH DE D5
Save DE (the value to display) onto the stack.
660E
Call display compressed string to output the label from (HL).
6611
Call the numeric format conversion routine at 68AFH. Prepares the display buffer.
6614
Call buffer display routine to output the formatted numeric string.
6617
Load HL with 6EA0H, address of separator/suffix string (e.g., " = " or similar).
661A
Call display compressed string to output the separator.
661D
LD HL,5487H 21 87 54
Load HL with 5487H, the decimal conversion buffer address.
6620
LD B,04H 06 04
Load B with 4, the number of buffer bytes to initialize.

[LOOP START] - Clear the conversion buffer to zeros.

6622
PUSH HL E5
Save HL (buffer start) for later use.
6623
LD (HL),00H 36 00
Store 00H at current buffer position, clearing it.
6625
INC HL 23
Advance to next buffer position.
6626
Decrement B and loop if not zero. Clear all 4 buffer bytes.

[LOOP END] - Buffer cleared.

6628
POP HL E1
Restore HL to point to buffer start (5487H).
6629
POP DE D1
Restore DE, the value to convert.
662A
PUSH HL E5
Save buffer start address again.
662B
Call 6665H to convert DE to hex ASCII and store in buffer at (HL).
662E
POP HL E1
Restore HL to buffer start.
662F
LD B,04H 06 04
Load B with 4, maximum hex digits to display.

[LOOP START] - Output hex digits with leading zero handling.

6631
LD A,(HL) 7E
Load A with current hex digit character from buffer.
6632
CP 3AH FE 3A
Compare with 3AH (one past '9'). Check if this is a letter (A-F) vs digit (0-9).
6634
If digit is '0'-'9', jump to 663BH to check for leading zero.
6636
LD A,30H 3E 30
Character is A-F (hex letter). Load A with '0' to output a leading zero before hex letters.
6638
Call character output to display the leading '0'.
663B
LD A,(HL) 7E
Reload A with the hex digit character.
663C
OR A B7
Test if A is zero (empty/unused digit position).
663D
INC HL 23
Advance to next buffer position.
663E
If character is not zero, call character output to display it.
6641
Decrement B and loop back to 663BH if not zero. Process all 4 hex digits.

[LOOP END] - All hex digits output.

6643
Load HL with 6EA3H, address of "H" suffix string (hex indicator).
6646
Jump to display compressed string to output "H" suffix and return.

6649H - Convert Byte to Hex and Display

Converts a byte in A to two hex ASCII characters in the buffer at 5487H, then displays them. On entry: A = byte to convert. On exit: Two hex characters displayed.

6649
PUSH HL E5
Save HL onto the stack.
664A
PUSH BC C5
Save BC onto the stack.
664B
LD HL,5487H 21 87 54
Load HL with 5487H, the conversion buffer address.
664E
Call 6674H to convert byte A to two hex ASCII characters at (HL). HL advances by 2.
6651
DEC HL 2B
Decrement HL to point back to the second character.
6652
DEC HL 2B
Decrement HL again to point to the first character.
6653
LD B,02H 06 02
Load B with 2, the number of characters to display.
6655
Call buffer display to output the 2 hex characters.
6658
POP BC C1
Restore BC.
6659
POP HL E1
Restore HL.
665A
RET C9
Return to caller.

665BH - Convert DE to Hex and Display with Suffix

Converts the 16-bit value in DE to 4 hex ASCII characters and displays them, followed by the "H" suffix. On entry: DE = 16-bit value to display.

665B
LD A,D 7A
Load A with D, the high byte of the value.
665C
Call 6649H to convert and display the high byte as 2 hex digits.
665F
LD A,E 7B
Load A with E, the low byte of the value.
6660
Call 6649H to convert and display the low byte as 2 hex digits.
6663
Jump to 6643H to display the "H" suffix and return.

6665H - Convert DE to Hex ASCII at (HL)

Converts the 16-bit value in DE to hex ASCII characters stored at (HL). Handles leading zeros by only outputting significant digits. On entry: DE = value to convert, HL = buffer address. On exit: HL points past the stored characters.

6665
LD A,D 7A
Load A with D, the high byte of the value.
6666
OR A B7
Test if D is zero. If high byte is zero, skip it for leading zero suppression.
6667
If D is zero, jump to 666FH to process only the low byte.
6669
Call 6670H to convert the high byte with possible leading zero handling.
666C
LD A,E 7B
Load A with E, the low byte.
666D
Jump to 6674H to convert the low byte (always both nibbles since high byte was non-zero).
666F
LD A,E 7B
High byte was zero. Load A with E, the low byte only.
6670
CP 10H FE 10
Compare A with 10H (16). Check if value needs both nibbles or just one.
6672
If A < 10H (single digit), jump to 667DH to convert just the low nibble.

6674H - Convert Byte to Two Hex ASCII Characters

Converts a byte in A to two hex ASCII characters (high nibble first, then low nibble) and stores them at (HL), advancing HL by 2. On entry: A = byte to convert, HL = destination buffer. On exit: HL = HL + 2.

6674
PUSH AF F5
Save A (the byte to convert) onto the stack.
6675
RRCA 0F
Rotate A right. First of 4 rotations to move high nibble to low position.
6676
RRCA 0F
Rotate A right again.
6677
RRCA 0F
Rotate A right again.
6678
RRCA 0F
Rotate A right a fourth time. High nibble is now in bits 0-3.
6679
Call 667DH to convert the high nibble to ASCII and store at (HL).
667C
POP AF F1
Restore original A. Low nibble is in bits 0-3. Fall through to convert it.

667DH - Convert Nibble to Hex ASCII and Store

Converts the low nibble (bits 0-3) of A to a hex ASCII character ('0'-'9' or 'A'-'F') and stores it at (HL), then increments HL. On entry: A = value with nibble in bits 0-3, HL = destination. On exit: Character stored, HL incremented.

667D
AND 0FHAND 00001111 E6 0F
Mask A with 0FH to isolate the low nibble (bits 0-3). A is now 00H-0FH.
667F
CP 0AH FE 0A
Compare A with 0AH (10). Check if nibble is 0-9 or A-F.
6681
If A < 0AH (0-9), jump to 6685H to skip the letter adjustment.
6683
ADD A,07H C6 07
Add 7 to A. Adjusts for the gap between '9' (39H) and 'A' (41H) in ASCII.
6685
ADD A,30H C6 30
Add 30H ('0') to A. Converts nibble to ASCII hex character ('0'-'9' or 'A'-'F').
6687
LD (HL),A 77
Store the hex ASCII character at (HL).
6688
INC HL 23
Increment HL to point to the next buffer position.
6689
RET C9
Return to caller.

668AH - Block Memory Copy Routine

This routine copies a block of B bytes from the address pointed to by HL (source) to the address pointed to by DE (destination). It is a standard memory block move operation used throughout SUPERZAP for buffer transfers. On entry: HL = source address, DE = destination address, B = number of bytes to copy. On exit: HL and DE point past the copied data, B = 0.

[LOOP START] - Copy B bytes from (HL) to (DE)

668A
LD A,(HL) 7E
Load Register A with the byte at the source address pointed to by HL. Each iteration reads the next byte from the source buffer.
668B
LD (DE),A 12
Store Register A (the byte just read from source) at the destination address pointed to by DE. This copies the byte from source to destination.
668C
INC DE 13
Increment DE to point to the next destination byte. After storing, we advance the destination pointer.
668D
INC HL 23
Increment HL to point to the next source byte. After reading, we advance the source pointer.
668E
Decrement B (the byte counter) and Jump if Not Zero back to 668AH. [LOOP] This repeats until all B bytes have been copied.
6690
RET C9
Return to caller. At this point, all B bytes have been copied from source to destination. HL and DE now point one byte past the end of their respective buffers.

6691H - Compare HL to DE (16-bit Equality)

This routine compares the 16-bit value in HL with the 16-bit value in DE, setting the Z flag if they are equal. This is used to test if two pointers or addresses are identical. On entry: HL = first value, DE = second value. On exit: Z flag set if HL equals DE, NZ flag set if they differ.

6691
LD A,H 7C
Load Register A with the high byte of the first value (H register). This prepares to compare the upper 8 bits of the two 16-bit values.
6692
CP D BA
Compare Register A (high byte of HL) with D (high byte of DE). If the high bytes differ, the Z flag is cleared (NZ condition).
6693
RET NZ C0
Return if Not Zero. If the high bytes H and D are different, return immediately with NZ flag set indicating the values are not equal.
6694
LD A,L 7D
Load Register A with the low byte of the first value (L register). Since high bytes matched, we must now compare the low bytes.
6695
CP E BB
Compare Register A (low byte of HL) with E (low byte of DE). This sets the Z flag if L equals E, completing the 16-bit comparison.
6696
RET C9
Return to caller. The Z flag indicates the result: Z set means HL equals DE, NZ set means they differ.

6697H - Compare HL Against BC:DE Range (Lower Bound Check)

This routine checks if the pointer HL is at or below a range boundary. It compares HL against BC and sets carry if HL is below the range start. This is used for boundary validation in buffer operations. On entry: HL = value to test, BC = first boundary, DE = second boundary. On exit: NZ if out of range, Carry set if HL is below L boundary.

6697
LD A,H 7C
Load Register A with the high byte of the test value (H register). We start by comparing the upper bytes.
6698
CP B B8
Compare Register A (high byte of HL) with B (high byte of BC). This checks if HL's upper byte matches BC's upper byte.
6699
RET NZ C0
Return if Not Zero. If the high bytes differ, the comparison result is already determined - return with NZ indicating HL is not equal to BC.
669A
CP L BD
Compare Register A (which still contains H) with L. This unusual comparison checks if H equals L, setting flags accordingly.
669B
RET C D8
Return if Carry. If the carry flag is set (meaning H is less than L in an unsigned comparison), return early.
669C
LD A,D 7A
Load Register A with D (the high byte of DE, the second boundary value). This prepares for the next comparison.
669D
CP H BC
Compare Register A (D) with H. This checks if the high byte of DE matches the high byte of HL.
669E
RET NZ C0
Return if Not Zero. If D does not equal H, return with NZ indicating the high bytes of DE and HL differ.
669F
LD A,E 7B
Load Register A with E (the low byte of DE). Since high bytes matched, we must compare low bytes.
66A0
CP L BD
Compare Register A (E) with L. This completes the comparison between DE and HL by checking the low bytes.
66A1
RET C9
Return to caller. Flags are set based on the final comparison: Z if DE equals HL, Carry if E is less than L.

66A2H - Compare BC Against DE Range

This routine compares BC against DE and HL as range boundaries. It performs a three-way comparison to determine if BC falls within a valid range. On entry: BC = value to test, DE = one boundary, HL = other boundary. On exit: Flags set based on comparison results.

66A2
LD A,D 7A
Load Register A with D (the high byte of DE). This prepares to compare DE against BC.
66A3
CP B B8
Compare Register A (D) with B. This checks if the high bytes of DE and BC are equal.
66A4
RET NZ C0
Return if Not Zero. If D does not equal B, the values differ significantly - return with NZ flag set.
66A5
CP E BB
Compare Register A (still D) with E. This unusual self-referential comparison checks if D equals E (high and low bytes of DE are the same).
66A6
RET C D8
Return if Carry. If the carry flag is set from the comparison, return early with the carry condition.
66A7
LD A,B 78
Load Register A with B (the high byte of BC). Now we compare BC against HL.
66A8
CP H BC
Compare Register A (B) with H. This checks if the high bytes of BC and HL match.
66A9
RET NZ C0
Return if Not Zero. If B does not equal H, return immediately with NZ indicating BC differs from HL in the high byte.
66AA
LD A,C 79
Load Register A with C (the low byte of BC). Since high bytes matched, compare the low bytes.
66AB
CP L BD
Compare Register A (C) with L. This completes the BC vs HL comparison by checking the low bytes.
66AC
RET C9
Return to caller. Z flag is set if BC equals HL, Carry flag indicates if C is less than L.

66ADH - Compare BC to DE (16-bit Equality)

This routine performs a simple 16-bit comparison between BC and DE, setting the Z flag if they are equal. This is a utility function for comparing two register pairs. On entry: BC = first value, DE = second value. On exit: Z flag set if BC equals DE.

66AD
LD A,B 78
Load Register A with B (the high byte of the first 16-bit value in BC).
66AE
CP D BA
Compare Register A (B) with D. This checks if the high bytes of BC and DE are equal.
66AF
RET NZ C0
Return if Not Zero. If B does not equal D, the 16-bit values are different - return with NZ flag set.
66B0
LD A,C 79
Load Register A with C (the low byte of BC). Since high bytes matched, we must compare low bytes.
66B1
CP E BB
Compare Register A (C) with E (the low byte of DE). This sets the Z flag if C equals E.
66B2
RET C9
Return to caller. Z flag is set if BC equals DE, NZ if they differ.

66B3H - Compare Memory Blocks

This routine compares B bytes starting at (DE) against B bytes starting at (HL). It returns with Z flag set if all bytes match, or NZ flag set at the first mismatch. This is used for search operations and data validation. On entry: DE = first block address, HL = second block address, B = number of bytes to compare. On exit: Z flag set if all bytes match, NZ flag set on first mismatch. HL and DE point past the last compared byte.

[LOOP START] - Compare B bytes at (DE) with bytes at (HL)

66B3
LD A,(DE) 1A
Load Register A with the byte at address pointed to by DE (the first block). Each iteration reads the next byte from the first buffer.
66B4
CP (HL) BE
Compare Register A with the byte at address pointed to by HL (the second block). The Z flag is set if they match, NZ if they differ.
66B5
INC DE 13
Increment DE to point to the next byte in the first block.
66B6
INC HL 23
Increment HL to point to the next byte in the second block.
66B7
RET NZ C0
Return if Not Zero. If the bytes at (DE) and (HL) did not match, return immediately with NZ flag set indicating a mismatch found.
66B8
Decrement B (the byte counter) and Jump if Not Zero back to 66B3H. [LOOP] Continue comparing until all B bytes are checked or a mismatch is found.
66BA
RET C9
Return to caller. Z flag is set because all B bytes matched (the loop completed without finding a mismatch).

66BBH - Check If Character Is Uppercase Letter (A-Z)

This routine checks if the character at (HL) is an uppercase letter (ASCII 41H-5AH, 'A'-'Z'). It uses the carry flag to indicate the result. On entry: HL = pointer to character to test. On exit: NC (No Carry) if character is uppercase letter A-Z, C (Carry) if character is outside this range.

66BB
LD A,(HL) 7E
Load Register A with the character at the address pointed to by HL. This is the character to be tested.
66BC
CP 41H FE 41
Compare Register A with 41H (ASCII A). If A is less than 'A', the carry flag is set.
66BE
CCF 3F
Complement Carry Flag. This inverts the carry flag: if A was less than 'A' (carry was set), carry is now clear; if A was >= 'A' (carry was clear), carry is now set.
66BF
RET NC D0
Return if No Carry. After the CCF, NC means the character was below 'A' (not an uppercase letter) - return with this indication.
66C0
CP 5BH FE 5B
Compare Register A with 5BH (one past ASCII Z). If A is less than 5BH (meaning A-Z), carry is set; if A >= 5BH, carry is clear.
66C2
RET C9
Return to caller. Carry flag indicates the result: C (Carry set) means character is in range A-Z (valid uppercase), NC means character is 5BH or above (not uppercase letter).

66C3H - Check If Character Is Uppercase Letter (A-Z) - Alternate Entry

This routine is an alternate entry point that checks if the character at (HL) is an uppercase letter, with slightly different flag behavior. On entry: HL = pointer to character. On exit: Carry flag indicates range validity.

66C3
LD A,(HL) 7E
Load Register A with the character at the address pointed to by HL.
66C4
CP 41H FE 41
Compare Register A with 41H (ASCII A). Sets carry if A is less than 'A'.
66C6
Jump Relative if Carry to 66D5H (the digit check routine). If character is below 'A', it might still be a valid digit 0-9.
66C8
CP 5BH FE 5B
Compare Register A with 5BH (one past Z). This checks if the character is in the range A-Z.
66CA
RET C9
Return to caller. If A was in range 41H-5AH (A-Z), carry is set. If A >= 5BH, carry is clear.

66CBH - Check If Character Is Valid Hex Digit (A-F)

This routine checks if Register A contains a valid hexadecimal letter digit (A-F, ASCII 41H-46H). On entry: A = character to test. On exit: NC if character is G or above (invalid hex letter), C if character is A-F (valid hex letter), or falls through to digit check.

66CB
CP 47H FE 47
Compare Register A with 47H (ASCII G). Hex digits only go up to F (46H), so G and above are invalid hex letters.
66CD
RET NC D0
Return if No Carry. If A >= 'G' (47H), the character is not a valid hex letter - return with NC indicating invalid.
66CE
CP 41H FE 41
Compare Register A with 41H (ASCII A). This checks the lower bound for hex letters.
66D0
CCF 3F
Complement Carry Flag. Inverts the carry: if A < 'A', carry was set, now clear; if A >= 'A', carry was clear, now set.
66D1
RET C D8
Return if Carry. After CCF, C means A >= 'A' and (from earlier check) A < 'G', so it's a valid hex letter A-F.
66D2
Jump Relative unconditionally to 66D5H. Character is below 'A', so check if it's a valid digit 0-9.

66D4H - Load Character and Check If Digit

This is an alternate entry point that loads a character from (HL) and checks if it's a digit 0-9. On entry: HL = pointer to character. On exit: C if digit 0-9, NC if not a digit.

66D4
LD A,(HL) 7E
Load Register A with the character at the address pointed to by HL. This is the character to test.

Fall through to digit validation at 66D5H

66D5H - Check If Character Is Digit (0-9)

This routine checks if Register A contains a decimal digit character (ASCII 30H-39H, '0'-'9'). It sets the carry flag if the character is a valid digit. On entry: A = character to test. On exit: C (Carry set) if character is a digit 0-9, NC (No Carry) if not a digit.

66D5
CP 3AH FE 3A
Compare Register A with 3AH (one past ASCII 9). If A is '0'-'9' (30H-39H), carry is set; if A >= ':' (3AH), carry is clear.
66D7
RET NC D0
Return if No Carry. If A >= 3AH, the character is not a digit (it's ':' or above) - return with NC.
66D8
CP 30H FE 30
Compare Register A with 30H (ASCII 0). This checks the lower bound for digits.
66DA
CCF 3F
Complement Carry Flag. Inverts carry: if A < '0', carry was set, now clear; if A >= '0', carry was clear, now set.
66DB
RET C9
Return to caller. Carry flag indicates result: C means character is in range '0'-'9' (valid digit), NC means it's below '0' (invalid).

66DCH - Prompt for TO Address Input

This routine displays the "TO?" prompt and collects a 16-bit address value from the user. It is used when SUPERZAP needs a destination address, such as for copy operations. The routine loops until valid input is provided. On entry: None. On exit: DE = validated address value, HL points past the input.

66DC
LD HL,6D6DH 21 6D 6D
Load HL with 6D6DH, the address of the compressed string "TO?" prompt message in the string table.
66DF
Jump Relative unconditionally to 66E4H to display the prompt and collect the address input. This shares code with the "FR?" prompt routine.

66E1H - Prompt for FROM Address Input

This routine displays the "FR?" (FROM?) prompt and collects a 16-bit address value from the user. It is used when SUPERZAP needs a source address. On entry: None. On exit: DE = validated address value, HL points past the input.

66E1
LD HL,6D71H 21 71 6D
Load HL with 6D71H, the address of the compressed string "FR?" (FROM?) prompt message in the string table.

Fall through to common prompt and input collection code at 66E4H

66E4H - Common Address Input Loop

This is the common code for prompting and collecting a 16-bit address value. It displays the prompt at (HL), collects user input, and validates it via the 677BH routine. If validation fails (carry set), it loops back to re-prompt. On entry: HL = address of prompt string. On exit: DE = validated address value, NC (No Carry) on success.

[LOOP START] - Prompt and collect address input until valid

66E4
PUSH HL E5
Push HL onto the stack to preserve the prompt string address. We need to keep this in case we need to re-prompt after an error.
66E5
Call 634EH (Display prompt and collect input). This displays the compressed string at (HL) and collects user keyboard input into the input buffer.
66E8
Call 677BH (Parse and validate address input). This routine parses the user's hex input, validates the value, and stores the result in DE. Returns carry set on error.
66EB
POP HL E1
Pop HL from the stack to restore the prompt string address.
66EC
Jump Relative if Carry back to 66E4H. [LOOP] If the input was invalid (carry set from 677BH), re-display the prompt and try again.
66EE
RET C9
Return to caller. Input was valid, DE contains the parsed 16-bit address value, and NC is set.

66EFH - Prompt for Granule Number Input

This routine displays the "GR?" (Granule?) prompt and collects a granule number from the user. Granules are allocation units on the disk (typically 5 sectors each). The routine validates that the value is within the valid granule range. On entry: None. On exit: Granule number stored at 54AEH, NC on success, C on error.

[LOOP START] - Prompt and collect granule number until valid

66EF
LD HL,6D75H 21 75 6D
Load HL with 6D75H, the address of the compressed string "GR?" (Granule?) prompt message.
66F2
Call 634EH (Display prompt and collect input). This displays the granule prompt and collects the user's response into the input buffer.
66F5
Call 66FBH (Validate granule input). This parses and validates the granule number, storing it at 54AEH if valid.
66F8
Jump Relative if Carry back to 66EFH. [LOOP] If the granule number was invalid (carry set), re-display the prompt and try again.
66FA
RET C9
Return to caller. Valid granule number is stored at 54AEH (granule number variable).

66FBH - Validate and Store Granule Number

This routine validates a granule number input. It parses the hex value, checks that it fits in a single byte (high byte must be zero), and stores it at 54AEH. On entry: HL = pointer to input buffer. On exit: NC and value at 54AEH on success, C on error with error message displayed.

66FB
Call 67E5H (Parse hex value with terminator check). This parses the input and returns the value in DE. Returns carry set on parse error or if input is empty.
66FE
PUSH HL E5
Push HL onto the stack to preserve the input pointer position after parsing.
66FF
PUSH AF F5
Push AF onto the stack to preserve the flags from the parse operation.
6700
Jump Relative if Carry to 670AH (error handler). If parsing failed, display an error message.
6702
LD A,E 7B
Load Register A with E (the low byte of the parsed value). This is the granule number if valid.
6703
LD (54AEH),A 32 AE 54
Store Register A at 54AEH (the granule number variable). This saves the granule value for later use.
6706
LD A,D 7A
Load Register A with D (the high byte of the parsed value). For a valid granule, this must be zero.
6707
OR A B7
OR Register A with itself. This sets the Z flag if A is zero (granule number fits in one byte), NZ if the value exceeds 255.
6708
Jump Relative if Zero to 6725H (success exit). If the high byte is zero, the granule number is valid - exit with success.
670A
LD HL,6E04H 21 04 6E
Load HL with 6E04H, the address of the compressed error message string (value out of range or invalid).
670D
Jump Relative to 672BH (display error and return with carry). Display the error message and return indicating failure.

670FH - Parse and Validate Drive Number

This routine parses a drive number from the input buffer and validates it. Valid drive numbers are 0-3 (single byte values). If valid, the drive number is stored at both 5406H (FCB drive byte) and 5499H (working drive variable), and the drive is selected via 67B5H. On entry: HL = pointer to input. On exit: NC on success, C on error with message displayed.

670F
Call 67EDH (Parse hex value with special handling). This parses the input value into DE, checking for terminators and special characters.
6712
PUSH HL E5
Push HL onto the stack to preserve the input pointer.
6713
PUSH AF F5
Push AF onto the stack to preserve the flags.
6714
Jump Relative if Carry to 6728H. If parsing failed (carry set), jump to display "INVALID DRIVE" error.
6716
LD A,D 7A
Load Register A with D (the high byte of the parsed value). For a valid drive number, this must be zero.
6717
OR A B7
OR Register A with itself. Sets Z flag if A is zero (value fits in one byte), NZ if value exceeds 255.
6718
Jump Relative if Not Zero to 6728H. If high byte is non-zero, the value is too large - display "INVALID DRIVE" error.
671A
LD A,E 7B
Load Register A with E (the drive number, 0-3).
671B
LD (5406H),A 32 06 54
Store Register A at 5406H (the FCB drive byte at offset 6 in the File Control Block at 5400H). This sets the drive for file operations.
671E
LD A,E 7B
Load Register A with E again (the drive number). Redundant but ensures A has the correct value.
671F
LD (5499H),A 32 99 54
Store Register A at 5499H (the working drive variable). This is used for display and calculations.
6722
Call 67B5H (Select drive and get disk parameters). This selects the drive and reads its format parameters (tracks, sectors per track, etc.).

Fall through to success exit at 6725H

6725H - Input Validation Success Exit

This is the common success exit point for input validation routines. It restores saved registers and returns with NC (No Carry) indicating the input was valid. On entry: AF and HL saved on stack. On exit: NC (success), registers restored.

6725
POP AF F1
Pop AF from the stack to restore the flags saved earlier. The carry flag will be clear (success).
6726
POP HL E1
Pop HL from the stack to restore the input pointer.
6727
RET C9
Return to caller. NC (No Carry) indicates success, input value is valid and stored appropriately.

6728H - Display "Invalid Drive" Error

This entry point is used when a drive number validation fails. It loads the "INVALID DRIVE" error message address and falls through to the common error display routine. On entry: AF and HL on stack. On exit: C (Carry set) indicating error.

6728
LD HL,6DEBH 21 EB 6D
Load HL with 6DEBH, the address of the compressed string "INVALID DRIVE" error message.

Fall through to common error display at 672BH

672BH - Display Error Message and Return with Carry

This is the common error exit routine. It displays the error message pointed to by HL, restores saved registers, sets the carry flag, and returns. All input validation routines use this to report errors. On entry: HL = error message address, AF and original HL on stack. On exit: C (Carry set) indicating error.

672B
Call 6245H (Display compressed string with newline). This displays the error message at (HL) followed by a carriage return.
672E
POP AF F1
Pop AF from the stack to restore the original flags (these will be overwritten by SCF below).
672F
POP HL E1
Pop HL from the stack to restore the input pointer.
6730
SCF 37
Set Carry Flag. This indicates an error condition to the calling routine.
6731
RET C9
Return to caller. Carry is set indicating the input validation failed.

6732H - Parse and Validate Sector-Within-Track Number

This routine parses a sector number (within the current track) from the input buffer and validates it against the disk's sectors-per-track value. Valid sector numbers range from 0 to (sectors_per_track - 1). If valid, the sector number is stored at 549EH. On entry: HL = pointer to input. On exit: NC on success, C on error with message displayed.

6732
Call 67EDH (Parse hex value with special handling). This parses the input value into DE, handling terminators and special characters.
6735
PUSH HL E5
Push HL onto the stack to preserve the input pointer position.
6736
PUSH AF F5
Push AF onto the stack to preserve the flags from the parse operation.
6737
Jump Relative if Carry to 674CH. If parsing failed, jump to display "INVALID SECTOR" error.
6739
LD A,D 7A
Load Register A with D (the high byte of the parsed value). For a valid sector, this must be zero.
673A
OR A B7
OR Register A with itself. Sets Z flag if A is zero, meaning the value fits in a single byte.
673B
Jump Relative if Not Zero to 674CH. If high byte is non-zero, value is too large - display "INVALID SECTOR" error.
673D
Call 67B5H (Select drive and get disk parameters). This ensures the disk parameters are current, including sectors per track at 430DH.
6740
LD HL,430DH 21 0D 43
Load HL with 430DH, the address of the sectors per track value in the DOS workspace. This is the maximum valid sector number + 1.
6743
LD A,E 7B
Load Register A with E (the sector number entered by the user).
6744
CP (HL) BE
Compare Register A with the byte at (HL), which is the sectors per track count. If A >= (HL), the sector number is invalid.
6745
Jump Relative if No Carry (A >= sectors_per_track) to 674CH. The entered sector number is too high - display error.
6747
LD (549EH),A 32 9E 54
Store Register A at 549EH (the sector within track variable). This is the validated sector number for operations.
674A
Jump Relative to 6725H (success exit). Sector number is valid - return with NC.
674C
LD HL,6DEFH 21 EF 6D
Load HL with 6DEFH, the address of the compressed string "INVALID SECTOR" error message.
674F
Jump Relative to 672BH (display error and return with carry). Display the error and indicate failure.

6751H - Parse and Validate Track Number

This routine parses a track number from the input buffer and validates it against the disk's track count. Valid track numbers range from 0 to (tracks - 1). The track count is stored at 549BH after drive selection. If valid, the track number is stored at 54A0H. On entry: HL = pointer to input. On exit: NC on success, C on error with message displayed.

6751
Call 67E5H (Parse hex value with terminator check). This parses the track number into DE.
6754
PUSH HL E5
Push HL onto the stack to preserve the input pointer.
6755
PUSH AF F5
Push AF onto the stack to preserve the flags.
6756
Jump Relative if Carry to 676BH. If parsing failed, jump to display "INVALID TRACK" error.
6758
LD A,D 7A
Load Register A with D (the high byte of the parsed value). For a valid track, this must be zero.
6759
OR A B7
OR Register A with itself. Sets Z flag if A is zero.
675A
Jump Relative if Not Zero to 676BH. If high byte is non-zero, value exceeds 255 - display "INVALID TRACK" error.
675C
Call 67B5H (Select drive and get disk parameters). This ensures 549BH contains the current disk's track count.
675F
LD HL,549BH 21 9B 54
Load HL with 549BH, the address of the tracks per disk variable (set by 67B5H from the disk's PDRIVE parameters).
6762
LD A,E 7B
Load Register A with E (the track number entered by the user).
6763
CP (HL) BE
Compare Register A with the byte at (HL), which is the total tracks on the disk. If A >= (HL), the track number is invalid.
6764
Jump Relative if No Carry (A >= tracks) to 676BH. The entered track number is beyond the disk - display error.
6766
LD (54A0H),A 32 A0 54
Store Register A at 54A0H (the current track number variable). This is the validated track for operations.
6769
Jump Relative to 6725H (success exit). Track number is valid - return with NC.
676B
LD HL,6DF3H 21 F3 6D
Load HL with 6DF3H, the address of the compressed string "INVALID TRACK" error message.
676E
Jump Relative to 672BH (display error and return with carry). Display the error and indicate failure.

6770H - Parse Hex Value with Error Check

This routine parses a hex value and returns with carry set on any error. Unlike other routines, it returns immediately on success (NC) without storing the value. Used as a validation-only check. On entry: HL = pointer to input. On exit: DE = parsed value, NC on success, C on error with message displayed.

6770
Call 67E5H (Parse hex value with terminator check). This parses the input into DE.
6773
RET NC D0
Return if No Carry. If parsing succeeded, return immediately with NC and the value in DE.
6774
PUSH HL E5
Push HL onto the stack to preserve the input pointer.
6775
PUSH AF F5
Push AF onto the stack to preserve the flags.
6776
LD HL,6DFFH 21 FF 6D
Load HL with 6DFFH, the address of a general input error message (value invalid or out of range).
6779
Jump Relative to 672BH (display error and return with carry). Display the error message and return with carry set.

677BH - Parse and Store 16-bit Address Value

This routine parses a 16-bit hex address from the input and stores it at 54ACH. It validates that the value is non-zero (zero is typically an invalid address for SUPERZAP operations). On entry: HL = pointer to input. On exit: DE = parsed value, value at 54ACH, NC on success, C on error.

677B
Call 67E5H (Parse hex value with terminator check). This parses the 16-bit address into DE.
677E
PUSH HL E5
Push HL onto the stack to preserve the input pointer.
677F
PUSH AF F5
Push AF onto the stack to preserve the flags.
6780
Jump Relative if Carry to 678AH. If parsing failed, jump to display error message.
6782
LD (54ACH),DE ED 53 AC 54
Store DE at 54ACH (the address value variable). This saves the 16-bit address for later operations.
6786
LD A,D 7A
Load Register A with D (the high byte of the address).
6787
OR E B3
OR Register A with E. This sets Z flag if DE is zero (both bytes are zero), NZ if DE is non-zero.
6788
Jump Relative if Not Zero to 6725H (success exit). If the address is non-zero, it's valid - return with NC.
678A
LD HL,6DFCH 21 FC 6D
Load HL with 6DFCH, the address of the "INVALID ADDRESS" error message (value is zero or parse failed).
678D
Jump Relative to 672BH (display error and return with carry). Display the error and return with carry set.

678FH - Prompt for Disk Parameters (Drive, Sector)

This routine displays a prefix message from (HL), then prompts for drive number and absolute sector number. It combines multiple input prompts into a single operation for disk access setup. The prompt at 6D50H asks for "DRIVE,SECTOR". On entry: HL = prefix message address. On exit: Drive at 5406H/5499H, sector at 54A2H, NC on success.

678F
Call 6255H (Display compressed string). This displays a prefix message at (HL) before the drive/sector prompt.

Fall through to the main sector parameter collection routine

6792H - Get Sector Parameters from User

This routine prompts the user for drive and absolute sector number using the combined prompt "DRIVE,SECTOR?" at 6D50H. It validates each input and stores the results. The routine handles ENTER-only input (returning carry set with Z flag) as a special case for "use current values". On entry: None. On exit: Drive at 5406H/5499H, sector at 54A2H, NC on success, C+Z if ENTER pressed without input.

6792
LD HL,6D50H 21 50 6D
Load HL with 6D50H, the address of the compressed string "DRIVE,SECTOR?" prompt.
6795
Call 634EH (Display prompt and collect input). This displays the prompt and collects the user's response into the input buffer.
6798
SCF 37
Set Carry Flag. This prepares the carry flag for the case where the user just pressed ENTER.
6799
RET Z C8
Return if Zero. If 634EH returned with Z set (user pressed ENTER with no input), return with C+Z indicating "use current values".
679A
Call 670FH (Parse and validate drive number). This parses the drive number from the input and stores it at 5406H and 5499H.
679D
RET C D8
Return if Carry. If the drive number was invalid, return with carry set indicating error.
679E
Call 67E5H (Parse hex value with terminator check). This parses the sector number from the remaining input.
67A1
PUSH HL E5
Push HL onto the stack to preserve the input pointer.
67A2
PUSH AF F5
Push AF onto the stack to preserve the flags.
67A3
Jump Relative if Carry to 67AFH. If parsing the sector number failed, jump to display error.
67A5
LD (54A2H),DE ED 53 A2 54
Store DE at 54A2H (the current absolute sector number variable). This is the target sector for the operation.
67A9
Call 67B5H (Select drive and get disk parameters). This selects the drive and retrieves the disk geometry.
67AC
Jump to 6725H (success exit). Both drive and sector are valid - return with NC.
67AF
LD HL,6DF7H 21 F7 6D
Load HL with 6DF7H, the address of the compressed string "INVALID SECTOR" error message (for absolute sector).
67B2
Jump to 672BH (display error and return with carry). Display the error and indicate failure.

67B5H - Select Drive and Get Disk Parameters

This routine selects the current drive (from 5406H) and retrieves the disk's format parameters from NEWDOS/80's PDRIVE table. It stores the tracks-per-disk at 549BH and 549CH, and calculates the maximum sector number (tracks × sectors_per_track) at 54A8H. This is called whenever drive parameters are needed for validation. On entry: 5406H contains drive number (0-3). On exit: 549BH = tracks per disk, 549CH = tracks per disk (copy), 54A8H = maximum sector count. All registers preserved.

67B5
PUSH AF F5
Push AF onto the stack to preserve the flags and accumulator.
67B6
PUSH HL E5
Push HL onto the stack to preserve HL.
67B7
PUSH DE D5
Push DE onto the stack to preserve DE.
67B8
PUSH BC C5
Push BC onto the stack to preserve BC.
67B9
LD A,(5406H) 3A 06 54
Load Register A with the byte at 5406H (the current drive number, 0-3, stored in the FCB at offset 6).
67BC
LD DE,5400H 11 00 54
Load DE with 5400H, the address of SUPERZAP's File Control Block (FCB). This is passed to the DOS call.
67BF
Call 445EH (NEWDOS/80 drive select and PDRIVE lookup). This selects the drive and populates the DOS workspace with the disk's format parameters.
67C2
Jump if Not Zero to 6578H (error handler). If the DOS call failed (NZ returned), jump to handle the disk error.
67C5
LD A,(430EH) 3A 0E 43
Load Register A with the byte at 430EH (the number of tracks on this disk from the DOS workspace, populated by the PDRIVE call).
67C8
LD (549BH),A 32 9B 54
Store Register A at 549BH (SUPERZAP's tracks per disk variable). This is used for track number validation.
67CB
LD A,(430FH) 3A 0F 43
Load Register A with the byte at 430FH (another copy of tracks per disk or a related parameter from DOS workspace).
67CE
LD (549CH),A 32 9C 54
Store Register A at 549CH (a secondary copy of the tracks value, used in some calculations).
67D1
LD A,(430DH) 3A 0D 43
Load Register A with the byte at 430DH (the sectors per track value from DOS workspace).
67D4
LD L,A 6F
Load Register L with A (the sectors per track). This prepares for the multiplication.
67D5
LD H,00H 26 00
Load Register H with 00H. HL now contains the sectors per track as a 16-bit value (00nn).
67D7
LD A,(549BH) 3A 9B 54
Load Register A with the byte at 549BH (the tracks per disk we just stored).
67DA
Call 687DH (8-bit by 16-bit multiply: HL = HL × A). This calculates total sectors = sectors_per_track × tracks.
67DD
LD (54A8H),HL 22 A8 54
Store HL at 54A8H (the maximum sector number variable). This is the total number of sectors on the disk, used for sector validation.
67E0
POP BC C1
Pop BC from the stack to restore BC.
67E1
POP DE D1
Pop DE from the stack to restore DE.
67E2
POP HL E1
Pop HL from the stack to restore HL.
67E3
POP AF F1
Pop AF from the stack to restore the flags and accumulator.
67E4
RET C9
Return to caller. Disk parameters are now stored at 549BH, 549CH, and 54A8H.

67E5H - Parse Hex Value with Terminator Validation

This routine parses a hex value from the input buffer at (HL) and validates the terminator. It calls 67EDH to do the actual parsing, then checks that the input was properly terminated (ENTER or comma). If the input ends with something unexpected, it jumps to 65A0H for error handling. On entry: HL = pointer to input buffer. On exit: DE = parsed value, HL points past the value, NC on success with proper terminator, C on error.

67E5
Call 67EDH (Parse hex input with special handling). This parses the hex value into DE and sets flags based on the terminator.
67E8
RET C D8
Return if Carry. If parsing failed (no valid digits, or special exit at 6598H), return with carry set indicating error.
67E9
Jump if Not Zero to 65A0H (syntax error handler). If 67EDH returned with NZ (invalid terminator character), jump to display syntax error.
67EC
RET C9
Return to caller. Value is in DE, NC and Z indicate success with valid terminator (ENTER or comma).

67EDH - Parse Hex Input with Special Character Handling

This routine parses a hexadecimal value from the input buffer. It handles special terminators: ENTER (0DH) returns via 6598H with carry, comma (2CH) advances HL and returns via 65A5H. It also supports optional drive letter prefix (A-H) for extended addressing and 'H' suffix for explicit hex notation. On entry: HL = pointer to input buffer. On exit: DE = parsed 16-bit value, HL points to terminator or past it, Z flag set if valid terminator, C flag set on parse error or empty input.

67ED
LD A,(HL) 7E
Load Register A with the first character at the input buffer position pointed to by HL.
67EE
CP 0DH FE 0D
Compare Register A with 0DH (ASCII carriage return/ENTER). Check if input is empty or we've reached end of input.
67F0
Jump if Zero to 6598H. If the first character is ENTER, the input is empty - jump to special exit that returns with carry set and Z flag.
67F3
CP 2CH FE 2C
Compare Register A with 2CH (ASCII comma). Check if we're at a field separator.
67F5
Jump if Zero to 65A5H. If the character is a , comma, jump to special exit that advances past the comma and returns with appropriate flags.
67F8
PUSH HL E5
Push HL onto the stack to save the starting position of the input for potential backup.
67F9
Call 6822H (Parse decimal digits into DE). This attempts to parse the input as a decimal number first.
67FC
POP BC C1
Pop the saved starting position into BC (instead of HL). BC now holds the original input position.
67FD
LD A,(HL) 7E
Load Register A with the terminator character after the parsed number (HL was advanced by 6822H).
67FE
SUB 41H D6 41
Subtract 41H (ASCII A) from Register A. This converts 'A'-'H' to values 0-7, testing if the terminator is a drive letter.
6800
CP 08H FE 08
Compare Register A with 08H. If A < 8, the character was a letter A-H (valid drive designator).
6802
Jump Relative if No Carry (A >= 8) to 680FH. If the character is not a drive letter A-H, skip the drive letter handling.
6804
LD H,B 60
Load Register H with B. Restore HL to the original starting position saved in BC.
6805
LD L,C 69
Load Register L with C. HL now points back to the beginning of input for re-parsing as hex.
6806
Call 684FH (Parse hexadecimal digits into DE). This re-parses the input as a hex number instead of decimal.
6809
LD A,(HL) 7E
Load Register A with the character at (HL), which should be the terminator after the hex number.
680A
CP 48H FE 48
Compare Register A with 48H (ASCII H). Check if the terminator is the explicit hex suffix 'H'.
680C
INC HL 23
Increment HL to point past the current character. This advances past the 'H' if present, or to the next position.
680D
Jump Relative if Not Zero to 6820H (error exit). If the terminator was not 'H', this is a syntax error - set carry and return.

At this point, we had a valid hex number with 'H' suffix, check for proper termination

680F
LD A,(HL) 7E
Load Register A with the next character at (HL), which should be a valid terminator after the number.
6810
CP 0DH FE 0D
Compare Register A with 0DH (ASCII ENTER). Check if input ends with carriage return.
6812
RET Z C8
Return if Zero. If the terminator is ENTER, return with Z flag set (valid terminator) and NC (success).
6813
CP 2CH FE 2C
Compare Register A with 2CH (ASCII comma). Check if input has a field separator.
6815
Jump if Not Zero to 681BH. If the terminator is not a comma, check for special 'X' character.
6818
INC HL 23
Increment HL to point past the comma. This positions HL at the start of the next field.
6819
OR A B7
OR Register A with itself. Since A contains 2CH (comma), this clears the carry flag and sets NZ. However, the important effect is clearing carry.
681A
RET C9
Return to caller. HL points past the comma, NC indicates success, NZ indicates comma terminator (not ENTER).
681B
CP 58H FE 58
Compare Register A with 58H (ASCII X). Check if the terminator is the special exit/cancel character.
681D
Jump if Zero to 54C5H. If the user typed X, jump to the abort/exit handler which cancels the current operation.
6820
SCF 37
Set Carry Flag. This indicates a parse error - invalid terminator character.
6821
RET C9
Return to caller with carry set indicating the input was invalid (bad terminator).

6822H - Parse Decimal Number from Input

This routine parses a decimal (base 10) number from the input buffer at (HL) into DE. It accumulates digits by multiplying the running total by 10 and adding each new digit. The routine stops when it encounters a non-digit character. On entry: HL = pointer to input buffer. On exit: DE = parsed decimal value, HL points to first non-digit character, NC on success, C if no digits found or overflow.

6822
LD DE,0000H 11 00 00
Load DE with 0000H. Initialize the accumulator to zero before parsing digits.

[LOOP START] - Parse decimal digits, accumulating value in DE

6825
Call 682CH (Process one decimal digit). This reads the next character, validates it as a digit 0-9, and accumulates it into DE (DE = DE × 10 + digit).
6828
RET C D8
Return if Carry. If 682CH returned with carry set, the character was not a valid digit - stop parsing and return with current value in DE.
6829
INC HL 23
Increment HL to point to the next character in the input buffer.
682A
Jump Relative back to 6825H. [LOOP] Continue processing digits until a non-digit is found.

682CH - Process One Decimal Digit

This routine processes a single decimal digit from the input. It validates the character at (HL) is a digit 0-9, then multiplies the current value in DE by 10 and adds the new digit. The multiplication is done as DE = DE × 2 × 2 + DE × 2 = DE × 10. On entry: HL = pointer to character, DE = current accumulated value. On exit: DE = new accumulated value (DE × 10 + digit), NC if valid digit processed, C if not a digit or overflow.

682C
LD A,(HL) 7E
Load Register A with the character at the address pointed to by HL.
682D
Call 66D5H (Check if character is digit 0-9). Returns with carry set if character is a valid decimal digit.
6830
CCF 3F
Complement Carry Flag. Inverts the result: now NC means valid digit, C means not a digit.
6831
RET C D8
Return if Carry. If the character is not a digit, return with carry set to signal end of number.
6832
SUB 30H D6 30
Subtract 30H (ASCII 0) from Register A. This converts the ASCII digit to its numeric value (0-9).
6834
PUSH HL E5
Push HL onto the stack to preserve the input pointer while we use HL for multiplication.
6835
LD H,D 62
Load Register H with D. Copy the current accumulated value from DE to HL.
6836
LD L,E 6B
Load Register L with E. HL now contains a copy of the current value for multiplication.
6837
EX AF,AF' 08
Exchange AF with AF'. This saves the digit value in A' while we check for overflow.
6838
LD A,1FH 3E 1F
Load Register A with 1FH (31 decimal). This is the overflow threshold - if D > 31, multiplying by 10 would overflow 16 bits.
683A
CP D BA
Compare Register A (1FH) with D. If D > 1FH (high byte > 31), the value is too large to safely multiply by 10.
683B
Jump Relative if Carry to 684DH (exit with current flags). If D > 1FH, overflow would occur - abort the digit addition.
683D
EX AF,AF' 08
Exchange AF with AF'. Restore the digit value to A for the final addition.

Multiply DE by 10: HL = HL × 2 × 2 + DE × 2 = HL × 4 + HL × 2 = HL × (4 + 2) ... wait, let's trace: HL×2, HL×4, HL×4+DE=HL×5, HL×10

683E
ADD HL,HL 29
Add HL to HL (HL = HL × 2). First doubling: HL now contains original value × 2.
683F
ADD HL,HL 29
Add HL to HL (HL = HL × 2). Second doubling: HL now contains original value × 4.
6840
ADD HL,DE 19
Add DE to HL. HL = (original × 4) + original = original × 5.
6841
ADD HL,HL 29
Add HL to HL (HL = HL × 2). HL = (original × 5) × 2 = original × 10.
6842
Jump Relative if Carry to 684DH. If the multiplication caused a carry (overflow), exit without updating DE.
6844
LD E,A 5F
Load Register E with A (the digit value 0-9). Prepare to add the digit to the multiplied result.
6845
LD D,00H 16 00
Load Register D with 00H. DE now contains just the single digit value (00nn).
6847
ADD HL,DE 19
Add DE to HL. HL = (original × 10) + digit. This completes the decimal accumulation.
6848
Jump Relative if Carry to 684DH. If adding the digit caused overflow, exit with the carry flag still set.
684A
EX DE,HL EB
Exchange DE and HL. Move the new accumulated value from HL back to DE.
684B
LD A,D 7A
Load Register A with D. This prepares to set flags based on whether DE is zero.
684C
OR E B3
OR Register A with E. Sets Z if DE is zero, NZ if non-zero. Also clears carry indicating success.
684D
POP HL E1
Pop HL from the stack to restore the input pointer.
684E
RET C9
Return to caller. DE contains the new accumulated value, NC if digit was processed successfully, C if overflow or not a digit.

684FH - Parse Hexadecimal Number from Input

This routine parses a hexadecimal (base 16) number from the input buffer at (HL) into DE. It accumulates digits by shifting the running total left by 4 bits (×16) and adding each new hex digit (0-9, A-F). On entry: HL = pointer to input buffer. On exit: DE = parsed hex value, HL points to first non-hex character, NC on success, C if no digits found or overflow.

684F
LD DE,0000H 11 00 00
Load DE with 0000H. Initialize the accumulator to zero before parsing hex digits.

[LOOP START] - Parse hex digits, accumulating value in DE

6852
Call 6859H (Process one hex digit). This reads the next character, validates it as a hex digit 0-9/A-F, and accumulates it into DE (DE = DE × 16 + digit).
6855
RET C D8
Return if Carry. If 6859H returned with carry set, the character was not a valid hex digit - stop parsing and return.
6856
INC HL 23
Increment HL to point to the next character in the input buffer.
6857
Jump Relative back to 6852H. [LOOP] Continue processing hex digits until a non-hex character is found.

6859H - Process One Hexadecimal Digit

This routine processes a single hexadecimal digit from the input. It validates the character at (HL) as a hex digit (0-9 or A-F), then shifts the current value in DE left by 4 bits and adds the new digit. On entry: HL = pointer to character, DE = current accumulated value. On exit: DE = new accumulated value (DE × 16 + digit), NC if valid digit processed, C if not a hex digit or overflow.

6859
LD A,(HL) 7E
Load Register A with the character at the address pointed to by HL.
685A
Call 686DH (Convert character to hex digit value). Returns the numeric value 0-15 in A with carry set if valid hex, or NC if not valid.
685D
CCF 3F
Complement Carry Flag. Inverts the result: now NC means valid hex digit, C means not a hex digit.
685E
RET C D8
Return if Carry. If the character is not a hex digit, return with carry set to signal end of number.
685F
PUSH HL E5
Push HL onto the stack to preserve the input pointer while we use HL for shifting.
6860
EX DE,HL EB
Exchange DE and HL. Move the current accumulated value to HL for the shift operation.
6861
EX AF,AF' 08
Exchange AF with AF'. Save the hex digit value in A' while we check for overflow.
6862
LD A,H 7C
Load Register A with H (the high byte of the current value).
6863
ADD F0H C6 F0
Add F0H to Register A. This checks if H > 0FH: if H > 0FH, then H + F0H > FFH causes carry (overflow would occur when shifting).
6865
Jump Relative if Carry to 684DH (exit with current flags). If H > 0FH, shifting left 4 bits would cause overflow - abort.
6867
EX AF,AF' 08
Exchange AF with AF'. Restore the hex digit value to A.

Multiply HL by 16 (shift left 4 bits) by adding HL to itself 4 times

6868
ADD HL,HL 29
Add HL to HL (HL = HL × 2). First shift: HL now contains original value × 2.
6869
ADD HL,HL 29
Add HL to HL (HL = HL × 2). Second shift: HL now contains original value × 4.
686A
ADD HL,HL 29
Add HL to HL (HL = HL × 2). Third shift: HL now contains original value × 8.
686B
Jump Relative to 6841H. This jumps into the decimal routine which does one more shift (×2 = ×16 total) and adds the digit value in A.

686DH - Convert ASCII Character to Hex Digit Value

This routine converts an ASCII character to its hexadecimal digit value (0-15). It handles both decimal digits (0-9) and uppercase hex letters (A-F). On entry: A = ASCII character to convert. On exit: A = hex value (0-15), C (Carry set) if valid hex digit, NC if not a valid hex digit.

686D
SUB 30H D6 30
Subtract 30H (ASCII 0) from Register A. This converts '0'-'9' to values 0-9, and 'A'-'F' to values 17-22.
686F
CP 0AH FE 0A
Compare Register A with 0AH (10 decimal). If A < 10, it was a decimal digit '0'-'9'.
6871
RET C D8
Return if Carry (A < 10). Character was a valid decimal digit, A contains value 0-9, carry is set indicating valid.
6872
SUB 11H D6 11
Subtract 11H (17 decimal) from Register A. This converts 'A' (which was 17 after -30H) to 0, 'B' to 1, etc.
6874
CP 06H FE 06
Compare Register A with 06H. If A < 6, the original character was 'A'-'F'.
6876
RET NC D0
Return if No Carry (A >= 6). Character was not a valid hex digit (not 0-9 or A-F), return with NC.
6877
ADD 0AH C6 0A
Add 0AH (10 decimal) to Register A. Convert 0-5 (representing A-F) to 10-15 (the actual hex values).
6879
SCF 37
Set Carry Flag. Indicate that this was a valid hex digit.
687A
RET C9
Return to caller. A contains hex value 10-15, carry is set indicating valid hex letter A-F.

687BH - 8-bit by 8-bit Multiply (Entry Point)

This is an alternate entry point for the multiply routine when the multiplicand is only 8 bits. It sets H to zero and falls through to the main 8×16 multiply routine. On entry: A = multiplier (8-bit), L = multiplicand (8-bit). On exit: HL = product (A × L).

687B
LD H,00H 26 00
Load Register H with 00H. Clear the high byte so HL contains only the 8-bit multiplicand in L.

Fall through to the main 8×16 multiply routine at 687DH

687DH - 8-bit by 16-bit Multiply (HL = HL × A)

This routine multiplies a 16-bit value in HL by an 8-bit value in A, returning the 16-bit result in HL. It uses the shift-and-add algorithm, shifting the multiplier right and conditionally adding the multiplicand. The result is shifted right to position it correctly. On entry: HL = multiplicand (16-bit), A = multiplier (8-bit). On exit: HL = product (HL × A), DE and BC preserved.

687D
PUSH DE D5
Push DE onto the stack to preserve DE.
687E
PUSH BC C5
Push BC onto the stack to preserve BC.
687F
EX DE,HL EB
Exchange DE and HL. Move the multiplicand to DE so HL can be used as the accumulator.
6880
LD C,80H 0E 80
Load Register C with 80H. C will accumulate the low bits of the extended result; 80H serves as a sentinel to count 8 iterations.
6882
LD HL,0000H 21 00 00
Load HL with 0000H. Initialize the product accumulator to zero.

[LOOP START] - Shift-and-add multiplication, 8 iterations

6885
RRCA 0F
Rotate Register A Right through Carry. Shift the multiplier right, moving bit 0 into the carry flag.
6886
Jump Relative if No Carry to 6889H. If the shifted-out bit was 0, skip the addition.
6888
ADD HL,DE 19
Add DE to HL. The multiplier bit was 1, so add the multiplicand to the running product.
6889
SRL H CB 3C
Shift Right Logical Register H. Shift the high byte of the product right, moving bit 0 into carry.
688B
RR L CB 1D
Rotate Right Register L through carry. Shift the low byte right, bringing in the bit from H and moving bit 0 to carry.
688D
RR C CB 19
Rotate Right Register C through carry. Shift C right, bringing in the bit from L. When the sentinel bit (initially 80H) shifts out, we're done.
688F
Jump Relative if No Carry to 6885H. [LOOP] Continue until the sentinel bit in C shifts out (after 8 iterations).
6891
LD H,L 65
Load Register H with L. Move the high byte of the final product into position.
6892
LD L,C 69
Load Register L with C. Move the low byte of the final product into position. HL now contains the result.
6893
POP BC C1
Pop BC from the stack to restore BC.
6894
POP DE D1
Pop DE from the stack to restore DE.
6895
RET C9
Return to caller. HL contains the 16-bit product of (original HL) × A.

6896H - 16-bit by 8-bit Divide (HL = HL ÷ A)

This routine divides a 16-bit value in HL by an 8-bit value in A, returning the quotient in HL and the remainder in A. It uses the standard shift-and-subtract division algorithm. On entry: HL = dividend (16-bit), A = divisor (8-bit). On exit: HL = quotient, A = remainder.

6896
LD C,A 4F
Load Register C with A. Save the divisor in C for repeated use in the division loop.
6897
LD B,10H 06 10
Load Register B with 10H (16 decimal). This is the bit counter for 16-bit division.
6899
XOR A AF
XOR Register A with itself. Clear A to zero; A will hold the working remainder.

[LOOP START] - Shift-and-subtract division, 16 iterations

689A
ADD HL,HL 29
Add HL to HL (HL = HL × 2). Shift the dividend left, moving the high bit into carry.
689B
RLA 17
Rotate Left through Carry Register A. Shift the carry (high bit of HL) into the remainder in A.
689C
Jump Relative if Carry to 68A1H. If A overflowed during the shift, the remainder is definitely >= divisor, so subtract.
689E
CP C B9
Compare Register A (remainder) with C (divisor). Check if the remainder >= divisor.
689F
Jump Relative if Carry to 68A3H. If remainder < divisor, skip the subtraction (quotient bit is 0).
68A1
SUB C 91
Subtract C (divisor) from A (remainder). Perform the division step: remainder = remainder - divisor.
68A2
INC L 2C
Increment L. Set the quotient bit to 1 (the low bit of HL, which was 0 after the ADD HL,HL).
68A3
Decrement B and Jump if Not Zero to 689AH. [LOOP] Repeat for all 16 bits of the dividend.
68A5
RET C9
Return to caller. HL contains the quotient, A contains the remainder.

68A6H - Convert 8-bit Value to Decimal String (Entry Point)

This is an alternate entry point for decimal conversion when the value is only 8 bits. It extends A to 16 bits in DE and falls through to the main conversion routine. On entry: A = 8-bit value to convert. On exit: 5487H-548BH contains 5-digit ASCII decimal string, B = count of significant digits, DE = original HL pointer.

68A6
LD E,A 5F
Load Register E with A. Put the 8-bit value in the low byte of DE.
68A7
LD D,00H 16 00
Load Register D with 00H. Clear the high byte so DE contains the 16-bit equivalent of the 8-bit value.
68A9
Jump Relative to 68AFH. Skip the 16-bit value fetch and proceed to the conversion routine.

68ABH - Convert 16-bit Value from Memory to Decimal String

This entry point reads a 16-bit value from memory at (HL) and converts it to a decimal ASCII string. It also advances HL past the 2-byte value. On entry: HL = pointer to 16-bit value (low byte first). On exit: 5487H-548BH contains 5-digit ASCII decimal string, B = count of significant digits, DE = original HL + 2.

68AB
LD E,(HL) 5E
Load Register E with the byte at (HL). Get the low byte of the 16-bit value.
68AC
INC HL 23
Increment HL to point to the next byte.
68AD
LD D,(HL) 56
Load Register D with the byte at (HL). Get the high byte of the 16-bit value. DE now holds the complete value.
68AE
INC HL 23
Increment HL to point past the value.

Fall through to common conversion entry at 68AFH

68AFH - Convert 16-bit Value to Decimal String with Leading Zero Suppression

This routine converts a 16-bit value in DE to a 5-digit ASCII decimal string at 5487H, then replaces leading zeros with spaces. On entry: DE = value to convert, HL = pointer (saved). On exit: 5487H-548BH contains decimal string with leading spaces, B = count of significant digits + 1, DE = original HL.

68AF
PUSH HL E5
Push HL onto the stack to preserve the caller's pointer.
68B0
Call 68D1H (Convert DE to 5-digit decimal at 5487H). This produces a string with leading zeros.
68B3
LD B,04H 06 04
Load Register B with 04H. We'll check up to 4 leading positions for zeros (leaving at least one digit).
68B5
LD HL,5487H 21 87 54
Load HL with 5487H, the address of the decimal conversion buffer.
68B8
LD A,30H 3E 30
Load Register A with 30H (ASCII 0). This is the character to look for and replace.

[LOOP START] - Replace leading zeros with spaces

68BA
CP (HL) BE
Compare Register A with the byte at (HL). Check if this position contains a leading zero.
68BB
Jump Relative if Not Zero to 68C2H. If not '0', we've found the first significant digit - stop replacing.
68BD
LD (HL),20H 36 20
Store 20H (ASCII SPACE) at (HL). Replace the leading zero with a space.
68BF
INC HL 23
Increment HL to point to the next character.
68C0
Decrement B and Jump if Not Zero to 68BAH. [LOOP] Continue checking up to 4 leading positions.
68C2
INC B 04
Increment B. B now contains the count of remaining digits (1-5), which is the significant digit count + 1.
68C3
POP DE D1
Pop the saved value into DE (not HL). This returns the original HL value to the caller in DE.
68C4
RET C9
Return to caller. Decimal string at 5487H has leading spaces, B = significant digits + 1.

68C5H - Convert and Display 16-bit Value as Decimal

This routine converts a 16-bit value in DE to decimal and displays it. It combines the conversion with buffer display. On entry: DE = value to convert and display. On exit: Value displayed on screen.

68C5
Call 68D1H (Convert DE to 5-digit decimal at 5487H). This produces the ASCII decimal string.
68C8
LD B,05H 06 05
Load Register B with 05H. We'll display all 5 digits (including leading zeros).
68CA
LD HL,5487H 21 87 54
Load HL with 5487H, the address of the decimal conversion buffer.
68CD
Jump to 62BAH (Display B bytes from buffer at HL). This displays the decimal string on screen.

68D0H - Convert HL to Decimal (Entry Point)

This entry point converts HL to decimal by first moving it to DE. On entry: HL = value to convert. On exit: 5487H-548BH contains 5-digit decimal string.

68D0
EX DE,HL EB
Exchange DE and HL. Move the value to convert from HL to DE for the conversion routine.

Fall through to the main decimal conversion routine at 68D1H

68D1H - Convert DE to 5-Digit Decimal ASCII String

This is the core decimal conversion routine. It converts a 16-bit value in DE to a 5-character ASCII decimal string stored at 5487H. The algorithm repeatedly subtracts powers of 10 (10000, 1000, 100, 10) to extract each digit. On entry: DE = 16-bit value to convert (0-65535). On exit: 5487H-548BH contains 5-digit ASCII decimal string (with leading zeros).

68D1
LD BC,5487H 01 87 54
Load BC with 5487H. This is the address of the output buffer where the decimal string will be stored.
68D4
LD HL,68F6H 21 F6 68
Load HL with 68F6H, the address of the powers of 10 table (contains -10000, -1000, -100, -10 as 16-bit values).
68D7
LD A,04H 3E 04
Load Register A with 04H. We'll process 4 powers of 10 (10000, 1000, 100, 10), then handle units separately.

[OUTER LOOP START] - Process each power of 10

68D9
EX AF,AF' 08
Exchange AF with AF'. Save the digit counter in A' while we extract one digit.
68DA
PUSH BC C5
Push BC onto the stack to save the output pointer.
68DB
LD C,(HL) 4E
Load Register C with the byte at (HL). Get the low byte of the negative power of 10.
68DC
INC HL 23
Increment HL to the next byte of the power of 10.
68DD
LD B,(HL) 46
Load Register B with the byte at (HL). Get the high byte. BC now contains the negative power of 10.
68DE
INC HL 23
Increment HL to point to the next power of 10 for the next iteration.
68DF
EX DE,HL EB
Exchange DE and HL. Move the remaining value to HL for arithmetic, save table pointer in DE.
68E0
LD A,2FH 3E 2F
Load Register A with 2FH (ASCII '0' - 1). This will be incremented to '0' before the first subtraction attempt.

[INNER LOOP START] - Count how many times we can subtract the power of 10

68E2
INC A 3C
Increment A. Advance the digit counter (from '/' to '0', then '0' to '1', etc.).
68E3
ADD HL,BC 09
Add BC to HL. Since BC contains a negative power of 10, this effectively subtracts the power.
68E4
Jump if Carry to 68E2H. [INNER LOOP] If no borrow occurred (result still positive), continue counting.
68E7
SBC HL,BC ED 42
Subtract BC from HL with borrow. Undo the last subtraction that caused underflow (add back the power of 10).
68E9
EX DE,HL EB
Exchange DE and HL. Move the remaining value back to DE, restore table pointer to HL.
68EA
POP BC C1
Pop BC from the stack to restore the output pointer.
68EB
LD (BC),A 02
Store Register A at (BC). Write the ASCII digit to the output buffer.
68EC
INC BC 03
Increment BC to point to the next output position.
68ED
EX AF,AF' 08
Exchange AF with AF'. Restore the power counter from A'.
68EE
DEC A 3D
Decrement A. Count down the remaining powers of 10 to process.
68EF
Jump Relative if Not Zero to 68D9H. [OUTER LOOP] Continue with the next power of 10.
68F1
LD A,E 7B
Load Register A with E. Get the remaining units digit (0-9) from the low byte of DE.
68F2
ADD 30H C6 30
Add 30H to Register A. Convert the units digit to ASCII.
68F4
LD (BC),A 02
Store Register A at (BC). Write the final units digit to the output buffer.
68F5
RET C9
Return to caller. The 5-digit decimal string is now at 5487H-548BH.

68F6H - Powers of 10 Table (Negated)

This is a data table containing the negative values of powers of 10, used by the decimal conversion routine. The values are stored as 16-bit little-endian integers: -10000 (D8F0H), -1000 (FC18H), -100 (FF9CH), -10 (FFF6H). Using negative values allows the conversion to use ADD instead of SBC.

68F6
DEFB F0H,D8H F0 D8
Data: -10000 (D8F0H = -10000 in two's complement, stored little-endian).
68F8
DEFB 18H,FCH 18 FC
Data: -1000 (FC18H = -1000 in two's complement, stored little-endian).
68FA
DEFB 9CH,FFH 9C FF
Data: -100 (FF9CH = -100 in two's complement, stored little-endian).
68FC
DEFB F6H,FFH F6 FF
Data: -10 (FFF6H = -10 in two's complement, stored little-endian).

68FEH - Status Display Label Table

This area contains 3-character ASCII label strings used for the status display in various SUPERZAP modes. These labels appear on screen to identify the drive number, track number, sector numbers, etc. The labels are referenced by display routines to show disk operation status.

68FE-6900
DEFM "DRV" 44 52 56
ASCII string "DRV" - Label for Drive number display (e.g., "DRV 0").
6901-6903
DEFM "TRK" 54 52 4B
ASCII string "TRK" - Label for Track number display (e.g., "TRK 17").
6904-6906
DEFM "TRS" 54 52 53
ASCII string "TRS" - Label for Track/Sector display or relative track sector.
6907-6909
DEFM "DRS" 44 52 53
ASCII string "DRS" - Label for Drive/Sector display (used in DFS mode).
690A-690C
DEFM "FRS" 46 52 53
ASCII string "FRS" - Label for File/Record/Sector display (used in file mode).
690D-690E
DEFM "DD" 44 44
ASCII string "DD" - Label for Disk Dump mode indicator.

690FH - Menu Command Definition Table

This area contains structured menu command definitions. Each entry consists of a command code byte (with bit 7 often set), followed by a 16-bit address or data, and additional parameters. These define the commands available in SUPERZAP's various menus and their associated handlers or data.

690F
DEFB 81H 81
Command code 81H - Command type identifier with high bit set.
6910
DEFB 00H 00
Parameter byte 00H - Associated data or address low byte.
6911
DEFB 84H 84
Command code 84H - Another command type with high bit set.
6912-6914
DEFM "UDM" 55 44 4D
ASCII string "UDM" - User Dump Memory command identifier.
6915
DEFB A1H A1
Command code A1H - Command type with high bit set.
6916
DEFB 00H 00
Parameter byte 00H - Terminator or null data.
6917-6919
DEFM "OVD" 4F 56 44
ASCII string "OVD" - Overlay Disk or Overwrite Disk command identifier.
691A-691B
DEFM "FS" 46 53
ASCII string "FS" - File Sector mode indicator.
691C
DEFB C1H C1
Command code C1H - Command type with high bit set (POP BC opcode when executed as code).
691D
DEFB 00H 00
Parameter byte 00H - Terminator.
691E-6920
DEFB CAH,55H,44H CA 55 44
Data bytes - May be interpreted as JP Z,4455H when executed, or data "ʕD".
6921-6922
DEFM "TS" 54 53
ASCII string "TS" - Track/Sector mode indicator.
6923
DEFB 91H 91
Command code 91H - Command type with high bit set.
6924
DEFB 00H 00
Parameter byte 00H - Terminator.
6925-6928
DEFM "EUDM" 45 55 44 4D
ASCII string "EUDM" - Extended User Dump Memory command.
6929-692B
DEFM "DB" + 89H 44 42 89
ASCII "DB" followed by command code 89H - Disk Block or Data Block command.
692C
DEFB 00H 00
Parameter byte 00H - Terminator.
692D-6931
DEFB CAH,55H,56H,44H,53H CA 55 56 44 53
Data bytes - Contains "UVDS" preceded by CAH, possibly User View Disk Sector command.
6932-6933
DEFB 80H,80H 80 80
Command codes 80H, 80H - Possibly mode flags or padding.

6934H - Command Keyword Table (Continued)

Continuation of the command keyword parsing table that begins at 690FH. This table is used by the command parser at 54E6H to match user input against valid SUPERZAP commands. Each entry consists of a keyword (ASCII characters), a terminator byte (80H), flag bytes, and handler address data. The complex interleaving of keywords and data bytes reflects the table's optimized structure for the parsing algorithm.

6934-6939
DEFB A6H,5BH,5AH,44H,53H,80H A6 5B 5A 44 53 80
Keyword table entry data. Bytes A6H and 5BH are flag/address data from the previous entry. 5AH,44H,53H = "ZDS" (Zap Disk Sector command), 80H = keyword terminator.
693A-6940
DEFB 40H,9EH,5BH,43H,44H,53H,80H 40 9E 5B 43 44 53 80
Bytes 40H,9EH,5BH are flag/address data for ZDS. 43H,44H,53H = "CDS" (Copy Disk Sector command), 80H = keyword terminator.
6941-6947
DEFB 20H,4DH,5BH,43H,44H,44H,80H 20 4D 5B 43 44 44 80
Bytes 20H,4DH,5BH are flag/address data for CDS. 43H,44H,44H = "CDD" (Copy Disk to Disk command), 80H = keyword terminator.
6948-694F
DEFB 10H,E0H,59H,44H,50H,57H,45H,80H 10 E0 59 44 50 57 45 80
Bytes 10H,E0H,59H are flag/address data for CDD. 44H,50H,57H,45H = "DPWE" (Disk Password Write Enable command), 80H = keyword terminator.
6950
DEFB 00H 00
Table section terminator 00H - Marks the end of this portion of the keyword table.

6951H - Command Keyword Table (Final Entries)

Final entries in the command keyword table, containing remaining SUPERZAP commands with their flag and handler data.

6951-6957
DEFB 49H,5EH,44H,4EH,54H,48H,80H 49 5E 44 4E 54 48 80
Bytes 49H,5EH are flag/address data for DPWE. 44H,4EH,54H,48H = "DNTH" (Disk N-TH sector command), 80H = keyword terminator.
6958
DEFB 00H 00
Table section terminator 00H - Marks the end of this portion of the keyword table.
6959-695E
DEFB A0H,5EH,52H,52H,54H,80H A0 5E 52 52 54 80
Bytes A0H,5EH are flag/address data for DNTH. 52H,52H,54H = "RRT" (possibly Re-Read Track or internal command), 80H = keyword terminator.
695F
DEFB 08H 08
Flag/data byte 08H for RRT entry.
6960-6966
DEFB DFH,5EH,45H,58H,49H,54H,80H DF 5E 45 58 49 54 80
Bytes DFH,5EH are flag/address data. 45H,58H,49H,54H = "EXIT" (Exit command), 80H = keyword terminator.
6967
DEFB 00H 00
Table terminator 00H - Marks the end of the command keyword table.

6968H - Escape Sequence and Table Marker

Short control sequence followed by a marker byte that may indicate the start of the compressed string lookup tables.

6968-696A
DEFB 1BH,58H,00H 1B 58 00
Escape sequence: 1BH (ESC) + 58H ('X') + 00H (terminator). This is the ESC-X sequence used for the exit function or screen control.
696B
DEFB 80H 80
Marker byte 80H - Start of short word lookup table (codes 80H-9FH). Referenced by string decompression routine at 626DH.

696CH - Display Prompt Strings

Compressed display strings used for prompts, confirmations, and status messages. These strings use the compressed word format where bytes 80H-FFH represent common words, and 08H serves as a formatting control (often interpreted as "don't add trailing space").

696C-696E
DEFB 20H,2DH,A0H 20 2D A0
String: space + "-" + compressed space (A0H). Displays as " - " separator in status lines.
696F-697D
DEFB 27H,2AH,A7H,27H,52H,A7H,27H,53H,A7H,27H,58H,A7H,27H,59H,A7H 27 2A A7 27 52 A7 27 53 A7 27 58 A7 27 59 A7
Key legend string with quoted single-letter commands. 27H=quote, A7H=compressed "DUMP". Displays as: '* '*R '*S '*X '*Y ' showing available single-key commands (* = re-display, R = re-read, S = search, X = exit, Y = write yes).
697E-6986
DEFB 28H,59H,20H,4FH,52H,20H,4EH,29H,A0H 28 59 20 4F 52 20 4E 29 A0
Confirmation prompt: "(Y OR N)" + compressed space. Displays as "(Y OR N) " for yes/no confirmation prompts.
6987-698B
DEFB 08H,3FH,3FH,3FH,A0H 08 3F 3F 3F A0
Format control + "???" + compressed space. The 08H prefix suppresses leading space. Displays as "??? " for unknown/error indicator.
698C-6992
DEFB 2AH,2AH,2AH,2AH,2AH,2AH,AAH 2A 2A 2A 2A 2A 2A AA
Asterisk pattern: "******" + terminator AAH. Used as a visual separator or password mask display.
6993-699A
DEFB 27H,45H,4EH,54H,45H,52H,A7H,08H 27 45 4E 54 45 52 A7 08
Quoted string: 'ENTER' (27H + "ENTER" + A7H terminator) + 08H format control. Displays as 'ENTER' instruction to user.
699B-69A0
DEFB 2EH,A0H,08H,27H,D3H,08H 2E A0 08 27 D3 08
Format string: "." + space + format control + quote + D3H (compressed 'S' with bit 7) + format control. Used for sentence-ending punctuation with quoted 'S' suffix.

69A1H - Additional Format Strings

More display formatting strings for prompts, separators, and input field labels. These continue the compressed string format used throughout SUPERZAP's user interface.

69A1-69A5
DEFB 27H,20H,20H,2DH,A0H 27 20 20 2D A0
Format string: quote + two spaces + "-" + compressed space. Displays as "' - " separator with leading quote.
69A6-69A7
DEFB A0H,08H A0 08
Compressed space + format control. Spacing element with suppressed trailing space.
69A8-69AB
DEFB 3FH,A0H,08H,3FH 3F A0 08 3F
Format string: "?" + space + format control + "?". Displays as "? ?" double question prompt.
69AC-69AD
DEFB 20H,A0H 20 A0
Space + compressed space. Double-space separator element.
69AE-69B4
DEFB 28H,88H,08H,A9H,1CH,1FH,88H 28 88 08 A9 1C 1F 88
Complex format: "(" + compressed "IS" (88H) + format control + compressed "EXIT" (A9H) + cursor codes (1CH,1FH) + compressed "IS". Part of conditional prompt like "(IS EXIT...".
69B5-69BC
DEFB 08H,28H,53H,A9H,08H,2FH,88H,A3H 08 28 53 A9 08 2F 88 A3
Complex format: format control + "(S" + compressed "EXIT" (A9H) + format control + "/" + compressed "IS" (88H) + A3H. Part of sector/status prompt formatting with slash separator.

69BDH - Compressed String Table 1 (Short Words, Codes 80H-9FH)

This is the first compressed string table containing common 2-4 letter words. Each word has its final character with the high bit (bit 7) set to mark the end of the string. When SUPERZAP displays messages, codes 80H-9FH in the message data are replaced with these short words. This compression saves memory by replacing frequently-used words with single-byte codes.

69BD-69BE
DEFM "AT" 41 D4
The T has the high bit set. The hex is D4 (Binary 11010100). Removing the high bit leaves 54H, the ASCII code for T.
69BF-69C0
DEFM "BE" 42 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
69C1-69C2
DEFM "DO" 44 CF
The O has the high bit set. The hex is CF (Binary 11001111). Removing the high bit leaves 4FH, the ASCII code for O.
69C3-69C4
DEFM "IF" 49 C6
The F has the high bit set. The hex is C6 (Binary 11000110). Removing the high bit leaves 46H, the ASCII code for F.
69C5-69C6
DEFM "IS" 49 D3
The S has the high bit set. The hex is D3 (Binary 11010011). Removing the high bit leaves 53H, the ASCII code for S.
69C7-69C8
DEFM "OF" 4F C6
The F has the high bit set. The hex is C6 (Binary 11000110). Removing the high bit leaves 46H, the ASCII code for F.
69C9-69CA
DEFM "OK" 4F CB
The K has the high bit set. The hex is CB (Binary 11001011). Removing the high bit leaves 4BH, the ASCII code for K.
69CB-69CC
DEFM "OR" 4F D2
The R has the high bit set. The hex is D2 (Binary 11010010). Removing the high bit leaves 52H, the ASCII code for R.
69CD-69CE
DEFM "TO" 54 CF
The O has the high bit set. The hex is CF (Binary 11001111). Removing the high bit leaves 4FH, the ASCII code for O.
69CF-69D1
DEFM "ALL" 41 4C CC
The L has the high bit set. The hex is CC (Binary 11001100). Removing the high bit leaves 4CH, the ASCII code for L.
69D2-69D4
DEFM "AND" 41 4E C4
The D has the high bit set. The hex is C4 (Binary 11000100). Removing the high bit leaves 44H, the ASCII code for D.
69D5-69D7
DEFM "BAD" 42 41 C4
The D has the high bit set. The hex is C4 (Binary 11000100). Removing the high bit leaves 44H, the ASCII code for D.
69D8-69DA
DEFM "END" 45 4E C4
The D has the high bit set. The hex is C4 (Binary 11000100). Removing the high bit leaves 44H, the ASCII code for D.
69DB-69DD
DEFM "EOF" 45 4F C6
The F has the high bit set. The hex is C6 (Binary 11000110). Removing the high bit leaves 46H, the ASCII code for F.
69DE-69E0
DEFM "FEW" 46 45 D7
The W has the high bit set. The hex is D7 (Binary 11010111). Removing the high bit leaves 57H, the ASCII code for W.
69E6
DEFM "Y" D9
The Y has the high bit set. The hex is D9 (Binary 11011001). Removing the high bit leaves 59H, the ASCII code for Y.
69E1-69E3
DEFM "FOR" 46 4F D2
The R has the high bit set. The hex is D2 (Binary 11010010). Removing the high bit leaves 52H, the ASCII code for R.
69E4-69E6
DEFM "MAY" 4D 41 D9
The Y has the high bit set. The hex is D9 (Binary 11011001). Removing the high bit leaves 59H, the ASCII code for Y.
69E7-69E9
DEFM "NOT" 4E 4F D4
The T has the high bit set. The hex is D4 (Binary 11010100). Removing the high bit leaves 54H, the ASCII code for T.
69EA-69EC
DEFM "OUT" 4F 55 D4
The T has the high bit set. The hex is D4 (Binary 11010100). Removing the high bit leaves 54H, the ASCII code for T.
69ED-69EF
DEFM "THE" 54 48 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
69F0-69F2
DEFM "TOO" 54 4F CF
The O has the high bit set. The hex is CF (Binary 11001111). Removing the high bit leaves 4FH, the ASCII code for O.
69F3-69F5
DEFM "YOU" 59 4F D5
The U has the high bit set. The hex is D5 (Binary 11010101). Removing the high bit leaves 55H, the ASCII code for U.
69F6-69F9
DEFM "BASE" 42 41 53 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
69FA-69FD
DEFM "BYTE" 42 59 54 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
69FE-6A01
DEFM "CHAR" 43 48 41 D2
The R has the high bit set. The hex is D2 (Binary 11010010). Removing the high bit leaves 52H, the ASCII code for R.
6A02-6A05
DEFM "CODE" 43 4F 44 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
6A06-6A09
DEFM "COPY" 43 4F 50 D9
The Y has the high bit set. The hex is D9 (Binary 11011001). Removing the high bit leaves 59H, the ASCII code for Y.
6A0A-6A0D
DEFM "DATA" 44 41 54 C1
The A has the high bit set. The hex is C1 (Binary 11000001). Removing the high bit leaves 41H, the ASCII code for A.
6A0E-6A11
DEFM "DISK" 44 49 53 CB
The K has the high bit set. The hex is CB (Binary 11001011). Removing the high bit leaves 4BH, the ASCII code for K.
6A12-6A15
DEFM "DUMP" 44 55 4D D0
The P has the high bit set. The hex is D0 (Binary 11010000). Removing the high bit leaves 50H, the ASCII code for P.
6A16-6A19
DEFM "EXIT" 45 58 49 D4
The T has the high bit set. The hex is D4 (Binary 11010100). Removing the high bit leaves 54H, the ASCII code for T.
6A1A-6A1D
DEFM "FILE" 46 49 4C C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
6A1E-6A21
DEFM "LOST" 4C 4F 53 D4
The T has the high bit set. The hex is D4 (Binary 11010100). Removing the high bit leaves 54H, the ASCII code for T.
6A24-6A27
DEFM "MAIN" 4D 41 49 CE
The N has the high bit set. The hex is CE (Binary 11001110). Removing the high bit leaves 4EH, the ASCII code for N.
6A28-6A2B
DEFM "MANY" 4D 41 4E D9
The Y has the high bit set. The hex is D9 (Binary 11011001). Removing the high bit leaves 59H, the ASCII code for Y.
6A2C-6A2F
DEFM "MENU" 4D 45 4E D5
The U has the high bit set. The hex is D5 (Binary 11010101). Removing the high bit leaves 55H, the ASCII code for U.
6A30-6A33
DEFM "MODE" 4D 4F 44 C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
6A34-6A37
DEFM "NAME" 4E 41 4D C5
The E has the high bit set. The hex is C5 (Binary 11000101). Removing the high bit leaves 45H, the ASCII code for E.
6A38-6A3B
DEFM "READ" 52 45 41 C4
The D has the high bit set. The hex is C4 (Binary 11000100). Removing the high bit leaves 44H, the ASCII code for D.
6A3C-6A3F
DEFM "SEEK" 53 45 45 CB
The K has the high bit set. The hex is CB (Binary 11001011). Removing the high bit leaves 4BH, the ASCII code for K.
6A40-6A43
DEFM "SKIP" 53 4B 49 D0
The P has the high bit set. The hex is D0 (Binary 11010000). Removing the high bit leaves 50H, the ASCII code for P.
6A44-6A47
DEFM "SOME" 53 4F 4D C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A48-6A4B
DEFM "SURE" 53 55 52 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A4C-6A4F
DEFM "THIS" 54 48 49 D3
The S has the high bit set. The hex is D3 which is 11010011 in binary. If you turn off the high bit, you get 01010011 which is 53H, which is hex for S
6A50-6A53
DEFM "TYPE" 54 59 50 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A54-6A57
DEFM "WANT" 57 41 4E D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6A58-6A5B
DEFM "WHEN" 57 48 45 CE
The N has the high bit set. The hex is CE which is 11001110 in binary. If you turn off the high bit, you get 01001110 which is 4EH, which is hex for N
6A5C-6A5F
DEFM "ZERO" 5A 45 52 CF
The O has the high bit set. The hex is CF which is 11001111 in binary. If you turn off the high bit, you get 01001111 which is 4FH, which is hex for O
6A60-6A64
DEFM "BLOCK" 42 4C 4F 43 CB
The K has the high bit set. The hex is CB which is 11001011 in binary. If you turn off the high bit, you get 01001011 which is 4BH, which is hex for K
6A65-6A69
DEFM "COUNT" 43 4F 55 4E D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6A6A-6A6E
DEFM "DRIVE" 44 52 49 56 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A6F-6A73
DEFM "ERROR" 45 52 52 4F D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6A74-6A78
DEFM "EXTRA" 45 58 54 52 C1
The A has the high bit set. The hex is C1 which is 11000001 in binary. If you turn off the high bit, you get 01000001 which is 41H, which is hex for A
6A79-6A7D
DEFM "FAULT" 46 41 55 4C D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6A7E-6A82
DEFM "FOUND" 46 4F 55 4E C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6A83-6A87
DEFM "INPUT" 49 4E 50 55 D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6A88-6A8C
DEFM "PAUSE" 50 41 55 53 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A8D-6A91
DEFM "PRESS" 50 52 45 53 D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6A92-6A96
DEFM "RANGE" 52 41 4E 47 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6A97-6A9B
DEFM "REPLY" 52 45 50 4C D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6A9C-6AA0
DEFM "RETRY" 52 45 54 52 D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6AA1-6AA5
DEFM "TRACK" 54 52 41 43 CB
The K has the high bit set. The hex is CB which is 11001011 in binary. If you turn off the high bit, you get 01001011 which is 4BH, which is hex for K
6AA6-6AAA
DEFM "VALUE" 56 41 4C 55 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6AAB-6AAF
DEFM "WRITE" 57 52 49 54 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6AB0-6AB5
DEFM "BEYOND" 42 45 59 4F 4E C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6AB6-6ABB
DEFM "BUFFER" 42 55 46 46 45 D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6ABC-6AC1
DEFM "DEVICE" 44 45 56 49 43 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6AC2-6AC7
DEFM "MEMORY" 4D 45 4D 4F 52 D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6AC8-6ACD
DEFM "OFFSET" 4F 46 46 53 45 D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6ACE-6AD3
DEFM "PARITY" 50 41 52 49 54 D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6AD4-6AD9
DEFM "RECORD" 52 45 43 4F 52 C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6ADA-6ADF
DEFM "RETURN" 52 45 54 55 52 CE
The N has the high bit set. The hex is CE which is 11001110 in binary. If you turn off the high bit, you get 01001110 which is 4EH, which is hex for N
6AE0-6AE5
DEFM "SECTOR" 53 45 43 54 4F D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6AE6-6AEB
DEFM "SOURCE" 53 4F 55 52 43 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6AEC-6AF1
DEFM "SYSTEM" 53 59 53 54 45 CD
The M has the high bit set. The hex is CD which is 11001101 in binary. If you turn off the high bit, you get 01001101 which is 4DH, which is hex for M
6AF2-6AF7
DEFM "VERIFY" 56 45 52 49 46 D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6AF8-6AFD
DEFM "WITHIN" 57 49 54 48 49 CE
The N has the high bit set. The hex is CE which is 11001110 in binary. If you turn off the high bit, you get 01001110 which is 4EH, which is hex for N
6AFE-6B04
DEFM "ADDRESS" 41 44 44 52 45 53 D3
The S has the high bit set. The hex is D3 which is 11010011 in binary. If you turn off the high bit, you get 01010011 which is 53H, which is hex for S
6B05-6B0B
DEFM "CONTAIN" 43 4F 4E 54 41 49 CE
The N has the high bit set. The hex is CE which is 11001110 in binary. If you turn off the high bit, you get 01001110 which is 4EH, which is hex for N
6B0C-6B12
DEFM "DISPLAY" 44 49 53 50 4C 41 D9
The Y has the high bit set. The hex is D9 which is 11011001 in binary. If you turn off the high bit, you get 01011001 which is 59H, which is hex for Y
6B13-6B19
DEFM "ILLEGAL" 49 4C 4C 45 47 41 CC
The L has the high bit set. The hex is CC which is 11001100 in binary. If you turn off the high bit, you get 01001100 which is 4CH, which is hex for L
6B1A-6B20
DEFM "INVALID" 49 4E 56 41 4C 49 C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6B21-6B27
DEFM "MISSING" 4D 49 53 53 49 4E C7
The G has the high bit set. The hex is C7 which is 11000111 in binary. If you turn off the high bit, you get 01000111 which is 47H, which is hex for G
6B28-6B2E
DEFM "NUMERIC" 4E 55 4D 45 52 49 C3
The C has the high bit set. The hex is C3 which is 11000011 in binary. If you turn off the high bit, you get 01000011 which is 43H, which is hex for C
6B2F-6B35
DEFM "PROTECT" 50 52 49 4E 54 45 D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6B36-6B3C
DEFM "REQUEST" 45 51 55 45 53 D4
The T has the high bit set. The hex is D4 which is 11010100 in binary. If you turn off the high bit, you get 01010100 which is 54H, which is hex for T
6B3D-6B44
DEFM "CONTENTS" 43 4F 4E 54 45 4E 54 D3
The S has the high bit set. The hex is D3 which is 11010011 in binary. If you turn off the high bit, you get 01010011 which is 53H, which is hex for S
6B45-6B4C
DEFM "CONTINUE" 43 4F 4E 54 49 4E 55 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6B4D-6B54
DEFM "DISKETTE" 44 49 53 4B 45 54 54 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6B55-6B5C
DEFM "FILE SPEC" 46 49 4C 45 53 50 45 C3
The C has the high bit set. The hex is C3 which is 11000011 in binary. If you turn off the high bit, you get 01000011 which is 43H, which is hex for C
6B5D-6B64
DEFM "FUNCTION" 46 55 4E 43 54 49 4F CE
The N has the high bit set. The hex is CE which is 11001110 in binary. If you turn off the high bit, you get 01001110 which is 4EH, which is hex for N
6B65-6B6C
DEFM "OPERATOR" 4F 50 45 52 41 54 4F D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6B6D-6B74
DEFM "PASSWORD" 50 41 53 53 57 4F 52 C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6B75-6B7C
DEFM "RELATIVE" 52 45 4C 41 54 49 56 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6B7D-6B84
DEFM "SUPERZAP" 53 55 50 45 52 5A 41 D0
The P has the high bit set. The hex is D0 which is 11010000 in binary. If you turn off the high bit, you get 01010000 which is 50H, which is hex for P
6B85-6B8D
DEFM "AVAILABLE" 41 56 41 49 4C 41 42 4C C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6B8E-6B96
DEFM "COMPLETED" 43 4F 4D 50 4C 45 54 45 C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6B97-6B9F
DEFM "PARAMETER" 50 41 52 41 4D 45 54 45 D2
The R has the high bit set. The hex is D2 which is 11010010 in binary. If you turn off the high bit, you get 01010010 which is 52H, which is hex for R
6BA0-6BA8
DEFM "PROTECTES" 50 52 4F 54 45 43 54 45 C4
The D has the high bit set. The hex is C4 which is 11000100 in binary. If you turn off the high bit, you get 01000100 which is 44H, which is hex for D
6BA9-6BB1
DEFM "TERMINATE" 54 45 52 4D 49 4E 41 54 C5
The E has the high bit set. The hex is C5 which is 11000101 in binary. If you turn off the high bit, you get 01000101 which is 45H, which is hex for E
6BB2-6BBC
DEFM "BAD/ILLEGAL" 42 41 44 2F 49 4C 4C 45 47 41 CC
The L has the high bit set. The hex is CC (Binary 11001100). Removing the high bit leaves 4CH, the ASCII code for L.
6BBD-6BC7
DEFM "DESTINATION" 44 45 53 54 49 4E 41 54 49 4F CE
The N has the high bit set. The hex is CE (Binary 11001110). Removing the high bit leaves 4EH, the ASCII code for N.
6BC8-6BD3
DEFM "MODIFICATION" 4D 4F 44 49 46 49 43 41 54 49 4F D2
The R has the high bit set. The hex is D2 (Binary 11010010). Removing the high bit leaves 52H, the ASCII code for R.
6BD4-6BEB
DEFM "RELATIVE-SECTOR-WITHIN- " 52 45 4C 41 54 49 56 45 2D 53 45 43 54 4F 52 2D 57 49 54 48 49 4E 2D 88
The final character has the high bit set. The hex is 88H, which is 10001000 in binary. Removing the high bit leaves 00001000, which is 08H, the ASCII code for Backspace or a control character.

6BECH - Error Message Lookup Table

This is the error message lookup table used by the error handler at 64FAH. Each entry consists of: (1) an error code byte, (2) the message content using compressed string codes (where codes 80H-FFH reference the compressed word tables at 69BDH and 6A24H), (3) a 00H terminator. Entries are separated by 03H bytes. The error handler searches this table for a matching error code and then displays the associated message. When a byte in the message has bit 7 set, it references a word from the compressed string tables.

6BEC
DEFB 00H 00
Padding or terminator byte before the start of the error table.

Error Entry 1: Error Code 02H

6BED
DEFB 02H 02
Error code 02H - DOS error code for this message entry.
6BEE
DEFB 0AH 0A
Message byte 0AH - Line feed or control character in the error message.
6BEF
DEFB 00H 00
Message terminator 00H - End of this error message.

Error Entry 2: Error Code 9DH - "ERROR" message

6BF0
DEFB 9DH 9D
Error code 9DH - This byte also serves as compressed string code for "ERROR" (code 9DH maps to the word at offset 1DH in the 80H-based table).
6BF1
DEFB A9H A9
Compressed string code A9H - References a word from the A0H-based table (likely "WRITE" or similar).
6BF2
DEFB 03H 03
Entry separator 03H - Marks the boundary between error table entries.

Error Entry 3: Error Code 03H

6BF3
DEFB 03H 03
Error code 03H - DOS error code.
6BF4
DEFB 0BH 0B
Message content byte 0BH - Control or reference byte.
6BF5
DEFB 00H 00
Message terminator 00H.

Error Entry 4: Error Code 96H - "NOT" related message

6BF6
DEFB 96H 96
Error code 96H - Also compressed code for "NOT" (96H - 80H = 16H offset).
6BF7
DEFB 91H 91
Compressed string code 91H - References "THE" or similar from 80H-based table.
6BF8
DEFB 03H 03
Entry separator 03H.

Error Entry 5: Error Code 04H

6BF9
DEFB 04H 04
Error code 04H - DOS error code.
6BFA
DEFB 0CH 0C
Message content byte 0CH - Form feed or control character.
6BFB
DEFB 00H 00
Message terminator 00H.

Error Entry 6: Error Code BBH - "WRITE ERROR" message

6BFC
DEFB BBH BB
Error code BBH - Also compressed code for "WRITE" (BBH - A0H = 1BH offset in A0H table).
6BFD
DEFB A9H A9
Compressed string code A9H - References "ERROR" or related word.
6BFE
DEFB 03H 03
Entry separator 03H.

Error Entry 7: Error Code 05H

6BFF
DEFB 05H 05
Error code 05H - DOS error code.
6C00
DEFB 0DH 0D
Message content byte 0DH - Carriage return.
6C01
DEFB 00H 00
Message terminator 00H.

Error Entry 8: Error Code 91H - "NOT PROTECT" or similar

6C02
DEFB 91H 91
Error code 91H - Also compressed code (91H - 80H = "THE").
6C03
DEFB BCH BC
Compressed string code BCH - References "DEVICE" from A0H table.
6C04
DEFB 87H 87
Compressed string code 87H - References "IF" from 80H table.
6C05
DEFB ACH AC
Compressed string code ACH - References word from A0H table.
6C06
DEFB 03H 03
Entry separator 03H.

Error Entry 9: Error Code 08H

6C07
DEFB 08H 08
Error code 08H - DOS error code (usually CRC error).
6C08
DEFB 10H 10
Message content byte 10H.
6C09
DEFB 00H 00
Message terminator 00H.

Error Entry 10: Error Code B8H - "READ ADD DUMP" or similar

6C0A
DEFB B8H B8
Error code B8H - Also compressed code for "READ" (B8H - A0H = 18H offset).
6C0B
DEFB 87H 87
Compressed string code 87H - "IF".
6C0C
DEFB D5H D5
Compressed string code D5H - References longer word from A0H table.
6C0D
DEFB 03H 03
Entry separator 03H.

Error Entry 11: Error Code 0EH

6C0E
DEFB 0EH 0E
Error code 0EH - DOS error code.
6C0F
DEFB 00H 00
Message terminator 00H.

Error Entry 12: Error Code A8H - "DISK SOURCE" or similar

6C10
DEFB A8H A8
Error code A8H - Compressed code for "DISK".
6C11
DEFB B5H B5
Compressed string code B5H - "SOURCE" or similar.
6C12
DEFB ABH AB
Compressed string code ABH.
6C13
DEFB 03H 03
Entry separator 03H.

Error Entry 13: Error Code 0FH

6C14
DEFB 0FH 0F
Error code 0FH - DOS error code.
6C15
DEFB 00H 00
Message terminator 00H.

Error Entry 14: Error Code B5H - "SOURCE SYSTEM" related

6C16
DEFB B5H B5
Error code B5H - Compressed code for "SOURCE".
6C17
DEFB D8H D8
Compressed string code D8H - References word from A0H table.
6C18
DEFB CEH CE
Compressed string code CEH - "PARITY" or similar.
6C19
DEFB 03H 03
Entry separator 03H.

Error Entry 15: Error Codes 1CH, 1DH

6C1A
DEFB 1CH 1C
Error code 1CH - DOS error code.
6C1B
DEFB 1DH 1D
Additional code 1DH or part of message.
6C1C
DEFB 00H 00
Message terminator 00H.

6C1DH - Error Message Table (Continued)

Continuation of the error message lookup table. Each entry consists of compressed message bytes using codes from the 80H-FFH range, terminated by 03H separators. Error codes appear as bytes before 00H markers. The messages use the compressed word system where bytes 80H-9FH represent short words (AT, BE, DO, IF, IS, etc.) and bytes A0H-FFH represent longer words (BUFFER, DISK, MEMORY, SECTOR, etc.).

Error message entries with compressed text

6C1D-6C1E
DEFB 76H,74H 76 74
Format control bytes 76H and 74H - cursor/display positioning codes for this message entry.
6C1F
DEFB B6H B6
Compressed word B6H = "BUFFER" from A0H table.
6C20
DEFB 82H 82
Compressed word 82H = "AT" from 80H table.
6C21
DEFB 7BH 7B
Format control 7BH - display positioning code.
6C22
DEFB CEH CE
Compressed word CEH = "PARITY" from A0H table.
6C23
DEFB 74H 74
Format control 74H - display positioning code.
6C24
DEFB 95H 95
Compressed word 95H = "TOO" from 80H table. Combined message: "BUFFER AT ... PARITY ... TOO".
6C25
DEFB 03H 03
Entry separator 03H - marks end of this message entry.

Next error table entry

6C26-6C27
DEFB 20H,00H 20 00
Error code structure: 20H (space or error code 32), 00H (separator before message).
6C28
DEFB C6H C6
Compressed word C6H = "MEMORY" from A0H table.
6C29
DEFB A8H A8
Compressed word A8H = "DISK". Combined: "MEMORY DISK".
6C2A
DEFB 75H 75
Format control 75H - display positioning code.
6C2B
DEFB 03H 03
Entry separator 03H - marks end of this message entry.
6C2C
DEFB 00H 00
Null byte 00H - separator or end marker.
6C2D
DEFB D0H D0
Compressed word D0H = "RECORD" from A0H table.
6C2E
DEFB D6H D6
Compressed word D6H - word from A0H table.
6C2F
DEFB 03H 03
Entry separator 03H - marks end of this message entry.

6C30H - APPARAT Copyright Message

This section contains the APPARAT company name as part of a copyright or identification message displayed by SUPERZAP. APPARAT was the company that created NEWDOS/80. The message uses format control codes (bytes 60H-7FH) for cursor positioning around the text.

6C30
DEFB 72H 72
Format control 72H - cursor positioning code before company name.
6C31-6C37
DEFM "APPARAT" 41 50 50 41 52 41 54
ASCII string "APPARAT" - The company that created NEWDOS/80 and SUPERZAP.
6C38
DEFB 6BH 6B
Format control 6BH - cursor positioning code after company name.
6C39-6C3C
DEFB D4H,2FH,38H,30H D4 2F 38 30
Message: D4H (compressed word) + "/80" (ASCII 2FH,38H,30H). Part of version string, likely displaying as "... /80" for NEWDOS/80.
6C3D
DEFB 6AH 6A
Format control 6AH - cursor positioning code.

6C3EH - Menu Header Text

Header text displayed above the SUPERZAP command menu. Uses compressed strings and formatting codes to display introductory text before the list of available commands.

6C3E
DEFB ADH AD
Compressed word ADH from A0H table - part of header message.
6C3F-6C42
DEFM " ONE" 20 4F 4E 45
ASCII string " ONE" - part of instruction text.
6C43
DEFB 7BH 7B
Format control 7BH - cursor positioning.
6C44
DEFB 89H 89
Compressed word 89H = "OK" from 80H table.
6C45-6C4E
DEFM " FOLLOWING" 20 46 4F 4C 4C 4F 57 49 4E 47
ASCII string " FOLLOWING" - part of instruction text.
6C4F
DEFB D0H D0
Compressed word D0H = "RECORD" - or may have bit 7 set as terminator for previous string.
6C50
DEFB 53H 53
ASCII 'S' - plural suffix, making "RECORDS".
6C51
DEFB 3AH 3A
ASCII ':' - colon separator before menu list.
6C52
DEFB 0DH 0D
Carriage return 0DH - new line before menu entries. Header displays approximately: "... ONE ... OK FOLLOWING RECORDS:".

6C53H - Menu Command Entry: 'DD - Disk Dump

Menu entry for the 'DD (Disk Dump to Disk) command. Each menu entry consists of a quote prefix (27H), the command letters, a format control code (6CH), and compressed text describing the command function, ending with a carriage return (0DH). Format control bytes in the 60H-7FH range control cursor positioning for the menu display.

6C53
DEFB 27H 27
ASCII ' (single quote) - Menu command prefix marker.
6C54-6C55
DEFM "DD" 44 44
ASCII string "DD" - Command name: Disk Dump (copy disk to disk).
6C56
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning for description column.
6C57
DEFB 7DH 7D
Format control 7DH - additional display positioning.
6C58-6C5C
DEFM " NULL" 20 4E 55 4C 4C
ASCII string " NULL" - description text (disk-to-disk with null/empty source handling).
6C5D
DEFB 60H 60
Format control 60H - display positioning.
6C5E
DEFB C5H C5
Compressed word C5H = "MEMORY" from A0H table.
6C5F
DEFB 92H 92
Compressed word 92H = "THE" from 80H table.
6C60
DEFB BEH BE
Compressed word BEH = "SECTOR" from A0H table.
6C61
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C62H - Menu Command Entry: 'DM - Dump Memory

Menu entry for the 'DM (Dump Memory) command, which displays memory contents in hex and ASCII format.

6C62
DEFB 27H 27
ASCII ' - Menu command prefix.
6C63-6C64
DEFM "DM" 44 4D
ASCII string "DM" - Command name: Dump Memory.
6C65
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C66
DEFB C5H C5
Compressed word C5H = "MEMORY".
6C67
DEFB 97H 97
Compressed word 97H = "YOU" from 80H table.
6C68
DEFB B9H B9
Compressed word B9H = "SEEK" from A0H table.
6C69
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C6AH - Menu Command Entry: 'DFS - Disk File Sector

Menu entry for the 'DFS (Disk File Sector) command, which displays sectors belonging to a specific file.

6C6A
DEFB 27H 27
ASCII ' - Menu command prefix.
6C6B-6C6D
DEFM "DFS" 44 46 53
ASCII string "DFS" - Command name: Disk File Sector display.
6C6E
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C6F
DEFB C5H C5
Compressed word C5H = "MEMORY".
6C70
DEFB 95H 95
Compressed word 95H = "TOO" from 80H table.
6C71
DEFB 6BH 6B
Format control 6BH - display positioning.
6C72
DEFB BEH BE
Compressed word BEH = "SECTOR".
6C73
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C74H - Menu Command Entry: 'DTS - Disk Track Sector

Menu entry for the 'DTS (Disk Track Sector) command, which displays sectors by track and sector number.

6C74
DEFB 27H 27
ASCII ' - Menu command prefix.
6C75-6C77
DEFM "DTS" 44 54 53
ASCII string "DTS" - Command name: Disk Track Sector display.
6C78
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C79
DEFB C5H C5
Compressed word C5H = "MEMORY".
6C7A
DEFB B3H B3
Compressed word B3H = "SOURCE" from A0H table.
6C7B
DEFB 6BH 6B
Format control 6BH - display positioning.
6C7C
DEFB BEH BE
Compressed word BEH = "SECTOR".
6C7D
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C7EH - Menu Command Entry: 'DMDB - Dump Memory Data Block

Menu entry for the 'DMDB (Dump Memory Data Block) command for viewing memory in block format.

6C7E
DEFB 27H 27
ASCII ' - Menu command prefix.
6C7F-6C82
DEFM "DMDB" 44 4D 44 42
ASCII string "DMDB" - Command name: Dump Memory Data Block.
6C83
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C84
DEFB C5H C5
Compressed word C5H = "MEMORY".
6C85
DEFB B9H B9
Compressed word B9H = "SEEK".
6C86
DEFB 93H 93
Compressed word 93H = "ALL" from 80H table.
6C87
DEFB A6H A6
Compressed word A6H = "DATA" from A0H table.
6C88
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C89H - Menu Command Entry: 'VDS - Verify Disk Sector

Menu entry for the 'VDS (Verify Disk Sector) command for verifying disk sector integrity.

6C89
DEFB 27H 27
ASCII ' - Menu command prefix.
6C8A-6C8C
DEFM "VDS" 56 44 53
ASCII string "VDS" - Command name: Verify Disk Sector.
6C8D
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C8E
DEFB C1H C1
Compressed word C1H = "VERIFY" from A0H table.
6C8F
DEFB 92H 92
Compressed word 92H = "THE".
6C90
DEFB BEH BE
Compressed word BEH = "SECTOR".
6C91
DEFB 53H 53
ASCII 'S' - Plural suffix making "SECTORS".
6C92
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C93H - Menu Command Entry: 'ZDS - Zap Disk Sector

Menu entry for the 'ZDS (Zap Disk Sector) command for writing/modifying disk sectors.

6C93
DEFB 27H 27
ASCII ' - Menu command prefix.
6C94-6C96
DEFM "ZDS" 5A 44 53
ASCII string "ZDS" - Command name: Zap Disk Sector (write/modify).
6C97
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6C98
DEFB A5H A5
Compressed word A5H = "COPY" from A0H table.
6C99
DEFB 92H 92
Compressed word 92H = "THE".
6C9A
DEFB BEH BE
Compressed word BEH = "SECTOR".
6C9B
DEFB 53H 53
ASCII 'S' - Plural suffix making "SECTORS".
6C9C
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6C9DH - Menu Command Entry: 'CDS - Copy Disk Sector

Menu entry for the 'CDS (Copy Disk Sector) command for copying sectors between locations.

6C9D
DEFB 27H 27
ASCII ' - Menu command prefix.
6C9E-6CA0
DEFM "CDS" 43 44 53
ASCII string "CDS" - Command name: Copy Disk Sector.
6CA1
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6CA2
DEFB 90H 90
Compressed word 90H = "AND" from 80H table.
6CA3
DEFB 92H 92
Compressed word 92H = "THE".
6CA4
DEFB BEH BE
Compressed word BEH = "SECTOR".
6CA5
DEFB 53H 53
ASCII 'S' - Plural suffix making "SECTORS".
6CA6
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6CA7H - Menu Command Entry: 'CDD - Copy Disk to Disk

Menu entry for the 'CDD (Copy Disk to Disk) command for full disk copying.

6CA7
DEFB 27H 27
ASCII ' - Menu command prefix.
6CA8-6CAA
DEFM "CDD" 43 44 44
ASCII string "CDD" - Command name: Copy Disk to Disk.
6CAB
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6CAC
DEFB 90H 90
Compressed word 90H = "AND".
6CAD
DEFB 92H 92
Compressed word 92H = "THE".
6CAE
DEFB 91H 91
Compressed word 91H = "NOT" from 80H table.
6CAF
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6CB0H - Menu Command Entry: 'DPWE - Disk Password Write Enable

Menu entry for the 'DPWE (Disk Password Write Enable) command for enabling write access with password.

6CB0
DEFB 27H 27
ASCII ' - Menu command prefix.
6CB1-6CB4
DEFM "DPWE" 44 50 57 45
ASCII string "DPWE" - Command name: Disk Password Write Enable.
6CB5
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6CB6
DEFB C5H C5
Compressed word C5H = "MEMORY".
6CB7
DEFB D2H D2
Compressed word D2H = "RETURN" from A0H table.
6CB8-6CBA
DEFM " EN" 20 45 4E
ASCII string " EN" - Part of description text.
6CBB
DEFB 08H 08
Format control 08H - backspace/formatting code.
6CBC
DEFB 8FH 8F
Compressed word 8FH = "OR" from 80H table.
6CBD
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6CBEH - Menu Command Entry: 'DNTH - Disk N-th Sector

Menu entry for the 'DNTH command for displaying the N-th absolute sector of a disk.

6CBE
DEFB 27H 27
ASCII ' - Menu command prefix.
6CBF-6CC2
DEFM "DNTH" 44 4E 54 48
ASCII string "DNTH" - Command name: Disk N-TH sector.
6CC3
DEFB 6CH 6C
Format control 6CH - cursor/tab positioning.
6CC4
DEFB C5H C5
Compressed word C5H = "MEMORY".
6CC5
DEFB 9BH 9B
Compressed word 9BH = "END" from 80H table.
6CC6
DEFB 74H 74
Format control 74H - display positioning.
6CC7
DEFB A2H A2
Compressed word A2H = "BASE" from A0H table.
6CC8-6CCC
DEFM " HASH" 20 48 41 53 48
ASCII string " HASH" - description text (referring to sector hash/number).
6CCD
DEFB 8FH 8F
Compressed word 8FH = "OR".
6CCE
DEFB 0DH 0D
Carriage return 0DH - end of menu entry line.

6CCFH - Menu Help Text: Printer Option

Help text explaining the ",P" printer option that can be appended to certain commands. This section describes which commands support printer output.

6CCF
DEFB 27H 27
ASCII ' - Quote marker for help text.
6CD0
DEFB 08H 08
Format control 08H - backspace/formatting.
6CD1
DEFB 94H 94
Compressed word 94H = "FOR" from 80H table.
6CD2
DEFB 6CH 6C
Format control 6CH - cursor positioning.
6CD3
DEFB 82H 82
Compressed word 82H = "AT" from 80H table.
6CD4
DEFB D4H D4
Compressed word D4H from A0H table.
6CD5
DEFB 2CH 2C
ASCII ',' - Comma separator.
6CD6
DEFB 94H 94
Compressed word 94H = "FOR".
6CD7
DEFB 7EH 7E
Format control 7EH - display positioning.
6CD8-6CDB
DEFM " DOS" + 0DH 20 44 4F 53 0D
ASCII string " DOS" + carriage return - Reference to DOS operations.
6CDC
DEFB 08H 08
Format control 08H - backspace/formatting.
6CDD
DEFB CAH CA
Compressed word CAH from A0H table.
6CDE-6CE5
DEFM " OUTPUT" 20 4F 55 54 50 55 54
ASCII string " OUTPUT" - printer output option text.
6CE6
DEFB 6AH 6A
Format control 6AH - display positioning.
6CE7-6CED
DEFM " APPEND" 20 41 50 50 45 4E 44
ASCII string " APPEND" - Append option for printer output.
6CEE-6CF1
DEFM " ,P~" 20 2C 50 7E
ASCII string " ,P" + format control 7EH - The ",P" printer option syntax.
6CF2-6CF5
DEFM " DD," 20 44 44 2C
ASCII string " DD," - DD command supports printer.
6CF6-6CF9
DEFM " DM," 20 44 4D 2C
ASCII string " DM," - DM command supports printer.
6CFA-6CFE
DEFM " DFS," 20 44 46 53 2C
ASCII string " DFS," - DFS command supports printer.
6CFF-6D03
DEFM " DTS}" 20 44 54 53 7D
ASCII string " DTS" + format control 7DH - DTS command supports printer, with closing format code.

6D04H - Menu Help Text: DMDB Command

Continuation of menu help text mentioning the DMDB command.

6D04-6D09
DEFM " DMDB" + 0DH 20 44 4D 44 42 0D
ASCII string " DMDB" + carriage return - Reference to Dump Memory Data Block command.
6D0A
DEFB 03H 03
Entry separator 03H - marks end of this help section.

6D0BH - Compressed Message Strings

Compressed message strings used for various prompts and status displays. These use compressed word codes (80H-FFH), format control bytes (60H-7FH), and 03H as entry separators.

6D0B
DEFB BFH BF
Compressed word BFH = "ZERO" from A0H table.
6D0C-6D0D
DEFB 20H,03H 20 03
Space + entry separator - "ZERO " message.
6D0E
DEFB DBH DB
Compressed word DBH = "DESTINATION" from A0H table.
6D0F-6D10
DEFB 20H,03H 20 03
Space + entry separator - "DESTINATION " message.
6D11
DEFB A0H A0
Compressed word A0H = space from A0H table.
6D12
DEFB 8BH 8B
Compressed word 8BH = "OR".
6D13
DEFB A3H A3
Compressed word A3H = "BYTE".
6D14
DEFB 7EH 7E
Format control 7EH - display positioning.
6D15
DEFB 78H 78
Format control 78H - display positioning.
6D16
DEFB A1H A1
Compressed word A1H = "BASE".
6D17
DEFB 67H 67
Format control 67H - display positioning.
6D18
DEFB 66H 66
Format control 66H - display positioning.
6D19
DEFB 03H 03
Entry separator 03H.

6D1AH - Sector Operation Messages

Compressed messages related to sector operations including "COPY THE SECTORS" and similar descriptions. Format control bytes (60H-7FH) provide cursor positioning.

6D1A
DEFB 68H 68
Format control 68H - display positioning.
6D1B
DEFB A5H A5
Compressed word A5H = "COPY".
6D1C
DEFB 92H 92
Compressed word 92H = "THE".
6D1D
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D1E
DEFB 53H 53
ASCII 'S' - plural suffix making "SECTORS".
6D1F
DEFB 67H 67
Format control 67H - display positioning.
6D20
DEFB 03H 03
Entry separator 03H - Message: "COPY THE SECTORS".
6D21
DEFB 68H 68
Format control 68H - display positioning.
6D22
DEFB 90H 90
Compressed word 90H = "AND".
6D23
DEFB 92H 92
Compressed word 92H = "THE".
6D24
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D25
DEFB 53H 53
ASCII 'S' - plural suffix.
6D26
DEFB 67H 67
Format control 67H - display positioning.
6D27
DEFB 03H 03
Entry separator 03H - Message: "AND THE SECTORS".
6D28
DEFB 68H 68
Format control 68H - display positioning.
6D29
DEFB 90H 90
Compressed word 90H = "AND".
6D2A
DEFB 92H 92
Compressed word 92H = "THE".
6D2B
DEFB 91H 91
Compressed word 91H = "NOT".
6D2C
DEFB 03H 03
Entry separator 03H - Message: "AND THE NOT".

6D2DH - Comparison and Search Messages

Compressed messages for comparison operations and search features. Format control bytes (60H-7FH) provide cursor positioning, compressed word codes (80H-FFH) reference the word tables, and 03H marks entry separators.

6D2D-6D2E
DEFB 20H,3DH 20 3D
ASCII " =" - equals sign with leading space.
6D2F
DEFB 20H 20
ASCII space.
6D30
DEFB 93H 93
Compressed word 93H = "ALL" from 80H table.
6D31
DEFB 6BH 6B
Format control 6BH - display positioning.
6D32
DEFB 8CH 8C
Compressed word 8CH = "TO" from 80H table.
6D33
DEFB B9H B9
Compressed word B9H = "SEEK".
6D34
DEFB C3H C3
Compressed word C3H = "CONTAIN".
6D35
DEFB 03H 03
Entry separator 03H.
6D36
DEFB 97H 97
Compressed word 97H = "YOU".
6D37
DEFB B9H B9
Compressed word B9H = "SEEK".
6D38
DEFB C3H C3
Compressed word C3H = "CONTAIN".
6D39
DEFB 6FH 6F
Format control 6FH - display positioning.
6D3A
DEFB 03H 03
Entry separator 03H.
6D3B
DEFB A8H A8
Compressed word A8H = "DISK".
6D3C
DEFB 2CH 2C
ASCII ',' - comma separator.
6D3D
DEFB B3H B3
Compressed word B3H = "SOURCE".
6D3E
DEFB 80H 80
Compressed word 80H = space from 80H table.
6D3F
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D40
DEFB 75H 75
Format control 75H - display positioning.
6D41
DEFB 6BH 6B
Format control 6BH - display positioning.
6D42
DEFB 6FH 6F
Format control 6FH - display positioning.
6D43
DEFB 03H 03
Entry separator 03H. Message: "DISK, SOURCE SECTOR".
6D44
DEFB B3H B3
Compressed word B3H = "SOURCE".
6D45
DEFB 80H 80
Compressed word 80H = space.
6D46
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D47
DEFB 75H 75
Format control 75H - display positioning.
6D48
DEFB 6BH 6B
Format control 6BH - display positioning.
6D49
DEFB 6FH 6F
Format control 6FH - display positioning.
6D4A
DEFB 03H 03
Entry separator 03H. Message: "SOURCE SECTOR".

6D4BH - Destination and Address Messages

Compressed messages for destination disk/sector and memory address operations.

6D4B
DEFB DDH DD
Compressed word DDH = "DESTINATION".
6D4C
DEFB B3H B3
Compressed word B3H = "SOURCE".
6D4D
DEFB 75H 75
Format control 75H - display positioning.
6D4E
DEFB 6FH 6F
Format control 6FH - display positioning.
6D4F
DEFB 03H 03
Entry separator. Message: "DESTINATION SOURCE".
6D50
DEFB A8H A8
Compressed word A8H = "DISK".
6D51
DEFB 80H 80
Compressed word 80H = space.
6D52
DEFB DDH DD
Compressed word DDH = "DESTINATION".
6D53
DEFB A8H A8
Compressed word A8H = "DISK".
6D54
DEFB 75H 75
Format control 75H.
6D55
DEFB 6BH 6B
Format control 6BH.
6D56
DEFB 6FH 6F
Format control 6FH.
6D57
DEFB 03H 03
Entry separator. Message: "DISK DESTINATION DISK".
6D58
DEFB DDH DD
Compressed word DDH = "DESTINATION".
6D59
DEFB A8H A8
Compressed word A8H = "DISK".
6D5A
DEFB 75H 75
Format control 75H.
6D5B
DEFB 6FH 6F
Format control 6FH.
6D5C
DEFB 03H 03
Entry separator. Message: "DESTINATION DISK".
6D5D
DEFB CFH CF
Compressed word CFH = "OFFSET".
6D5E
DEFB 6FH 6F
Format control 6FH.
6D5F
DEFB 03H 03
Entry separator. Message: "OFFSET".
6D60
DEFB 95H 95
Compressed word 95H = "TOO".
6D61
DEFB 9BH 9B
Compressed word 9BH = "END".
6D62
DEFB 6FH 6F
Format control 6FH.
6D63
DEFB 03H 03
Entry separator. Message: "TOO END" (value too high).
6D64
DEFB 95H 95
Compressed word 95H = "TOO".
6D65
DEFB A2H A2
Compressed word A2H = "BASE".
6D66
DEFB 6FH 6F
Format control 6FH.
6D67
DEFB 03H 03
Entry separator. Message: "TOO BASE" (value too low).
6D68
DEFB DDH DD
Compressed word DDH = "DESTINATION".
6D69
DEFB 95H 95
Compressed word 95H = "TOO".
6D6A
DEFB 75H 75
Format control 75H.
6D6B
DEFB 6FH 6F
Format control 6FH.
6D6C
DEFB 03H 03
Entry separator. Message: "DESTINATION TOO".

6D6DH - Input Prompt Messages

Short compressed messages for input prompts.

6D6D
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D6E
DEFB A7H A7
Compressed word A7H = "DUMP".
6D6F
DEFB 6FH 6F
Format control 6FH.
6D70
DEFB 03H 03
Entry separator. Message: "SECTOR DUMP".
6D71
DEFB 8DH 8D
Compressed word 8DH = "TO" from 80H table.
6D72
DEFB A7H A7
Compressed word A7H = "DUMP".
6D73
DEFB 6FH 6F
Format control 6FH.
6D74
DEFB 03H 03
Entry separator. Message: "TO DUMP".
6D75
DEFB 8DH 8D
Compressed word 8DH = "TO".
6D76
DEFB BAH BA
Compressed word BAH = "SKIP".
6D77
DEFB C2H C2
Compressed word C2H = "VERIFY".
6D78
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D79
DEFB 6FH 6F
Format control 6FH.
6D7A
DEFB 03H 03
Entry separator. Message: "TO SKIP VERIFY SECTOR".
6D7B
DEFB 93H 93
Compressed word 93H = "ALL".
6D7C
DEFB 97H 97
Compressed word 97H = "YOU".
6D7D
DEFB B9H B9
Compressed word B9H = "SEEK".
6D7E
DEFB C3H C3
Compressed word C3H = "CONTAIN".
6D7F
DEFB 6FH 6F
Format control 6FH.
6D80
DEFB 03H 03
Entry separator.

6D81H - Status and Error Messages

Various status messages and error indicators for disk operations.

6D81
DEFB AEH AE
Compressed word AEH = "INPUT".
6D82
DEFB A4H A4
Compressed word A4H = "CODE".
6D83
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D84
DEFB 9CH 9C
Compressed word 9CH = "EOF" from 80H table.
6D85
DEFB D8H D8
Compressed word D8H = "SYSTEM".
6D86
DEFB 67H 67
Format control 67H.
6D87
DEFB 66H 66
Format control 66H.
6D88
DEFB 03H 03
Entry separator.
6D89
DEFB AFH AF
Compressed word AFH = "PAUSE".
6D8A
DEFB 69H 69
Format control 69H.
6D8B
DEFB 7EH 7E
Format control 7EH.
6D8C
DEFB BDH BD
Compressed word BDH = "PROTECT".
6D8D
DEFB 7EH 7E
Format control 7EH.
6D8E
DEFB 99H 99
Compressed word 99H = "BAD" from 80H table.
6D8F
DEFB 03H 03
Entry separator.

6D90H - Retry/Skip/Exit Prompt Message

Compressed message for the retry/skip/exit prompt displayed after disk errors.

6D90
DEFB B7H B7
Compressed word B7H = "BUFFER".
6D91
DEFB 86H 86
Compressed word 86H = "DO" from 80H table.
6D92
DEFB C4H C4
Compressed word C4H = "ILLEGAL".
6D93
DEFB 9FH 9F
Compressed word 9FH = "FEW" from 80H table.
6D94
DEFB 7DH 7D
Format control 7DH.
6D95
DEFB 7FH 7F
Format control 7FH.
6D96
DEFB 7BH 7B
Format control 7BH.
6D97
DEFB BEH BE
Compressed word BEH = "SECTOR".
6D98
DEFB 91H 91
Compressed word 91H = "NOT".
6D99
DEFB 0DH 0D
Carriage return 0DH - end of line.
6D9A
DEFB 08H 08
Format control 08H - backspace.

6D9BH - File and Modification Messages

Compressed messages related to file operations and sector modifications.

6D9B
DEFB AFH AF
Compressed word AFH = "PAUSE".
6D9C
DEFB 69H 69
Format control 69H.
6D9D
DEFB 7EH 7E
Format control 7EH.
6D9E
DEFB C5H C5
Compressed word C5H = "MEMORY".
6D9F
DEFB B7H B7
Compressed word B7H = "BUFFER".
6DA0
DEFB CCH CC
Compressed word CCH from A0H table.
6DA1
DEFB 03H 03
Entry separator 03H.
6DA2
DEFB 72H 72
Format control 72H.
6DA3
DEFB B1H B1
Compressed word B1H = "EXTRA".
6DA4
DEFB 65H 65
Format control 65H.
6DA5
DEFB 79H 79
Format control 79H.
6DA6
DEFB 7CH 7C
Format control 7CH.
6DA7
DEFB 7EH 7E
Format control 7EH.
6DA8
DEFB B5H B5
Compressed word B5H = "SOURCE".
6DA9-6DB1
DEFM " MODIFIED" 20 4D 4F 44 49 46 49 45 44
ASCII string " MODIFIED".
6DB2
DEFB BEH BE
Compressed word BEH = "SECTOR".
6DB3
DEFB 7EH 7E
Format control 7EH.
6DB4
DEFB 92H 92
Compressed word 92H = "THE".
6DB5
DEFB 6DH 6D
Format control 6DH.
6DB6
DEFB 03H 03
Entry separator. Message: "SOURCE MODIFIED SECTOR THE".

6DB7H - Copy Operation Messages

Compressed messages displayed during copy operations.

6DB7
DEFB 7AH 7A
Format control 7AH.
6DB8
DEFB 7EH 7E
Format control 7EH.
6DB9
DEFB 77H 77
Format control 77H.
6DBA-6DC0
DEFM " COPIED" 20 43 4F 50 49 45 44
ASCII string " COPIED" - completion message for copy operations.
6DC1
DEFB 7EH 7E
Format control 7EH.
6DC2
DEFB 0DH 0D
Carriage return 0DH.
6DC3
DEFB 03H 03
Entry separator.

6DC4H - Cancelled/Aborted Messages

Messages displayed when operations are cancelled or aborted by the user.

6DC4
DEFB 72H 72
Format control 72H.
6DC5
DEFB DCH DC
Compressed word DCH from A0H table.
6DC6
DEFB D6H D6
Compressed word D6H from A0H table.
6DC7
DEFB 03H 03
Entry separator.
6DC8
DEFB 72H 72
Format control 72H.
6DC9
DEFB DCH DC
Compressed word DCH.
6DCA-6DD3
DEFM " CANCELLED" 20 43 41 4E 43 45 4C 4C 45 44
ASCII string " CANCELLED" - operation cancelled message.
6DD4
DEFB 03H 03
Entry separator.

6DD5H - Password and System Messages

Compressed messages related to password operations and system functions.

6DD5
DEFB AFH AF
Compressed word AFH = "PAUSE".
6DD6
DEFB 69H 69
Format control 69H.
6DD7
DEFB 7EH 7E
Format control 7EH.
6DD8
DEFB CDH CD
Compressed word CDH from A0H table.
6DD9
DEFB 6DH 6D
Format control 6DH.
6DDA
DEFB 03H 03
Entry separator.
6DDB
DEFB 72H 72
Format control 72H.
6DDC
DEFB C7H C7
Compressed word C7H from A0H table.
6DDD
DEFB DCH DC
Compressed word DCH.
6DDE
DEFB 9AH 9A
Compressed word 9AH from 80H table.
6DDF
DEFB 8EH 8E
Compressed word 8EH from 80H table.
6DE0
DEFB 6AH 6A
Format control 6AH.
6DE1
DEFB B1H B1
Compressed word B1H = "EXTRA".
6DE2
DEFB 61H 61
Format control 61H.
6DE3
DEFB 7EH 7E
Format control 7EH.
6DE4
DEFB CDH CD
Compressed word CDH.
6DE5
DEFB 6DH 6D
Format control 6DH.
6DE6
DEFB 03H 03
Entry separator.

6DE7H - Invalid Parameter Error Messages

Error messages displayed when invalid parameters are entered by the user. These use compressed codes with format controls and 03H separators between entries.

6DE7
DEFB C6H C6
Compressed word C6H = "MEMORY".
6DE8
DEFB CAH CA
Compressed word CAH from A0H table.
6DE9
DEFB CBH CB
Compressed word CBH = "PARITY".
6DEA
DEFB 03H 03
Entry separator.
6DEB
DEFB DAH DA
Compressed word DAH = "INVALID".
6DEC
DEFB A8H A8
Compressed word A8H = "DISK". Message: "INVALID DISK".
6DED
DEFB 75H 75
Format control 75H.
6DEE
DEFB 03H 03
Entry separator.
6DEF
DEFB DAH DA
Compressed word DAH = "INVALID".
6DF0
DEFB B3H B3
Compressed word B3H = "SOURCE". Message: "INVALID SOURCE".
6DF1
DEFB 75H 75
Format control 75H.
6DF2
DEFB 03H 03
Entry separator.
6DF3
DEFB DAH DA
Compressed word DAH = "INVALID".
6DF4
DEFB BEH BE
Compressed word BEH = "SECTOR". Message: "INVALID SECTOR".
6DF5
DEFB 75H 75
Format control 75H.
6DF6
DEFB 03H 03
Entry separator.
6DF7
DEFB DAH DA
Compressed word DAH = "INVALID".
6DF8
DEFB D3H D3
Compressed word D3H from A0H table.
6DF9
DEFB BEH BE
Compressed word BEH = "SECTOR".
6DFA
DEFB 75H 75
Format control 75H.
6DFB
DEFB 03H 03
Entry separator.
6DFC
DEFB DAH DA
Compressed word DAH = "INVALID".
6DFD
DEFB A7H A7
Compressed word A7H = "DUMP". Message: "INVALID DUMP" (address error).
6DFE
DEFB 03H 03
Entry separator.
6DFF
DEFB DAH DA
Compressed word DAH = "INVALID".
6E00
DEFB 97H 97
Compressed word 97H = "YOU".
6E01
DEFB B9H B9
Compressed word B9H = "SEEK". Message: "INVALID YOU SEEK".
6E02
DEFB C3H C3
Compressed word C3H = "CONTAIN".
6E03
DEFB 03H 03
Entry separator.
6E04
DEFB DAH DA
Compressed word DAH = "INVALID".
6E05
DEFB BAH BA
Compressed word BAH = "SKIP".
6E06
DEFB C2H C2
Compressed word C2H = "VERIFY".
6E07
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E08
DEFB B4H B4
Compressed word B4H from A0H table.
6E09
DEFB 03H 03
Entry separator.

6E0AH - Too Many/Too Few Error Messages

Error messages for parameter count errors using compressed word codes.

6E0A
DEFB 8AH 8A
Compressed word 8AH from 80H table.
6E0B
DEFB 84H 84
Compressed word 84H = "BE" from 80H table.
6E0C
DEFB D7H D7
Compressed word D7H = "WITHIN" from A0H table.
6E0D
DEFB 53H 53
ASCII 'S' - plural suffix.
6E0E
DEFB 03H 03
Entry separator 03H.
6E0F
DEFB 8AH 8A
Compressed word 8AH from 80H table.
6E10
DEFB 98H 98
Compressed word 98H from 80H table.
6E11
DEFB D7H D7
Compressed word D7H = "WITHIN".
6E12
DEFB 53H 53
ASCII 'S' - plural suffix.
6E13
DEFB 03H 03
Entry separator 03H.

6E14H - Embedded/Imbedded Command Message

Message related to embedded commands and special operations.

6E14
DEFB C8H C8
Compressed word C8H = "OFFSET" from A0H table.
6E15-6E1D
DEFM " IMBEDDED" 20 49 4D 42 45 44 44 45 44
ASCII string " IMBEDDED".
6E1E
DEFB D7H D7
Compressed word D7H = "WITHIN".
6E1F
DEFB 03H 03
Entry separator 03H.

6E20H - Sector Read/Write Error Messages

Error messages for sector read and write failures.

6E20
DEFB BFH BF
Compressed word BFH = "ZERO".
6E21
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E22
DEFB 88H 88
Compressed word 88H = "IS" from 80H table.
6E23
DEFB 7BH 7B
Format control 7BH.
6E24
DEFB B0H B0
Compressed word B0H = "BEYOND". Message: "ZERO SECTOR IS BEYOND".
6E25
DEFB 03H 03
Entry separator 03H.
6E26
DEFB DBH DB
Compressed word DBH = "DESTINATION".
6E27
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E28
DEFB 88H 88
Compressed word 88H = "IS".
6E29
DEFB 7BH 7B
Format control 7BH.
6E2A
DEFB B0H B0
Compressed word B0H = "BEYOND". Message: "DESTINATION SECTOR IS BEYOND".
6E2B
DEFB 03H 03
Entry separator 03H.

6E2CH - Sector Error Messages

Prefix messages used with sector error codes for read, write, and verify errors.

6E2C
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E2D
DEFB 9CH 9C
Compressed word 9CH = "EOF" from 80H table.
6E2E
DEFB A9H A9
Compressed word A9H = "EXIT".
6E2F
DEFB 03H 03
Entry separator. Message: "SECTOR EOF EXIT" (sector read error).
6E30
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E31
DEFB B5H B5
Compressed word B5H = "SOURCE".
6E32
DEFB A9H A9
Compressed word A9H = "EXIT".
6E33
DEFB 03H 03
Entry separator. Message: "SECTOR SOURCE EXIT" (sector write error).
6E34
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E35
DEFB C1H C1
Compressed word C1H = "VERIFY".
6E36
DEFB A9H A9
Compressed word A9H = "EXIT".
6E37
DEFB 03H 03
Entry separator. Message: "SECTOR VERIFY EXIT".

6E38H - Error Code and Previous Operation Messages

Messages for displaying error codes and referencing previous operations.

6E38
DEFB C0H C0
Compressed word C0H from A0H table.
6E39
DEFB A9H A9
Compressed word A9H = "EXIT".
6E3A
DEFB 8FH 8F
Compressed word 8FH = "OR" from 80H table.
6E3B
DEFB 20H 20
ASCII space.
6E3C
DEFB 03H 03
Entry separator 03H.
6E3D
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E3E
DEFB 87H 87
Compressed word 87H = "IF" from 80H table.
6E3F-6E56
DEFM " PREVIOUSLY SUCCESSFULLY" 20 50 52 45 56 49 4F 55 53 4C 59 20 53 55 43 43 45 53 53 46 55 4C 4C 59
ASCII string " PREVIOUSLY SUCCESSFULLY".
6E57
DEFB 9CH 9C
Compressed word 9CH = "EOF".
6E58
DEFB 03H 03
Entry separator 03H.

6E59H - Internal Programming Error Message

Error message displayed for internal programming errors - this indicates a bug in SUPERZAP itself rather than a user error.

6E59
DEFB D4H D4
Compressed word D4H from A0H table.
6E5A-6E6E
DEFM " INTERNAL PROGRAMMING" 20 49 4E 54 45 52 4E 41 4C 20 50 52 4F 47 52 41 4D 4D 49 4E 47
ASCII string " INTERNAL PROGRAMMING".
6E6F
DEFB A9H A9
Compressed word A9H = "EXIT". Message: "INTERNAL PROGRAMMING EXIT" (error).
6E70
DEFB 03H 03
Entry separator 03H.

6E71H - Retry/Skip/Exit Option Prompt

The standard error recovery prompt showing available options after an error occurs. Uses compressed codes and format control bytes to display "'R'ETRY, 'S'KIP, E'X'IT".

6E71
DEFB B1H B1
Compressed word B1H = "EXTRA".
6E72
DEFB 62H 62
Format control 62H.
6E73
DEFB 85H 85
Compressed word 85H = "BY" from 80H table.
6E74
DEFB B2H B2
Compressed word B2H = "FOUND".
6E75
DEFB 2CH 2C
ASCII ',' - comma.
6E76
DEFB 63H 63
Format control 63H.
6E77
DEFB 85H 85
Compressed word 85H = "BY".
6E78
DEFB 9EH 9E
Compressed word 9EH from 80H table.
6E79
DEFB A9H A9
Compressed word A9H = "EXIT".
6E7A
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E7B
DEFB 2CH 2C
ASCII ',' - comma.
6E7C
DEFB 7DH 7D
Format control 7DH.
6E7D
DEFB 64H 64
Format control 64H.
6E7E
DEFB 7EH 7E
Format control 7EH.
6E7F
DEFB 0DH 0D
Carriage return 0DH.
6E80
DEFB 08H 08
Format control 08H - backspace.

6E81H - Record/Byte Display Messages

Messages used when displaying records and bytes.

6E81
DEFB D9H D9
Compressed word D9H = "DISKETTE".
6E82
DEFB D0H D0
Compressed word D0H = "RECORD".
6E83
DEFB 6DH 6D
Format control 6DH.
6E84
DEFB 03H 03
Entry separator. Message: "DISKETTE RECORD".
6E85
DEFB D0H D0
Compressed word D0H = "RECORD".
6E86
DEFB D9H D9
Compressed word D9H = "DISKETTE".
6E87
DEFB 44H 44
ASCII 'D'.
6E88-6E8A
DEFM " BY" 20 42 59
ASCII string " BY".
6E8B
DEFB D1H D1
Compressed word D1H = "RETURN".
6E8C
DEFB 03H 03
Entry separator.

6E8DH - Display Label Messages

Short label messages used in the status display area for disk, source, sector, DRS, FRS, and other labels.

6E8D
DEFB A8H A8
Compressed word A8H = "DISK".
6E8E
DEFB 20H 20
ASCII space.
6E8F
DEFB 03H 03
Entry separator. Label: "DISK ".
6E90
DEFB B3H B3
Compressed word B3H = "SOURCE".
6E91
DEFB 20H 20
ASCII space.
6E92
DEFB 03H 03
Entry separator. Label: "SOURCE ".
6E93
DEFB BEH BE
Compressed word BEH = "SECTOR".
6E94
DEFB 20H 20
ASCII space.
6E95
DEFB 03H 03
Entry separator. Label: "SECTOR ".
6E96-6E98
DEFM "DRS" 44 52 53
ASCII string "DRS" - Drive/Relative Sector.
6E99
DEFB 20H 20
ASCII space.
6E9A
DEFB 03H 03
Entry separator. Label: "DRS ".
6E9B-6E9D
DEFM "FRS" 46 52 53
ASCII string "FRS" - File/Record/Sector.
6E9E
DEFB 20H 20
ASCII space.
6E9F
DEFB 03H 03
Entry separator. Label: "FRS ".
6EA0
DEFB 2CH 2C
ASCII ',' - comma.
6EA1
DEFB 20H 20
ASCII space.
6EA2
DEFB 03H 03
Entry separator. Label: ", ".
6EA3
DEFB 48H 48
ASCII 'H'.
6EA4-6EA5
DEFM " " 20 20
ASCII two spaces (padding).
6EA6
DEFB 03H 03
Entry separator. Label: "H " (hex suffix).
6EA7
DEFB 2DH 2D
ASCII '-' - dash.
6EA8-6EA9
DEFM " " 20 20
ASCII two spaces (padding).
6EAA
DEFB 03H 03
Entry separator. Label: "- ".

6EABH - Enable/Disable Status Messages

Messages for feature availability and enable/disable status.

6EAB
DEFB BEH BE
Compressed word BEH = "SECTOR".
6EAC
DEFB 87H 87
Compressed word 87H = "IF".
6EAD
DEFB 9CH 9C
Compressed word 9CH = "EOF".
6EAE-6EB1
DEFM "ABLE" 41 42 4C 45
ASCII string "ABLE".
6EB2
DEFB 03H 03
Entry separator.
6EB3
DEFB BEH BE
Compressed word BEH = "SECTOR".
6EB4
DEFB 87H 87
Compressed word 87H = "IF".
6EB5
DEFB 9CH 9C
Compressed word 9CH = "EOF".
6EB6
DEFB D8H D8
Compressed word D8H = "SYSTEM".
6EB7
DEFB 03H 03
Entry separator.
6EB8
DEFB BEH BE
Compressed word BEH = "SECTOR".
6EB9
DEFB 9CH 9C
Compressed word 9CH = "EOF".
6EBA
DEFB D8H D8
Compressed word D8H = "SYSTEM".
6EBB
DEFB 03H 03
Entry separator.

6EBCH - Shall I Write Confirmation Prompt

Confirmation prompt asking the user if SUPERZAP should write changes to disk.

6EBC-6EC3
DEFM "SHALL IT" 53 48 41 4C 4C 20 49 54
ASCII string "SHALL IT".
6EC4-6EC5
DEFM " w" 20 77
ASCII string " w".
6EC6
DEFB 9CH 9C
Compressed word 9CH = "EOF".
6EC7
DEFB D8H D8
Compressed word D8H = "SYSTEM".
6EC8
DEFB 67H 67
Format control 67H.
6EC9
DEFB 66H 66
Format control 66H.
6ECA
DEFB 03H 03
Entry separator. Prompt: "SHALL IT WRITE?".

6ECBH - Partial Data Due Message

Message indicating partial data was read or written.

6ECB-6ED1
DEFM "PARTIAL" 50 41 52 54 49 41 4C
ASCII string "PARTIAL".
6ED2
DEFB 20H 20
ASCII space.
6ED3
DEFB A6H A6
Compressed word A6H = "DATA".
6ED4-6ED7
DEFM " DUE" 20 44 55 45
ASCII string " DUE".
6ED8
DEFB 7EH 7E
Format control 7EH.
6ED9
DEFB 83H 83
Compressed word 83H = "AN" from 80H table.
6EDA
DEFB 03H 03
Entry separator. Message: "PARTIAL DATA DUE".

6EDBH - No Match Message

Message displayed when a search operation finds no matches.

6EDB
DEFB 72H 72
Format control 72H.
6EDC-6EE3
DEFM "NO MATCH" 4E 4F 20 4D 41 54 43 48
ASCII string "NO MATCH".
6EE4
DEFB 0DH 0D
Carriage return 0DH.
6EE5
DEFB 03H 03
Entry separator. Message: "NO MATCH".

6EE6H - Under DOS-Call Message

Technical message about DOS call status.

6EE6
DEFB D2H D2
Compressed word D2H = "RETURN".
6EE7
DEFB 6FH 6F
Format control 6FH.
6EE8
DEFB 03H 03
Entry separator.
6EE9
DEFB D0H D0
Compressed word D0H = "RECORD".
6EEA
DEFB C6H C6
Compressed word C6H = "MEMORY".
6EEB-6EF9
DEFM " UNDER DOS-CALL" 20 55 4E 44 45 52 20 44 4F 53 2D 43 41 4C 4C
ASCII string " UNDER DOS-CALL".
6EFA
DEFB 03H 03
Entry separator.

6EFBH - Final Message Entry

Last message entry in the string table.

6EFB
DEFB 97H 97
Compressed word 97H = "YOU".
6EFC
DEFB B9H B9
Compressed word B9H = "SEEK".
6EFD
DEFB B0H B0
Compressed word B0H = "BEYOND".
6EFE
DEFB 6DH 6D
Format control 6DH.
6EFF
DEFB 03H 03
Entry separator. Message: "YOU SEEK BEYOND".

6F00H - Buffer/Work Area (Zeros)

This area from 6F00H to 6FFDH is initialized to zeros and serves as a work buffer or reserved space for SUPERZAP operations. The 254 bytes of zeros provide scratch space for various disk and memory operations.

6F00-6FFD
DEFS 254,00H 00 00 00 ... (254 bytes)
254 bytes of zeros - Work buffer/reserved area used for temporary storage during SUPERZAP disk operations.

Program Entry Point

SUPERZAP's program entry point is at address 54C5H. When SUPERZAP is loaded and executed, control transfers to this address to begin the main initialization and menu display sequence.

ENTRY
ORG 54C5H
Program Entry = 54C5H - SUPERZAP execution begins at this address.