5200H - Program Entry, Sign-On, and File Opening
PATCH is loaded and run by the DOS command interpreter with Register Pair HL pointing at the command line following the word PATCH. This section displays the sign-on banner, parses and opens the object file to be patched, and parses the /FIX patch filename, copying it into the CLP name buffer.
5200
PUSH HL E5
Save Register Pair HL (the DOS command-line pointer, positioned just past the command verb) on the stack while the banner is printed.
5201
LD HL,58A5H 21 A5 58
Point Register Pair HL at the sign-on banner text at 58A5H.
5204
GOSUB to the resident @DSPLY routine to display the banner (Register Pair HL) on the video screen.
5207
POP HL E1
Restore Register Pair HL to the command-line pointer saved at 5200H.
5208
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at 5AF0H, the File Control Block that will describe the object file being patched.
520B
GOSUB to the resident @FSPEC routine to parse the filespec at (HL) into the File Control Block at 5AF0H.
520E
If @FSPEC returned the NZ FLAG (the filespec was malformed), JUMP to the error exit at 5880H, which reports "PROGRAM file name required".
5211
LD A,(DE) 1A
Load Register A with the first byte of the parsed filespec at 5AF0H (the first filename character, or 2AH for a device name).
5212
CP 2AH FE 2A
Compare Register A against 2AH (ASCII *). If it equals, the Z FLAG is set, marking a device specification rather than a disk file.
5214
If the Z FLAG is set (the object name was a device such as *XX), JUMP to the error exit at 5880H; PATCH only patches disk files.
5217
PUSH HL E5
Save Register Pair HL (command-line pointer) while the default extension is applied.
5218
LD HL,589FH 21 9F 58
Point Register Pair HL at the three-character default extension "CMD" at 589FH.
521B
GOSUB to the resident @FEXT routine, which supplies the default extension at (HL) to the File Control Block at (DE=5AF0H) when the filespec named none, so a bare name defaults to a /CMD file.
521E
LD HL,5E00H 21 00 5E
Point Register Pair HL at 5E00H, the 256-byte sector buffer that @OPEN will attach to the object file.
5221
LD B,00H 06 00
Load Register B with 00H, the logical record length passed to @OPEN (0 means a full 256-byte record).
5223
GOSUB to the resident @OPEN routine to open the object file described by the File Control Block at 5AF0H, using sector buffer 5E00H.
5226
If @OPEN returned the NZ FLAG (the object file could not be opened), JUMP to the shared error exit at 5867H, which passes the error code to @ERROR.
5229
POP HL E1
Restore Register Pair HL to the command-line pointer.
522A
LD DE,5B10H 11 10 5B
Point Register Pair DE at 5B10H, the File Control Block that will describe the /FIX patch file.
522D
GOSUB to @FSPEC to parse the next filespec on the command line (the patch file) into the File Control Block at 5B10H.
5230
If @FSPEC returned the NZ FLAG (no second filespec was present), JUMP to 525EH to scan the command line for a parenthesised option list or an inline patch instead of a /FIX file.
5233
PUSH HL E5
Save Register Pair HL (command-line pointer) while the default extension is applied to the patch file.
5234
LD HL,58A2H 21 A2 58
Point Register Pair HL at the three-character default extension "FIX" at 58A2H.
5237
GOSUB to @FEXT to give the patch File Control Block at (DE=5B10H) the default extension /FIX when the filespec named none.
523A
LD HL,5B10H 21 10 5B
Point Register Pair HL at 5B10H; before the file is opened, the File Control Block still begins with the filespec text, so its bytes are read here as ASCII characters.
523D
LD DE,5AC1H 11 C1 5A
Point Register Pair DE at 5AC1H, the eight-byte CLP name buffer that will hold the patch identifier.
5240
LD B,00H 06 00
Load Register B with 0 to count the name characters copied.
Loop Start
The following loop copies the alphanumeric characters of the patch filename into the CLP name buffer, stopping at the extension slash or the first non-alphanumeric character.
5242
LD A,(HL) 7E
Load Register A with the next filespec character at (HL) within the patch File Control Block.
5243
INC HL 23
Advance Register Pair HL to the following filespec character.
5244
CP 2FH FE 2F
Compare Register A against 2FH (ASCII /). If it equals, the Z FLAG is set, marking the start of the extension.
5246
If the Z FLAG is set (the slash before the extension was reached), jump forward to 5259H to finish the name.
5248
CP 3AH FE 3A
Compare Register A against 3AH (ASCII :). If Register A is below 3AH the CARRY FLAG is set, covering the digits 0-9 and lower codes.
524A
If the CARRY FLAG is set (the character is 3AH or below, i.e. a digit or separator kept as part of the name), jump to 5254H to store it.
524C
CP 41H FE 41
Compare Register A against 41H (ASCII A). If Register A is below 41H the CARRY FLAG is set (a character between : and @).
524E
If the CARRY FLAG is set (a punctuation character below A), jump to 5259H to end the name.
5250
CP 5BH FE 5B
Compare Register A against 5BH (ASCII [, one past Z). If Register A is 5BH or above the NO CARRY FLAG is set.
5252
If the NO CARRY FLAG is set (the character is past Z), jump to 5259H to end the name; only digits and letters are copied.
5254
LD (DE),A 12
Store the accepted name character (Register A) into the CLP name buffer at (DE).
5255
INC DE 13
Advance Register Pair DE to the next CLP buffer position.
5256
INC B 04
Increment Register B, the count of name characters copied.
5257
LOOP BACK to 5242H to test and copy the next filespec character.
Loop End
5259
LD A,B 78
Load Register A with Register B, the number of characters copied into the CLP name buffer.
525A
LD (5AC0H),A 32 C0 5A
Store the CLP name length (Register A) at 5AC0H, where 52A5H and the yank scan at 5450H read it back.
525D
POP HL E1
Restore Register Pair HL to the command-line pointer and fall through to the option scan at 525EH.
525EH - Command-Line Option and Inline-Patch Scan
Reached when the command line carried no separate /FIX filespec. This scans past blanks, requires an opening parenthesis, and either parses the REMOVE and OPTION parameters with @PARAM or copies an inline patch body typed in parentheses into the command buffer at 5F00H.
525E
LD A,(HL) 7E
Load Register A with the next command-line character at (HL).
525F
CP 0DH FE 0D
Compare Register A against 0DH (carriage return). If it equals, the Z FLAG is set, marking the end of the command line.
5261
If the Z FLAG is set (end of line with no options), jump to 52A5H to open and read the /FIX patch file.
5263
INC HL 23
Advance Register Pair HL past the character just tested.
5264
CP 20H FE 20
Compare Register A against 20H (space). If it equals, the Z FLAG is set.
5266
If the Z FLAG is set (a blank), LOOP BACK to 525EH to skip it.
5268
CP 28H FE 28
Compare Register A against 28H (ASCII (). If it equals, the Z FLAG is set, marking the start of the parenthesised list.
526A
If the NO Z FLAG is set (no opening parenthesis where one is required), JUMP to 586CH, which loads a comma and reports "Patch input format error".
526D
LD DE,5AC9H 11 C9 5A
Point Register Pair DE at the @PARAM keyword table at 5AC9H (the REMOVE and OPTION keywords with their result cells).
5270
PUSH HL E5
Save Register Pair HL (the position of the opening parenthesis) before @PARAM.
5271
DEC HL 2B
Back up Register Pair HL by one so it addresses the opening parenthesis, the delimiter @PARAM scans from.
5272
GOSUB to the resident @PARAM routine to parse (REMOVE=..,OPTION=..) at (HL), storing each value into the result cell named by the table at (DE=5AC9H); the Z FLAG is returned when every keyword was recognised.
5275
LD A,(5AEEH) 3A EE 5A
Load Register A with the OPTION result cell at 5AEEH filled by @PARAM.
5278
LD (57D5H),A 32 D5 57
Store the OPTION value (Register A) into the self-modifying operand at 57D5H, the on/off flag tested at 57D4H before each data statement.
527B
LD A,(5AECH) 3A EC 5A
Load Register A with the REMOVE result cell at 5AECH filled by @PARAM.
527E
LD (57DBH),A 32 DB 57
Store the REMOVE value (Register A) into the self-modifying operand at 57DBH, the reverse/remove flag tested at 57DAH.
5281
POP HL E1
Restore Register Pair HL to the character after the parenthesised text.
5282
If @PARAM returned the Z FLAG (the parentheses held only REMOVE/OPTION keywords), jump to 52A5H to open the /FIX file.
Inline Patch Capture
@PARAM returned the NZ FLAG, so the parenthesised text is an inline patch body rather than an option list. The following loop copies it into the command buffer at 5F00H, turning each colon into a carriage return so several statements can share one line.
5284
LD BC,5F00H 01 00 5F
Point Register Pair BC at 5F00H, the destination command buffer.
5287
LD A,(HL) 7E
Load Register A with the next inline character at (HL).
5288
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, end of command line).
528A
If the Z FLAG is set (end of line), JUMP to 529CH to terminate the buffer.
528D
CP 29H FE 29
Compare Register A against 29H (ASCII ), the closing parenthesis).
528F
If the Z FLAG is set (closing parenthesis), jump to 529CH to terminate the buffer.
5291
INC HL 23
Advance Register Pair HL past the character just tested.
5292
CP 3AH FE 3A
Compare Register A against 3AH (ASCII :, the statement separator).
5294
If the NZ FLAG is set (not a colon), skip the substitution at 5298H and store the character as-is.
5296
LD A,0DH 3E 0D
Load Register A with 0DH so a colon is stored as a carriage return, ending one statement and starting the next.
5298
LD (BC),A 02
Store the character (Register A) into the command buffer at (BC).
5299
INC BC 03
Advance Register Pair BC to the next command-buffer position.
529A
LOOP BACK to 5287H to copy the next inline character.
529C
LD A,0DH 3E 0D
Load Register A with 0DH to terminate the final statement with a carriage return.
529E
LD (BC),A 02
Store the carriage return (Register A) at the current buffer position (BC).
529F
INC BC 03
Advance Register Pair BC past the carriage return.
52A0
LD A,03H 3E 03
Load Register A with 03H, the end-of-buffer marker the dispatcher tests for.
52A2
LD (BC),A 02
Store the 03H terminator (Register A) at the end of the command buffer (BC).
52A3
Jump to the main command dispatch loop at 52FCH to execute the inline patch.
52A5H - Open the Patch File and Fill the Command Buffer
Opens the /FIX patch file and reads it a character at a time into the command buffer at 5F00H, stripping each byte to seven bits, honouring quotation marks, and turning colons outside quotes into carriage returns. Overflow past 7300H reports "Fix file too big - partition it".
52A5
LD A,(5AC0H) 3A C0 5A
Load Register A with the CLP name length stored at 5AC0H by 525AH.
52A8
OR A B7
Test Register A; the Z FLAG is set when the length is zero, meaning no patch filename was supplied.
52A9
If the Z FLAG is set (no patch name), JUMP to the error exit at 5880H, "PROGRAM file name required".
52AC
LD DE,5B10H 11 10 5B
Point Register Pair DE at the /FIX patch File Control Block at 5B10H.
52AF
LD HL,5C00H 21 00 5C
Point Register Pair HL at 5C00H, the 256-byte sector buffer for the patch file.
52B2
GOSUB to @OPEN to open the patch file described at 5B10H, using sector buffer 5C00H.
52B5
If @OPEN returned the NZ FLAG (the patch file could not be opened), JUMP to the shared error exit at 5867H.
52B8
LD HL,7300H 21 00 73
Point Register Pair HL at 7300H, one past the top of the command buffer.
52BB
DEC HL 2B
Back up Register Pair HL to 72FFH, the overflow limit tested each pass.
52BC
LD BC,5F00H 01 00 5F
Point Register Pair BC at 5F00H, the start of the command buffer being filled.
Loop Start
The following loop reads the /FIX file one character at a time and stores the translated text into the command buffer.
52BF
LD DE,5B10H 11 10 5B
Reload Register Pair DE with the patch File Control Block address 5B10H, the device @GET reads from, since @GET may alter DE.
52C2
GOSUB to the ROM @GET routine to fetch the next byte of the patch file (the File Control Block is at DE); Register A returns the byte and the Z FLAG shows a byte was available.
52C5
If @GET returned the NZ FLAG (no byte, end of file or error), jump to 52F4H to check for the normal end-of-file code.
52C7
AND 7FH E6 7F
Mask Register A to seven bits, discarding any high bit so text compares work regardless of the eighth bit.
52C9
If the result is zero (a null byte), jump to 52F9H to terminate the buffer.
52CB
LD E,A 5F
Save the character in Register E while the quote state is examined.
52CC
CP 22H FE 22
Compare Register A against 22H (ASCII ", a quotation mark).
52CE
If the NZ FLAG is set (not a quotation mark), skip the quote-toggle at 52D5H.
52D0
XOR 00H EE 00
Self-Modifying Code
Exclusive-OR Register A with the operand byte at 52D1H, then store it back at 52D2H, so each quotation mark toggles the quote-state flag held in that operand between 00H and 22H.
52D2
LD (52D1H),A 32 D1 52
Store the toggled quote state (Register A) into the operand cell 52D1H, the quote-state flag read at 52D5H.
52D5
LD A,(52D1H) 3A D1 52
Load Register A with the quote-state flag at 52D1H (00H outside quotes, non-zero inside).
52D8
OR A B7
Test Register A; the NZ FLAG is set when the reader is currently inside a quoted string.
52D9
LD A,E 7B
Restore the current character into Register A from Register E without disturbing the flags.
52DA
If the NZ FLAG is set (inside quotes), jump to 52E2H to store the character literally, leaving any colon untouched.
52DC
CP 3AH FE 3A
Compare Register A against 3AH (ASCII :).
52DE
If the NZ FLAG is set (not a colon), jump to 52E2H to store the character unchanged.
52E0
LD A,0DH 3E 0D
Load Register A with 0DH so a colon outside quotes becomes a carriage return separating two statements.
52E2
LD (BC),A 02
Store the translated character (Register A) into the command buffer at (BC).
52E3
SUB 0DH D6 0D
Subtract 0DH from Register A; the Z FLAG is set when the stored character was a carriage return.
52E5
If the NZ FLAG is set (not a carriage return), skip the quote-state reset at 52E7H.
52E7
LD (52D1H),A 32 D1 52
A carriage return ends a statement, so store the now-zero Register A into the quote-state flag at 52D1H to clear it.
52EA
INC BC 03
Advance Register Pair BC to the next command-buffer position.
52EB
PUSH HL E5
Save Register Pair HL (the 72FFH limit) before the overflow test corrupts it.
52EC
SBC HL,BC ED 42
Subtract the buffer pointer (BC) from the limit 72FFH (HL); the CARRY FLAG is set when BC has passed the limit.
52EE
POP HL E1
Restore Register Pair HL to the 72FFH limit.
52EF
If the CARRY FLAG is set (the buffer overflowed), JUMP to 587CH, "Fix file too big - partition it".
52F2
LOOP BACK to 52BFH to read the next patch-file character.
Loop End
52F4
CP 1CH FE 1C
Compare Register A against 1CH (error code 28, end of file). If it equals, the Z FLAG is set, marking the normal end of the patch file.
52F6
If the NZ FLAG is set (a real read error rather than end of file), JUMP to the shared error exit at 5867H.
52F9
LD A,03H 3E 03
Load Register A with 03H, the end-of-buffer marker.
52FB
LD (BC),A 02
Store the 03H terminator (Register A) at the end of the filled command buffer (BC) and fall through to the dispatch loop.
52FCH - Main Command Dispatch Loop
Walks the command buffer statement by statement. On the first pass it routes through 57A8H (which only sets flags and validates); once 57A2H has set the pass flag at 530BH non-zero, each statement is routed by its leading letter: the patch verbs D (direct disk modify), F (find/verify), L (library overlay) and X (memory-load patch), plus the internal handlers for the YANK, REMOVE and OPTION parameters (Y, R and O), with a leading period treated as a comment.
52FC
LD HL,5F00H 21 00 5F
Point Register Pair HL at 5F00H, the start of the translated command buffer.
52FF
PUSH HL E5
Save Register Pair HL (the current statement pointer) while the status line is displayed.
5300
LD HL,5944H 21 44 59
Point Register Pair HL at the "Reading input" status string at 5944H.
5303
GOSUB to @DSPLY to write the status string (Register Pair HL) on the status line; its leading and trailing control codes reposition the cursor so it overwrites in place.
5306
POP HL E1
Restore Register Pair HL to the current statement pointer.
5307
LD (5897H),HL 22 97 58
Save the current statement pointer (Register Pair HL) at 5897H so a sub-command can resume the scan after it returns.
530A
LD A,00H 3E 00
Self-Modifying Code
Load Register A with the pass-flag operand at 530BH; it is 00H on the first pass and is set non-zero by 57A2H for later passes.
530C
OR A B7
Test Register A; the Z FLAG is set on the first pass (operand still 00H).
530D
LD A,(HL) 7E
Load Register A with the first character of the current statement at (HL) without disturbing the flags set by 530CH.
530E
If the Z FLAG is set (first pass), JUMP to the first-pass dispatcher at 57A8H, which validates each statement and sets the option and remove flags before any file is written.
5311
LD A,(HL) 7E
Load Register A again with the leading character of the statement (second pass).
5312
CP 03H FE 03
Compare Register A against 03H (the end-of-buffer marker). If it equals, the Z FLAG is set.
5314
If the Z FLAG is set (all statements processed), jump to 5375H to close the file and report success.
5316
CP 2EH FE 2E
Compare Register A against 2EH (ASCII ., a comment line).
5318
If the Z FLAG is set (comment), JUMP to 538CH to skip the rest of the line.
531B
RES 5,A CB AF
Reset bit 5 of Register A, folding a lower-case command letter to upper case so either case is accepted.
531D
CP 46H FE 46
Compare Register A against 46H (ASCII F). A standalone find line is verified inside the D handler, so a leading F is skipped here.
531F
If the Z FLAG is set (a leading F), JUMP to 538CH to skip the line.
5322
CP 44H FE 44
Compare Register A against 44H (ASCII D, the data-patch command).
5324
If the Z FLAG is set, JUMP to the D sub-command at 539DH.
5327
CP 59H FE 59
Compare Register A against 59H (ASCII Y).
5329
If the Z FLAG is set, JUMP to the Y sub-command at 5411H, which drives the yank (patch removal) search.
532C
CP 4CH FE 4C
Compare Register A against 4CH (ASCII L, the library-overlay command).
532E
If the Z FLAG is set, JUMP to the L sub-command at 54D3H.
5331
CP 52H FE 52
Compare Register A against 52H (ASCII R, the reverse/remove command).
5333
If the Z FLAG is set, JUMP to the R sub-command at 5409H.
5336
CP 4FH FE 4F
Compare Register A against 4FH (ASCII O, the option command).
5338
If the Z FLAG is set, JUMP to the O sub-command at 54A4H.
533B
CP 58H FE 58
Compare Register A against 58H (ASCII X, the memory-load-location patch command that installs an X'nnnn'= patch).
533D
If the NZ FLAG is set (the leading letter was none of the recognised commands), JUMP to 588DH, "Patch input format error".
5340
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H to install the X-verb memory-load patch.
5343
LD BC,0000H 01 00 00
Load Register Pair BC with 0, the record number to position to.
5346
GOSUB to 585DH to position the object file (@POSN) to record 0.
5349
GOSUB to 5526H to read the next load-module record header of the object file, returning its type in Register A.
534C
PUSH AF F5
Save Register A (the record type) and the flags on the stack across the status display.
534D
PUSH HL E5
Save Register Pair HL (statement pointer) across the status display.
534E
PUSH DE D5
Save Register Pair DE (object File Control Block) across the status display.
534F
LD HL,5969H 21 69 59
Point Register Pair HL at the "Installing patch" status string at 5969H.
5352
GOSUB to @DSPLY to show the "Installing patch" status (Register Pair HL).
5355
POP DE D1
Restore Register Pair DE to the object File Control Block.
5356
POP HL E1
Restore Register Pair HL to the statement pointer.
5357
POP AF F1
Restore Register A to the record type read at 5349H.
5358
CP 02H FE 02
Compare the record type (Register A) against 02H (the transfer-address record that ends a load module).
535A
If the NZ FLAG is set (not the expected transfer record), JUMP to 5878H, "Load file format error".
535D
LD A,01H 3E 01
Load Register A with 1 to set the update flag in the object File Control Block.
535F
LD (5AF9H),A 32 F9 5A
Store 1 (Register A) into the File Control Block flag byte at 5AF9H, marking the buffered record as modified so @BKSP rewrites it.
5362
GOSUB to @BKSP to back the object file up one record so the assembled X-verb load module is appended just before the file's transfer record.
5365
If @BKSP returned the NZ FLAG (an error), JUMP to the shared error exit at 5867H.
5368
XOR A AF
Set Register A to 0 and clear the flags.
5369
LD (5AF9H),A 32 F9 5A
Clear the File Control Block flag byte at 5AF9H now that the record has been repositioned.
536C
GOSUB to 555BH to assemble the X-verb memory-load patch (a named type-07 record plus its X'nnnn' entries) into the work image and append it to the file.
536F
LD A,(HL) 7E
Load Register A with the character the statement scan stopped on (at HL).
5370
CP 03H FE 03
Compare Register A against 03H (the end-of-buffer marker expected after the X-verb patch has been assembled).
5372
If the NZ FLAG is set (unexpected trailing text), JUMP to 588DH, "Patch input format error", then fall through to the success path at 5375H.
5375H - Completion and Exit
Closes the object file, displays the closing message and returns to DOS. The closing message pointer at 5384H is normally "Patch(s) successfully installed" but is changed to "Patch successfully yanked" by the yank path.
5375
LD A,0DH 3E 0D
Load Register A with 0DH (carriage return) to move the cursor to a fresh line before the closing message.
5377
GOSUB to the ROM @DSP routine to display the carriage return in Register A.
537A
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H.
537D
GOSUB to @CLOSE to close the object file, flushing any updated record and finalising the directory entry.
5380
If @CLOSE returned the NZ FLAG (an error), JUMP to the shared error exit at 5867H.
5383
LD HL,5A52H 21 52 5A
Self-Modifying Code
Point Register Pair HL at the closing message via the operand at 5384H, which is 5A52H ("Patch(s) successfully installed") unless 5493H overwrote it with 5AA6H ("Patch successfully yanked").
5386
GOSUB to @LOGOT to display the carriage-return-terminated closing message (Register Pair HL) on the video screen.
5389
JUMP to the resident @EXIT vector to return control to DOS Ready.
538CH - Skip to End of Command Line
Advances the statement pointer past a comment or otherwise skipped line, then re-enters the dispatch loop. The quote-state flag is cleared first so a colon in the skipped text cannot leave the reader stuck inside quotes.
538C
XOR A AF
Set Register A to 0 and clear the flags.
538D
LD (52D1H),A 32 D1 52
Clear the quote-state flag at 52D1H so the skipped line leaves the reader outside quotes.
Loop Start
Advance to the carriage return or end-of-buffer marker that ends the current line.
5390
LD A,(HL) 7E
Load Register A with the next character at (HL).
5391
INC HL 23
Advance Register Pair HL past that character.
5392
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
5394
If the Z FLAG is set (end of buffer), jump to 539AH to re-enter the dispatch loop.
5396
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, end of this statement).
5398
If the NZ FLAG is set (not yet the end of the line), LOOP BACK to 5390H.
Loop End
539A
JUMP back into the dispatch loop at 52FFH to process the next statement.
539DH - D Sub-Command - Apply a Data Patch
Handles a D statement: it parses the record number and byte offset, then parses and applies the replacement data, verifying the original bytes through the F clause when one is present.
539D
GOSUB to 53A6H to parse the record number and byte offset and read that record of the object file.
53A0
GOSUB to 53D0H to parse the replacement bytes after the equals sign and write them into the record.
53A3
JUMP back to the dispatch loop at 52FFH for the next statement.
53A6H - Parse the Record Number and Byte Offset
Reads the hexadecimal record number and the comma-separated byte offset that address a byte inside the load module, positions the object file to that record, reads it, and stores the offset.
53A6
INC HL 23
Advance Register Pair HL past the D command letter.
53A7
GOSUB to the token/hex scanner at 5668H to read the record number into Register A.
53AA
LD B,00H 06 00
Load Register B with 0 to form the high byte of the record number in Register Pair BC.
53AC
LD C,A 4F
Load Register C with the record number (Register A) so Register Pair BC holds it for @POSN.
53AD
LD A,(HL) 7E
Load Register A with the next statement character at (HL).
53AE
CP 2CH FE 2C
Compare Register A against 2CH (ASCII ,).
53B0
If the Z FLAG is set (a comma follows, so the byte offset comes next), jump to 53B6H.
53B2
Otherwise GOSUB to the scanner at 5668H to read a second hexadecimal value into Register A.
53B5
LD C,A 4F
Load Register C with that value, replacing the record number in Register Pair BC.
53B6
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H.
53B9
GOSUB to 585DH to position the object file (@POSN) to the record number in Register Pair BC.
53BC
LD A,(HL) 7E
Load Register A with the current statement character at (HL).
53BD
CP 2CH FE 2C
Compare Register A against 2CH (ASCII ,) which must separate the record number from the byte offset.
53BF
If the NZ FLAG is set (no comma), JUMP to 588DH, "Patch input format error".
53C2
INC HL 23
Advance Register Pair HL past the comma.
53C3
GOSUB to @READ to read the positioned record of the object file into its sector buffer at 5E00H.
53C6
If @READ returned the NZ FLAG (a read error), JUMP to the shared error exit at 5867H.
53C9
GOSUB to the scanner at 5668H to read the byte offset within the record into Register A.
53CC
LD (5AF5H),A 32 F5 5A
Store the byte offset (Register A) at 5AF5H, where the apply routine at 5849H reads it.
53CF
RET C9
Return to the D sub-command at 53A0H.
53D0H - Parse and Apply the Replacement Data
Parses the bytes after the equals sign and hands each to 5849H, which on the second pass writes it into the record buffer and on the first pass verifies the original byte. When the statement ends, and only on the second pass, the modified record is written back with @RWRIT.
53D0
LD A,(HL) 7E
Load Register A with the current statement character at (HL).
53D1
CP 3DH FE 3D
Compare Register A against 3DH (ASCII =) which must introduce the replacement data.
53D3
If the NZ FLAG is set (no equals sign), JUMP to 588DH, "Patch input format error".
Loop Start
Scan and apply each replacement byte until the statement ends.
53D6
INC HL 23
Advance Register Pair HL past the equals sign or the previous data byte.
53D7
GOSUB to the scanner entry at 566CH to read the next data byte into Register A, tracking quotation marks but not resetting the quote flag.
53DA
GOSUB to 5849H, which on the second pass writes Register A into the record buffer at the stored offset, and on the first pass compares it against the byte already there.
53DD
LD A,(HL) 7E
Load Register A with the character the scanner stopped on (at HL).
53DE
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, end of statement).
53E0
If the Z FLAG is set (end of statement), jump to 53F9H to write the record back.
53E2
CP 22H FE 22
Compare Register A against 22H (ASCII ", a quotation mark).
53E4
If the Z FLAG is set (a quotation mark, which the scanner already consumed), jump to 53F8H.
53E6
SUB 3BH D6 3B
Subtract 3BH (ASCII ;) from Register A; the result is zero when the character was a semicolon separating data groups.
53E8
LD C,A 4F
Save the difference in Register C for the test below.
53E9
LD A,(5681H) 3A 81 56
Load Register A with the scanner quote flag at 5681H (non-zero while a quoted string is being read).
53EC
OR A B7
Test Register A; the NZ FLAG is set when the scanner is inside quotes.
53ED
If the NZ FLAG is set (inside quotes), jump to 53F3H, where the following continuation is taken unconditionally.
53EF
INC C 0C
Increment Register C, then decrement it, purely to set the Z FLAG from the semicolon test held in Register C.
53F0
DEC C 0D
Decrement Register C so the Z FLAG reflects whether the character was a semicolon.
53F1
If the Z FLAG is set (a semicolon outside quotes), jump to 53F8H to advance to the next data group.
53F3
OR A B7
Clear the CARRY FLAG (Register A already holds the quote flag) so the following relative jump is taken.
53F4
If the Z FLAG is set (outside quotes, ordinary data continues), LOOP BACK to 53D6H for the next byte.
53F6
Inside quotes, LOOP BACK to 53D7H to read the next quoted byte without advancing past a delimiter.
53F8
LD A,(HL) 7E
Load Register A with the current character at (HL) before scanning to the end of the statement.
Loop Start
Advance to the carriage return that ends the statement.
53F9
INC HL 23
Advance Register Pair HL past the current character.
53FA
CP 0DH FE 0D
Compare Register A against 0DH (carriage return).
53FC
If the NZ FLAG is set (not yet the end), LOOP BACK to 53F8H.
Loop End
53FE
LD A,(530BH) 3A 0B 53
Load Register A with the pass flag at 530BH (zero on the first pass, non-zero on the second).
5401
OR A B7
Test Register A; the NZ FLAG is set on the second pass, when the record is actually written.
5402
If the NZ FLAG is set (second pass), GOSUB to @RWRIT to write the modified record back to the object file; on the first pass the write is skipped so only verification occurs.
5405
RET Z C8
Return to the D sub-command if the Z FLAG is set (first pass, nothing written), or if @RWRIT reported success.
5406
Otherwise JUMP to the shared error exit at 5867H because @RWRIT failed.
5409H - R Sub-Command - Reverse the Patch Sense
A R statement forces the reverse/remove flag on so the following statements remove rather than install a patch, then skips the rest of the line.
5409
LD A,0FFH 3E FF
Load Register A with 0FFH, the value that marks reverse/remove mode.
540B
LD (57DBH),A 32 DB 57
Store 0FFH (Register A) into the self-modifying reverse/remove flag operand at 57DBH, tested at 57DAH.
540E
JUMP to 538CH to skip the remainder of the R line and continue with the next statement.
5411H - Y Sub-Command - Yank (Remove) a Patch
Displays "Yanking patch from file", then reads the object file's load records looking for the type-07 patch record whose stored name matches the CLP name. When found, the patch is unlinked and the record removed; when the file ends without a match, "Can't yank, patch not in load file" is shown.
Loop Start
Skip the rest of the Y keyword line up to its carriage return.
5411
LD A,(HL) 7E
Load Register A with the next character of the Y line at (HL).
5412
INC HL 23
Advance Register Pair HL past that character.
5413
CP 0DH FE 0D
Compare Register A against 0DH (carriage return).
5415
If the NZ FLAG is set (not yet the end of the line), LOOP BACK to 5411H.
Loop End
5417
PUSH HL E5
Save Register Pair HL (the position after the Y line) while the file is scanned.
5418
LD HL,5998H 21 98 59
Point Register Pair HL at the "Yanking patch from file" status string at 5998H.
541B
GOSUB to @DSPLY to show the yank status (Register Pair HL).
541E
LD BC,0000H 01 00 00
Load Register Pair BC with 0, the record number to position to.
5421
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H.
5424
GOSUB to 585DH to position the object file (@POSN) to record 0.
Loop Start
Read successive load records, skipping over each until a type-07 patch record whose name matches the CLP name is found.
5427
GOSUB to ROM @GET to read the next load-record type byte of the object file into Register A.
542A
If @GET returned the NZ FLAG (end of file or error), JUMP to 5499H to check for the normal end of file.
542D
CP 07H FE 07
Compare Register A against 07H, the load-record type PATCH uses to record an installed patch.
542F
If the Z FLAG is set (a patch record), jump to 544CH to compare its stored name against the CLP name.
5431
LD (5439H),A 32 39 54
Self-Modifying Code
Store the record type (Register A) into the operand at 5439H so the counter test at 5438H starts from that value while the record is skipped.
5434
GOSUB to the object-file byte reader at 56F7H to read the record's length byte into Register A.
5437
LD B,A 47
Load Register B with the record length (Register A) to count the bytes to skip.
5438
LD A,00H 3E 00
Self-Modifying Code
Load Register A with the operand at 5439H set by 5431H (the record type just read).
543A
DEC A 3D
Decrement Register A to distinguish a type-01 load record (whose address occupies two extra bytes) from other types.
543B
If the NZ FLAG is set (not a type-01 record), jump to 5445H to skip the plain data.
543D
GOSUB to 56F7H to read the record's load-address low byte (skipped).
5440
DEC B 05
Decrement Register B for the address low byte just consumed.
5441
GOSUB to 56F7H to read the load-address high byte (skipped).
5444
DEC B 05
Decrement Register B for the address high byte just consumed.
5445
GOSUB to 56F7H to read one data byte of the record (skipped).
5448
DECrement Register B and LOOP BACK to 5445H until the whole record has been skipped.
544A
LOOP BACK to 5427H to read the next record type.
Patch Record Found
Register A held a type-07 record; compare its stored name length and characters against the CLP name.
544C
GOSUB to 56F7H to read the patch record's name-length byte into Register A.
544F
LD B,A 47
Load Register B with the stored name length (Register A).
5450
LD A,(5AC0H) 3A C0 5A
Load Register A with the CLP name length at 5AC0H (the length of the patch being yanked).
5453
CP B B8
Compare the CLP name length (Register A) against the stored length (Register B).
5454
If the NZ FLAG is set (lengths differ, not this patch), jump to 5445H to skip the rest of the record.
5456
LD HL,5AC1H 21 C1 5A
Point Register Pair HL at the CLP name buffer at 5AC1H to compare it character by character.
Loop Start
Compare each stored name character against the CLP name.
5459
GOSUB to 56F7H to read the next stored name character of the record into Register A.
545C
CP (HL) BE
Compare the stored character (Register A) against the CLP name character at (HL).
545D
INC HL 23
Advance Register Pair HL to the next CLP name character.
545E
If the NZ FLAG is set (a character differs), jump to 5448H to skip the remaining record bytes and resume the record scan.
5460
DECrement Register B and LOOP BACK to 5459H until every name character has matched.
Matching Patch Located
The record's stored name matches the CLP name; remove the patch record and rewrite the load file.
5462
GOSUB to 56F7H to read the next byte after the matched name into Register A.
5465
CP 01H FE 01
Compare Register A against 01H, the sub-record marker within the patch record.
5467
If the NZ FLAG is set (no more sub-records), JUMP to 548FH to finish the yank.
546A
LD A,01H 3E 01
Load Register A with 1 to set the update flag in the File Control Block.
546C
LD (5AF9H),A 32 F9 5A
Store 1 (Register A) into the File Control Block flag byte at 5AF9H so @BKSP rewrites the buffered record.
546F
GOSUB to @BKSP to back the object file up one record so the record can be rewritten with the patch removed.
5472
If @BKSP returned the NZ FLAG (an error), JUMP to the shared error exit at 5867H.
5475
XOR A AF
Set Register A to 0 and clear the flags.
5476
LD (5AF9H),A 32 F9 5A
Clear the File Control Block flag byte at 5AF9H after the reposition.
5479
LD A,10H 3E 10
Load Register A with 10H, the replacement record type written to neutralise the removed patch sub-record.
547B
GOSUB to the @PUT wrapper at 5863H to write the 10H byte (Register A) back to the object file.
547E
GOSUB to @RWRIT to write the modified record back to the object file.
5481
If @RWRIT returned the NZ FLAG (a write error), JUMP to the shared error exit at 5867H.
5484
GOSUB to 56F7H to read this sub-record's length byte into Register A.
5487
LD B,A 47
Load Register B with the sub-record length (Register A).
Loop Start
Skip the sub-record's data bytes.
5488
GOSUB to 56F7H to read and discard one sub-record data byte.
548B
DECrement Register B and LOOP BACK to 5488H until the sub-record is consumed.
548D
LOOP BACK to 5462H to handle the next sub-record of the patch.
548F
POP HL E1
Restore Register Pair HL (the position after the Y line) saved at 5417H.
5490
LD HL,5AA6H 21 A6 5A
Point Register Pair HL at the "Patch successfully yanked" message at 5AA6H.
5493
LD (5384H),HL 22 84 53
Self-Modifying Code
Store 5AA6H (Register Pair HL) into the closing-message operand at 5384H so the completion path reports the yank instead of an install.
5496
JUMP to the completion path at 5375H to close the file and report success.
5499
CP 1CH FE 1C
Compare Register A against 1CH (error code 28, end of file). If it equals, the Z FLAG is set.
549B
If the NZ FLAG is set (a real error rather than end of file), JUMP to the shared error exit at 5867H.
549E
LD HL,59B3H 21 B3 59
Point Register Pair HL at the "Can't yank, patch not in load file" message at 59B3H.
54A1
JUMP to the message-and-abort path at 5883H to display the message (Register Pair HL) and return to DOS.
54A4H - O Sub-Command - Set the On/Off Option
An O=Y, O=N or O=OFF statement sets the on/off option flag that gates whether the following data statements are applied, then skips the rest of the line.
54A4
INC HL 23
Advance Register Pair HL past the O command letter.
54A5
LD A,(HL) 7E
Load Register A with the next character at (HL).
54A6
CP 3DH FE 3D
Compare Register A against 3DH (ASCII =).
54A8
If the NZ FLAG is set (no equals sign), jump to 54C7H, which raises "Patch input format error".
54AA
INC HL 23
Advance Register Pair HL past the equals sign.
54AB
LD A,(HL) 7E
Load Register A with the option value character at (HL).
54AC
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, an empty value).
54AE
If the Z FLAG is set (no value given), jump to 54CBH to turn the option on.
54B0
RES 5,A CB AF
Reset bit 5 of Register A to fold the value letter to upper case.
54B2
CP 4EH FE 4E
Compare Register A against 4EH (ASCII N, for No/off).
54B4
If the Z FLAG is set (N), jump to 54CBH.
54B6
CP 59H FE 59
Compare Register A against 59H (ASCII Y, for Yes/on).
54B8
If the Z FLAG is set (Y), jump to 54CAH to turn the option on.
54BA
CP 4FH FE 4F
Compare Register A against 4FH (ASCII O, the first letter of OFF).
54BC
If the NZ FLAG is set (not the start of OFF), jump to 54C7H to raise the format error.
54BE
GOSUB to 5844H to read the next character (upper-cased) into Register A, expecting the second letter of OFF.
54C1
CP 46H FE 46
Compare Register A against 46H (ASCII F).
54C3
If the Z FLAG is set (OFF), jump to 54CBH to leave the option off.
54C5
CP 4EH FE 4E
Compare Register A against 4EH (ASCII N) as an alternate spelling.
54C7
If the NZ FLAG is set (an unrecognised option value), JUMP to 588DH, "Patch input format error".
Overlapping On/Off Entry
Entered at 54CAH the two bytes 3E AFH form LD A,0AFH, loading the non-zero value that turns the option on. The off cases jump one byte in, to 54CBH, where the AFH byte alone executes as XOR A, clearing Register A to turn the option off. Both paths then store Register A at 54CCH.
54CA
DEFB 3EH 3E
Opcode byte of LD A,0AFH; the value character Y enters here so Register A is loaded with the non-zero 0AFH held in the operand byte at 54CBH, marking the option on.
54CB
XOR A AF
This byte is both the operand of the 54CAH instruction and an entry point: the off cases at 54AEH, 54B4H and 54C3H jump here, where the AFH byte alone is XOR A, setting Register A to 0 to mark the option off.
54CC
LD (57D5H),A 32 D5 57
Store 0AFH (Register A) into the self-modifying option-flag operand at 57D5H, tested at 57D4H.
54CF
DEC HL 2B
Back up Register Pair HL by one so the line-skip below sees the value character.
54D0
JUMP to 538CH to skip the remainder of the O line.
54D3H - L Sub-Command - Select a Library Overlay
An L statement names a library-overlay number. PATCH locates that overlay inside the load file, reads its record, regenerates the library map and rebuilds the load image so that subsequent D statements address bytes within the chosen overlay.
54D3
INC HL 23
Advance Register Pair HL past the L command letter.
54D4
GOSUB to the scanner at 5668H to read the library-overlay number into Register A.
54D7
LD C,A 4F
Load Register C with the overlay number (Register A) for the search routine.
54D8
LD (5741H),A 32 41 57
Store the overlay number (Register A) at 5741H, where the search routine at 56BFH reads it.
54DB
LD A,(HL) 7E
Load Register A with the character following the number at (HL).
54DC
INC HL 23
Advance Register Pair HL past that character.
54DD
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, which must end the L statement).
54DF
If the NZ FLAG is set (trailing text), JUMP to 588DH, "Patch input format error".
54E2
GOSUB to 56BFH to scan the object file for the named library overlay, returning its position; Register A returns the record offset.
54E5
PUSH AF F5
Save Register A (the record offset) and the flags while the File Control Block flag is adjusted.
54E6
LD A,(5AF1H) 3A F1 5A
Load Register A with the File Control Block flag byte at 5AF1H.
54E9
RES 7,A CB BF
Reset bit 7 of Register A, clearing the end-of-file condition in the File Control Block so the overlay record can be re-read.
54EB
LD (5AF1H),A 32 F1 5A
Store the adjusted flag byte (Register A) back at 5AF1H.
54EE
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H.
54F1
GOSUB to 585DH to position the object file (@POSN) to the located overlay record.
54F4
GOSUB to @READ to read the overlay record into the sector buffer.
54F7
If @READ returned the NZ FLAG (a read error), JUMP to the shared error exit at 5867H.
54FA
POP AF F1
Restore Register A to the record offset saved at 54E5H.
54FB
LD (5AF5H),A 32 F5 5A
Store the record offset (Register A) at 5AF5H for the apply routine.
54FE
GOSUB to 5526H to read the overlay's load record, returning its type in Register A.
5501
CP 04H FE 04
Compare the record type (Register A) against 04H, the expected library-overlay marker.
5503
If the NZ FLAG is set (unexpected record type), JUMP to 5878H, "Load file format error".
5506
LD A,01H 3E 01
Load Register A with 1 to set the File Control Block update flag.
5508
LD (5AF9H),A 32 F9 5A
Store 1 (Register A) into the File Control Block flag byte at 5AF9H so @BKSP rewrites the buffered record.
550B
GOSUB to @BKSP to back the object file up one record.
550E
If @BKSP returned the NZ FLAG (an error), JUMP to the shared error exit at 5867H.
5511
XOR A AF
Set Register A to 0 and clear the flags.
5512
LD (5AF9H),A 32 F9 5A
Clear the File Control Block flag byte at 5AF9H after the reposition.
5515
GOSUB to 555BH to regenerate the library map from the overlay's records.
5518
PUSH HL E5
Save Register Pair HL (statement pointer) while the status line is shown.
5519
LD HL,597DH 21 7D 59
Point Register Pair HL at the "Re-building library map" status string at 597DH.
551C
GOSUB to @DSPLY to show the library-map status (Register Pair HL).
551F
GOSUB to 56FEH to rebuild the load-module image in the 7300H work area from the overlay's records.
5522
POP HL E1
Restore Register Pair HL to the statement pointer.
5523
JUMP back to the dispatch loop at 52FFH for the next statement.
5526H - Read the Next Load-Module Record
Displays "Positioning load file", then reads load-record type bytes from the object file, skipping over each record's data, and returns when it reaches a record whose type is 02H, 03H, 04H or 0AH - the record types the callers act on.
5526
PUSH HL E5
Save Register Pair HL (statement pointer) across the status display.
5527
PUSH DE D5
Save Register Pair DE (object File Control Block) across the status display.
5528
LD HL,592BH 21 2B 59
Point Register Pair HL at the "Positioning load file" status string at 592BH.
552B
GOSUB to @DSPLY to show the positioning status (Register Pair HL).
552E
POP DE D1
Restore Register Pair DE to the object File Control Block.
552F
POP HL E1
Restore Register Pair HL to the statement pointer.
Loop Start
Read record type bytes, returning on a record the caller handles and skipping the data of any other.
5530
GOSUB to the object-file byte reader at 56F7H to read the next load-record type byte into Register A.
5533
CP 20H FE 20
Compare Register A against 20H; a valid load-record type is below 20H.
5535
If the NO CARRY FLAG is set (the byte is 20H or above and cannot be a record type), JUMP to 5878H, "Load file format error".
5538
CP 02H FE 02
Compare Register A against 02H (transfer-address record).
553A
RET Z C8
Return to the caller with Register A = 02H if this is a transfer record.
553B
CP 03H FE 03
Compare Register A against 03H.
553D
RET Z C8
Return with Register A = 03H if this record type is 03H.
553E
CP 04H FE 04
Compare Register A against 04H (library-overlay marker).
5540
RET Z C8
Return with Register A = 04H if this is the library-overlay record.
5541
CP 0AH FE 0A
Compare Register A against 0AH.
5543
RET Z C8
Return with Register A = 0AH if this record type is 0AH.
5544
LD C,A 4F
Load Register C with the record type (Register A) to note whether it needs an address skip.
5545
GOSUB to 56F7H to read the record's length byte into Register A.
5548
LD B,A 47
Load Register B with the record length (Register A) to count the bytes to skip.
5549
DEC C 0D
Decrement Register C to test whether the type was 01H (a data-with-address record).
554A
If the NZ FLAG is set (not a type-01 record), jump to 5554H to skip only the data.
554C
GOSUB to 56F7H to read the load-address low byte (skipped).
554F
DEC B 05
Decrement Register B for the address low byte consumed.
5550
GOSUB to 56F7H to read the load-address high byte (skipped).
5553
DEC B 05
Decrement Register B for the address high byte consumed.
5554
GOSUB to 56F7H to read one data byte of the record (skipped).
5557
DECrement Register B and LOOP BACK to 5554H until the record's data is consumed.
5559
LOOP BACK to 5530H to read the next record type.
555BH - Assemble the X-Verb Memory-Load Patch Module
Displays "Generating patch", writes a type-07 patch record carrying the CLP name (the identification that later lets YANK find and remove this patch) into the work image at 7300H, then walks the remaining statements assembling each X'nnnn' memory-load entry into the image before the module is appended to the file.
555B
PUSH HL E5
Save Register Pair HL (statement pointer) across the status display.
555C
LD HL,5955H 21 55 59
Point Register Pair HL at the "Generating patch" status string at 5955H.
555F
GOSUB to @DSPLY to show the generate status (Register Pair HL).
5562
LD DE,7300H 11 00 73
Point Register Pair DE at 7300H, the work image where the new library map is assembled.
5565
LD HL,5AC0H 21 C0 5A
Point Register Pair HL at the CLP name length cell at 5AC0H, followed by the CLP name.
5568
LD A,(HL) 7E
Load Register A with the CLP name length at (HL).
5569
OR A B7
Test Register A; the Z FLAG is set when there is no CLP name.
556A
If the Z FLAG is set (no name), jump to 5578H, omitting the name header.
556C
LD A,07H 3E 07
Load Register A with 07H, the patch-record type byte.
556E
LD (DE),A 12
Store the 07H type byte (Register A) at the start of the work image at (DE).
556F
INC DE 13
Advance Register Pair DE past the type byte.
5570
LD B,(HL) 46
Load Register B with the CLP name length at (HL).
5571
INC B 04
Increment Register B so the loop copies the length byte plus the name characters.
Loop Start
Copy the CLP name length and characters into the patch record header.
5572
LD A,(HL) 7E
Load Register A with the next CLP byte at (HL) (the length, then each name character).
5573
INC HL 23
Advance Register Pair HL to the next CLP byte.
5574
LD (DE),A 12
Store the byte (Register A) into the work image at (DE).
5575
INC DE 13
Advance Register Pair DE to the next image position.
5576
DECrement Register B and LOOP BACK to 5572H until the length and name are copied.
5578
POP HL E1
Restore Register Pair HL to the statement pointer.
Loop Start
Scan the remaining statements, assembling each X'nnnn' memory-load patch entry into the work image.
5579
LD (5897H),HL 22 97 58
Save the current statement pointer (Register Pair HL) at 5897H.
557C
LD A,(HL) 7E
Load Register A with the leading character of the statement at (HL).
557D
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
557F
If the Z FLAG is set (all statements scanned), JUMP to 5605H to install the assembled patch.
5582
INC HL 23
Advance Register Pair HL past the leading character.
5583
CP 2EH FE 2E
Compare Register A against 2EH (ASCII ., a comment).
5585
If the Z FLAG is set (a comment), jump to 5590H to skip the line.
5587
RES 5,A CB AF
Reset bit 5 of Register A to fold the letter to upper case.
5589
CP 58H FE 58
Compare Register A against 58H (ASCII X, an X'nnnn' memory-load patch line).
558B
If the Z FLAG is set (an X entry), jump to 559DH to build it into the image.
558D
Otherwise JUMP to 588DH, "Patch input format error".
Loop Start
Skip a comment line to its carriage return.
5590
LD A,(HL) 7E
Load Register A with the next comment character at (HL).
5591
INC HL 23
Advance Register Pair HL past that character.
5592
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
5594
If the Z FLAG is set (a comment ran into the buffer end), JUMP to 588DH, "Patch input format error".
5597
CP 0DH FE 0D
Compare Register A against 0DH (carriage return).
5599
If the NZ FLAG is set (not the end of the comment line), LOOP BACK to 5590H.
559B
LOOP BACK to 5579H to examine the next statement.
X Memory-Load Patch Entry
Build an X'nnnn' entry - a sub-record type, a byte-count slot, the two-byte memory load address, and the patch data bytes - into the work image.
559D
LD A,01H 3E 01
Load Register A with 01H, the sub-record type for an X'nnnn' memory-load patch entry.
559F
LD (DE),A 12
Store the 01H sub-record type (Register A) into the work image at (DE).
55A0
INC DE 13
Advance Register Pair DE past the type byte.
55A1
PUSH DE D5
Save the image position (Register Pair DE) where the byte count will be filled in.
55A2
INC DE 13
Advance Register Pair DE past the byte-count slot to be back-filled at 5600H.
55A3
LD A,(HL) 7E
Load Register A with the next statement character at (HL).
55A4
INC HL 23
Advance Register Pair HL past that character.
55A5
CP 27H FE 27
Compare Register A against 27H (ASCII '), which must open the load-address value.
55A7
If the NZ FLAG is set (no opening apostrophe), JUMP to 588DH, "Patch input format error".
55AA
GOSUB to the scanner at 5668H to read the high byte of the load address into Register A.
55AD
LD B,A 47
Save the high byte in Register B.
55AE
GOSUB to the scanner at 5668H to read the low byte of the load address into Register A.
55B1
LD (DE),A 12
Store the address low byte (Register A) into the work image at (DE).
55B2
INC DE 13
Advance Register Pair DE past the low byte.
55B3
LD A,B 78
Load Register A with the saved high byte from Register B.
55B4
LD (DE),A 12
Store the address high byte (Register A) into the work image at (DE).
55B5
INC DE 13
Advance Register Pair DE past the high byte.
55B6
LD A,(HL) 7E
Load Register A with the character after the address at (HL).
55B7
CP 3DH FE 3D
Compare Register A against 3DH (ASCII =) which introduces the data.
55B9
If the Z FLAG is set (an equals sign), jump to 55C1H to read the data.
55BB
CP 27H FE 27
Compare Register A against 27H (ASCII '), the alternate closing quote before the data.
55BD
If the NZ FLAG is set (neither an equals sign nor an apostrophe), JUMP to 588DH, "Patch input format error".
55C0
INC HL 23
Advance Register Pair HL past the apostrophe.
55C1
INC HL 23
Advance Register Pair HL to the first data character.
55C2
LD B,02H 06 02
Load Register B with 2, the running byte count (the two address bytes already stored).
Loop Start
Read data bytes into the X'nnnn' patch entry, honouring a quoted literal string.
55C4
LD A,(HL) 7E
Load Register A with the next data character at (HL).
55C5
CP 22H FE 22
Compare Register A against 22H (ASCII "), which opens a quoted literal string.
55C7
If the Z FLAG is set (a quotation mark), jump to 55E8H to copy the quoted string literally.
55C9
LD A,(HL) 7E
Load Register A with the data character at (HL).
55CA
INC HL 23
Advance Register Pair HL past that character.
55CB
CP 3BH FE 3B
Compare Register A against 3BH (ASCII ;, which separates data groups).
55CD
If the Z FLAG is set (a semicolon), jump to 55E0H to skip to the end of the group.
55CF
CP 0DH FE 0D
Compare Register A against 0DH (carriage return, end of the statement).
55D1
If the Z FLAG is set (end of statement), jump to 55FFH to store the entry's byte count.
55D3
CP 20H FE 20
Compare Register A against 20H (a space between data bytes).
55D5
If the Z FLAG is set (a blank), LOOP BACK to 55C4H to skip it.
55D7
DEC HL 2B
Back up Register Pair HL so the scanner re-reads this data character.
55D8
GOSUB to the scanner entry at 566CH to read one data byte into Register A.
55DB
LD (DE),A 12
Store the data byte (Register A) into the work image at (DE).
55DC
INC DE 13
Advance Register Pair DE past the data byte.
55DD
INC B 04
Increment Register B, the running byte count of the entry.
55DE
LOOP BACK to 55C9H for the next data byte.
Loop Start
Skip the remainder of a data group after a semicolon.
55E0
LD A,(HL) 7E
Load Register A with the next character at (HL).
55E1
INC HL 23
Advance Register Pair HL past it.
55E2
CP 0DH FE 0D
Compare Register A against 0DH (carriage return).
55E4
If the NZ FLAG is set (not the end of the line), LOOP BACK to 55E0H.
55E6
Jump to 55FFH to store the entry's byte count.
Quoted Literal
Copy the bytes of a quoted string directly into the entry.
55E8
INC HL 23
Advance Register Pair HL past the opening quotation mark.
55E9
LD A,(HL) 7E
Load Register A with the next quoted character at (HL).
55EA
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker inside an unterminated string).
55EC
If the Z FLAG is set (the string ran into the buffer end), JUMP to 588DH, "Patch input format error".
55EF
INC HL 23
Advance Register Pair HL past the character.
55F0
CP 0DH FE 0D
Compare Register A against 0DH (carriage return inside an unterminated string).
55F2
If the Z FLAG is set, JUMP to 55FFH to store the byte count.
55F5
CP 22H FE 22
Compare Register A against 22H (ASCII ", closing the quoted string).
55F7
If the Z FLAG is set (the string closed), jump back to 55C9H to resume ordinary data.
55F9
DEC HL 2B
Back up Register Pair HL so the character is stored, not consumed as a delimiter.
55FA
LD (DE),A 12
Store the quoted character (Register A) into the work image at (DE).
55FB
INC DE 13
Advance Register Pair DE past the stored character.
55FC
INC B 04
Increment Register B, the running byte count.
55FD
LOOP BACK to 55E8H for the next quoted character.
55FF
EX (SP),HL E3
Exchange Register Pair HL with the image position saved at 55A1H, so HL now points at the byte-count slot while the saved value goes back on the stack.
5600
LD (HL),B 70
Store the running byte count (Register B) into the entry's byte-count slot at (HL).
5601
POP HL E1
Restore Register Pair HL to the statement pointer.
5602
JUMP back to 5579H to scan the next statement.
5605H - Install the Assembled Patch Into the Load File
Copies the object File Control Block, reads the load file forward while writing each byte back and also into the work image beyond the assembled patch, then appends the assembled patch record to the file.
5605
PUSH HL E5
Save Register Pair HL (statement pointer) on the stack.
5606
EX DE,HL EB
Exchange Register Pair DE (the end of the assembled patch in the work image) into Register Pair HL to compute its length.
5607
LD DE,7300H 11 00 73
Point Register Pair DE at 7300H, the start of the assembled patch, for the length subtraction.
560A
XOR A AF
Set Register A to 0 to clear the CARRY FLAG before the subtraction.
560B
SBC HL,DE ED 52
Subtract 7300H (DE) from the patch end (HL); Register Pair HL now holds the length of the assembled patch.
560D
LD (5769H),HL 22 69 57
Store the patch length (Register Pair HL) at 5769H, used as the write-back offset while the file is streamed.
5610
LD HL,5969H 21 69 59
Point Register Pair HL at the "Installing patch" status string at 5969H.
5613
GOSUB to @DSPLY to show the install status (Register Pair HL).
5616
LD HL,5AF0H 21 F0 5A
Point Register Pair HL at the object File Control Block at 5AF0H (the copy source).
5619
LD DE,5B10H 11 10 5B
Point Register Pair DE at 5B10H (the copy destination, the now-closed patch File Control Block reused as a second handle on the object file).
561C
LD BC,0020H 01 20 00
Load Register Pair BC with 32, the size of a File Control Block, as the copy count.
561F
LDIR ED B0
Block-copy 32 bytes from the object File Control Block at (HL=5AF0H) to (DE=5B10H), giving a second open handle on the same file positioned independently.
5621
LD HL,5D00H 21 00 5D
Point Register Pair HL at 5D00H, a spare sector buffer for the second handle.
5624
LD (5B13H),HL 22 13 5B
Store 5D00H (Register Pair HL) into the buffer-address field at 5B13H of the copied File Control Block.
5627
LD DE,5B10H 11 10 5B
Point Register Pair DE at the copied File Control Block at 5B10H.
562A
GOSUB to @RREAD to read the current record of the object file through the second handle at 5B10H.
562D
If @RREAD returned the NZ FLAG (an error), JUMP to the shared error exit at 5867H.
5630
LD HL,7300H 21 00 73
Point Register Pair HL at 7300H, the start of the assembled patch in the work image.
Loop Start
Read each remaining byte of the object file, write it back to the file and also into the work image just past the assembled patch, so the tail of the file follows the new patch record.
5633
LD DE,5B10H 11 10 5B
Reload Register Pair DE with the second File Control Block address 5B10H that @GET reads from.
5636
GOSUB to ROM @GET to read the next byte of the object file into Register A through the second handle.
5639
If @GET returned the NZ FLAG (end of file), JUMP to 5650H to flush the assembled patch.
563C
PUSH HL E5
Save Register Pair HL (the work-image write pointer).
563D
PUSH AF F5
Save Register A (the byte just read) and the flags.
563E
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the original object File Control Block at 5AF0H (the write handle).
5641
LD A,(HL) 7E
Load Register A with the byte currently in the work image at (HL) (part of the assembled patch to be written first).
5642
GOSUB to the @PUT wrapper at 5863H to write that byte (Register A) back to the object file, shifting the file contents to make room for the patch.
5645
LD BC,(5769H) ED 4B 69 57
Load Register Pair BC with the patch length from 5769H.
5649
ADD HL,BC 09
Add the patch length (BC) to the work-image pointer (HL) so it addresses the position one patch-length beyond the current byte.
564A
POP AF F1
Restore Register A to the file byte read at 5636H.
564B
LD (HL),A 77
Store that file byte (Register A) into the work image at (HL), queuing the displaced tail behind the patch.
564C
POP HL E1
Restore Register Pair HL to the work-image write pointer.
564D
INC HL 23
Advance Register Pair HL to the next work-image position.
564E
LOOP BACK to 5633H to process the next file byte.
Flush
The file ended; write the remaining assembled-patch bytes still held in the work image out to the object file.
5650
CP 1CH FE 1C
Compare Register A against 1CH (error code 28, end of file).
5652
If the NZ FLAG is set (a real error, not end of file), JUMP to 5878H, "Load file format error".
5655
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H (the write handle).
5658
LD BC,(5769H) ED 4B 69 57
Load Register Pair BC with the patch length from 5769H as the remaining byte count.
Loop Start
Write out the trailing patch-length bytes.
565C
LD A,(HL) 7E
Load Register A with the next work-image byte at (HL).
565D
INC HL 23
Advance Register Pair HL past it.
565E
GOSUB to the @PUT wrapper at 5863H to write the byte (Register A) to the object file.
5661
DEC BC 0B
Decrement Register Pair BC, the remaining byte count.
5662
LD A,B 78
Load Register A with the high byte of the count (Register B).
5663
OR C B1
OR in the low byte (Register C); the Z FLAG is set when the count reaches zero.
5664
If the NZ FLAG is set (bytes remain), LOOP BACK to 565CH.
5666
POP HL E1
Restore Register Pair HL to the statement pointer saved at 5605H.
5667
RET C9
Return to the caller with the patch installed.
5668H - Token and Hexadecimal Scanner
Reads one value from the command buffer. A quoted character is returned literally; otherwise one or two hexadecimal digits are converted to a byte. The entry at 5668H first clears the quote flag; the entry at 566CH preserves it.
5668
XOR A AF
Set Register A to 0 to clear the quote flag before scanning a fresh value.
5669
LD (5681H),A 32 81 56
Store 0 (Register A) into the quote flag at 5681H, which is also the operand of the LD A instruction at 5680H.
566C
LD A,(HL) 7E
Load Register A with the current buffer character at (HL) (the entry point that leaves the quote flag unchanged).
566D
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
566F
If the Z FLAG is set (unexpected end of buffer), JUMP to 588DH, "Patch input format error".
5672
CP 22H FE 22
Compare Register A against 22H (ASCII ", opening a quoted character).
5674
If the NZ FLAG is set (not a quotation mark), jump to 5680H to treat the character as a hexadecimal digit.
5676
LD (5681H),A 32 81 56
Store the quotation mark (Register A = 22H) into the quote flag at 5681H, marking that a literal character follows.
5679
INC HL 23
Advance Register Pair HL past the quotation mark.
567A
LD A,(HL) 7E
Load Register A with the quoted character at (HL).
567B
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker inside the quote).
567D
If the Z FLAG is set, JUMP to 588DH, "Patch input format error".
5680
LD A,00H 3E 00
Self-Modifying Code
Load Register A with the quote-flag operand at 5681H (00H when scanning hex, 22H when a quoted character was seen), written by 5669H and 5676H.
5682
OR A B7
Test Register A; the NZ FLAG is set when a quoted character is being returned.
5683
LD A,(HL) 7E
Load Register A with the current character at (HL) without disturbing the flags.
5684
INC HL 23
Advance Register Pair HL past that character.
5685
RET NZ C0
Return with the literal character in Register A if the NZ FLAG is set (a quoted character).
5686
GOSUB to 56ADH to convert the first hexadecimal digit (Register A) to its 0-15 value.
5689
LD C,A 4F
Save the first digit value in Register C.
568A
LD A,(HL) 7E
Load Register A with the next character at (HL), a possible second hex digit.
568B
INC HL 23
Advance Register Pair HL past it.
568C
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
568E
If the Z FLAG is set, JUMP to 588DH, "Patch input format error".
5691
CP 30H FE 30
Compare Register A against 30H (ASCII 0). If Register A is below 30H the CARRY FLAG is set.
5693
If the CARRY FLAG is set (a delimiter below 0, so only one digit was given), jump to 56AAH to return the single-digit value.
5695
CP 3AH FE 3A
Compare Register A against 3AH (one past 9). If Register A is below 3AH the CARRY FLAG is set (a digit).
5697
If the CARRY FLAG is set (a decimal digit), jump to 569DH to combine both digits.
5699
CP 41H FE 41
Compare Register A against 41H (ASCII A). If Register A is below 41H the CARRY FLAG is set (a delimiter between 9 and A).
569B
If the CARRY FLAG is set (a delimiter, single digit only), jump to 56AAH.
569D
RLC C CB 01
Rotate the first digit (Register C) left one bit as the first of four shifts that move it into the high nibble.
569F
RLC C CB 01
Rotate Register C left a second time.
56A1
RLC C CB 01
Rotate Register C left a third time.
56A3
RLC C CB 01
Rotate Register C left a fourth time, so the first digit now occupies the high nibble.
56A5
GOSUB to 56ADH to convert the second hexadecimal digit (Register A) to its 0-15 value.
56A8
OR C B1
Combine the high nibble (Register C) with the low-nibble second digit (Register A), forming the full byte in Register A.
56A9
RET C9
Return with the assembled byte in Register A.
56AA
LD A,C 79
A single digit was given, so load Register A with its value from Register C.
56AB
DEC HL 2B
Back up Register Pair HL so the delimiter that ended the value is re-read by the caller.
56AC
RET C9
Return with the single-digit value in Register A.
56ADH - Convert an ASCII Hexadecimal Digit
Converts the ASCII digit in Register A to its 0-15 value, or aborts with "Non-hex digit encountered" if it is not a valid hexadecimal digit.
56AD
SUB 30H D6 30
Subtract 30H (ASCII 0) from Register A. The CARRY FLAG is set when the character was below 0.
56AF
If the CARRY FLAG is set (below 0), JUMP to 5889H, "Non-hex digit encountered".
56B2
CP 0AH FE 0A
Compare Register A against 0AH. If Register A is below 0AH the CARRY FLAG is set (a digit 0-9).
56B4
RET C D8
Return with the value 0-9 in Register A if the CARRY FLAG is set.
56B5
RES 5,A CB AF
Reset bit 5 of Register A to fold a lower-case letter a-f to upper case A-F.
56B7
SUB 07H D6 07
Subtract 07H so that A (originally 41H, now 11H) maps to 0AH.
56B9
CP 10H FE 10
Compare Register A against 10H. If Register A is below 10H the CARRY FLAG is set (a valid digit A-F).
56BB
RET C D8
Return with the value 0AH-0FH in Register A if the CARRY FLAG is set.
56BC
Otherwise JUMP to 5889H, "Non-hex digit encountered".
56BFH - Locate a Library Overlay in the Load File
Scans the object file's load records counting library-overlay markers (type 08H) until the overlay number requested by the L command is reached, then reads that overlay's load address and length into Register Pair BC and Register C. Reaching the transfer record first raises "Library overlay not found".
56BF
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H for the byte reader.
Loop Start
Read record types, counting library-overlay markers and skipping other records.
56C2
GOSUB to the object-file byte reader at 56F7H to read the next record type into Register A.
56C5
CP 08H FE 08
Compare Register A against 08H, the library-overlay-header record type.
56C7
If the Z FLAG is set (an overlay header), jump to 56DEH to test whether it is the wanted overlay.
56C9
CP 0AH FE 0A
Compare Register A against 0AH.
56CB
If the Z FLAG is set (the record list ended without the overlay), JUMP to 5870H, "Library overlay not found".
56CE
CP 01H FE 01
Compare Register A against 01H (a data-with-address load record).
56D0
If the Z FLAG is set (an unexpected data record before the overlay header), JUMP to 5874H, "Invalid library format".
56D3
GOSUB to 56F7H to read the record's length byte into Register A.
56D6
LD B,A 47
Load Register B with the record length (Register A) as the skip count.
Loop Start
Skip the record's data bytes.
56D7
GOSUB to 56F7H to read and discard one record data byte.
56DA
DECrement Register B and LOOP BACK to 56D7H until the record is consumed.
56DC
LOOP BACK to 56C2H to read the next record type.
Overlay Header Found
Compare this overlay's number against the requested number in Register C.
56DE
GOSUB to 56F7H to read the overlay header's length byte into Register A.
56E1
LD B,A 47
Load Register B with the header length (Register A).
56E2
GOSUB to 56F7H to read this overlay's number into Register A.
56E5
DEC B 05
Decrement Register B for the overlay-number byte just read.
56E6
CP C B9
Compare this overlay's number (Register A) against the requested number in Register C.
56E7
If the NZ FLAG is set (not the wanted overlay), jump to 56D7H to skip the rest of the header and resume the record scan.
56E9
GOSUB to 56F7H to read a header byte of the matched overlay (skipped).
56EC
GOSUB to 56F7H to read a further header byte (skipped).
56EF
GOSUB to 56F7H to read the overlay's low address/length byte into Register A.
56F2
LD C,A 4F
Save that byte in Register C.
56F3
GOSUB to 56F7H to read the overlay's high byte into Register A, then fall through into the byte reader whose result the L command uses.
56F6
LD B,A 47
Load Register B with that high byte (Register A); Register Pair BC now describes the located overlay.
56F7H - Object-File Byte Reader
Reads the next byte of the open object file through the ROM @GET routine, returning it in Register A, or diverts to the shared error exit if the read fails. Reached both by direct call and by falling through from 56F6H.
56F7
GOSUB to ROM @GET to read the next object-file byte (the File Control Block is in Register Pair DE) into Register A; the Z FLAG is set when a byte was available.
56FA
RET Z C8
Return with the byte in Register A if the Z FLAG is set (a byte was read).
56FB
Otherwise JUMP to the shared error exit at 5867H with the error code in Register A.
56FEH - Rebuild the Load-Module Image
Streams the object file's load records into the work area at 7300H so that a load address can be resolved to a byte position, adjusting each record's stored load address as the records are laid down, then writes the rebuilt image back to the file.
56FE
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H.
5701
LD BC,0000H 01 00 00
Load Register Pair BC with 0, the record number to position to.
5704
GOSUB to 585DH to position the object file (@POSN) to record 0.
5707
LD HL,7300H 21 00 73
Point Register Pair HL at 7300H, the destination work image.
Loop Start
Copy each load record into the work image, stopping at the transfer-address record (0AH).
570A
GOSUB to 56F7H to read the next record type into Register A.
570D
CP 04H FE 04
Compare Register A against 04H. If Register A is below 04H the CARRY FLAG is set.
570F
If the CARRY FLAG is set (a record type below 04H, invalid here), JUMP to 5874H, "Invalid library format".
5712
CP 0AH FE 0A
Compare Register A against 0AH (the transfer-address record ending the module).
5714
If the Z FLAG is set (end of module), jump to 5727H to resolve addresses.
5716
LD (HL),A 77
Store the record type (Register A) into the work image at (HL).
5717
INC HL 23
Advance Register Pair HL past the type byte.
5718
GOSUB to 56F7H to read the record's length byte into Register A.
571B
LD B,A 47
Load Register B with the record length (Register A) as the data count.
571C
LD (HL),A 77
Store the length byte (Register A) into the work image at (HL).
571D
INC HL 23
Advance Register Pair HL past the length byte.
Loop Start
Copy the record's data bytes into the image.
571E
GOSUB to 56F7H to read one data byte into Register A.
5721
LD (HL),A 77
Store the data byte (Register A) into the work image at (HL).
5722
INC HL 23
Advance Register Pair HL past the stored byte.
5723
DECrement Register B and LOOP BACK to 571EH until the record's data is copied.
5725
LOOP BACK to 570AH to copy the next record.
5727
LD (HL),A 77
Store the 0AH transfer-record type (Register A) into the work image to mark its end.
5728
LD HL,7300H 21 00 73
Point Register Pair HL back at 7300H to walk the image and adjust load addresses.
Loop Start
Walk the copied records looking for the type-08H overlay header whose address fields are patched.
572B
LD A,(HL) 7E
Load Register A with the record type at (HL).
572C
INC HL 23
Advance Register Pair HL to the length byte.
572D
LD B,(HL) 46
Load Register B with the record length at (HL).
572E
INC HL 23
Advance Register Pair HL to the record's data.
572F
CP 08H FE 08
Compare the record type (Register A) against 08H (a library-overlay header).
5731
If the Z FLAG is set (an overlay header), jump to 573DH to process its address entries.
5733
CP 0AH FE 0A
Compare Register A against 0AH (the transfer record ending the image).
5735
If the Z FLAG is set (end of image with no overlay header found), JUMP to 5870H, "Library overlay not found".
Loop Start
Skip this record's data bytes.
5738
INC HL 23
Advance Register Pair HL past one data byte.
5739
DECrement Register B and LOOP BACK to 5738H until the record is skipped.
573B
LOOP BACK to 572BH to examine the next record.
573D
LD A,(HL) 7E
Load Register A with the first byte of the overlay header's data at (HL).
573E
INC HL 23
Advance Register Pair HL past it.
573F
DEC B 05
Decrement Register B, the header's remaining byte count.
5740
CP 00H FE 00
Compare Register A against 0. If it equals, the Z FLAG is set (a zero entry).
5742
If the NZ FLAG is set (a non-zero header byte), jump to 5738H to continue skipping the header.
5744
INC HL 23
Advance Register Pair HL past a header byte.
5745
INC HL 23
Advance Register Pair HL past another header byte.
5746
LD E,(HL) 5E
Load Register E with the overlay's start-address low byte at (HL).
5747
INC HL 23
Advance Register Pair HL to the high byte.
5748
LD D,(HL) 56
Load Register D with the overlay's start-address high byte at (HL); Register Pair DE now holds the overlay's load address.
5749
INC HL 23
Advance Register Pair HL to the count byte.
574A
LD B,(HL) 46
Load Register B with the overlay's entry count at (HL).
574B
INC HL 23
Advance Register Pair HL to the first entry.
Loop Start
Match each overlay entry's address against Register Pair DE, adjusting the image when it differs.
574C
LD A,(HL) 7E
Load Register A with the entry type byte at (HL).
574D
CP 0AH FE 0A
Compare Register A against 0AH (the end-of-entries marker).
574F
If the Z FLAG is set (no more entries), jump to 577FH to write the rebuilt image back.
5751
INC HL 23
Advance Register Pair HL past the entry type.
5752
INC HL 23
Advance Register Pair HL over an entry byte.
5753
INC HL 23
Advance Register Pair HL over an entry byte.
5754
INC HL 23
Advance Register Pair HL over an entry byte.
5755
INC HL 23
Advance Register Pair HL over an entry byte to reach the address field.
5756
LD A,(HL) 7E
Load Register A with the entry's address low byte at (HL).
5757
INC HL 23
Advance Register Pair HL to the high byte.
5758
CP E BB
Compare the entry's low byte (Register A) against the overlay start-address low byte in Register E.
5759
If the NZ FLAG is set (low bytes differ), jump to 5767H to adjust this entry.
575B
LD A,(HL) 7E
Load Register A with the entry's address high byte at (HL).
575C
INC HL 23
Advance Register Pair HL past it.
575D
CP D BA
Compare the entry's high byte (Register A) against the overlay start-address high byte in Register D.
575E
If the NZ FLAG is set (high bytes differ), jump to 5768H to adjust this entry.
5760
LD A,(HL) 7E
Load Register A with the next entry byte at (HL).
5761
CP B B8
Compare it (Register A) against the entry count in Register B.
5762
If the NZ FLAG is set (a mismatch), jump to 5768H to adjust this entry.
5764
INC HL 23
Advance Register Pair HL past the matched byte.
5765
LOOP BACK to 574CH for the next entry.
5767
INC HL 23
Advance Register Pair HL past the entry's high byte before adjusting.
5768
LD DE,0000H 11 00 00
Load Register Pair DE with 0, the adjustment added to the entry's stored address.
576B
LD A,(HL) 7E
Load Register A with the entry's address low byte at (HL).
576C
ADD A,E 83
Add the adjustment low byte (Register E) to it in Register A.
576D
LD (HL),A 77
Store the adjusted low byte (Register A) back into the entry at (HL).
576E
DEC HL 2B
Back up Register Pair HL by one.
576F
DEC HL 2B
Back up Register Pair HL to the entry's high byte.
5770
LD A,(HL) 7E
Load Register A with the entry's address high byte at (HL).
5771
ADC A,D 8A
Add the adjustment high byte (Register D) with carry from the low byte, in Register A.
5772
LD (HL),A 77
Store the adjusted high byte (Register A) back into the entry at (HL).
5773
INC HL 23
Advance Register Pair HL forward.
5774
LD A,(HL) 7E
Load Register A with the following entry byte at (HL).
5775
ADC A,00H CE 00
Add zero with any remaining carry into Register A to propagate the address adjustment.
5777
LD (HL),A 77
Store the propagated byte (Register A) back at (HL).
5778
INC HL 23
Advance Register Pair HL.
5779
INC HL 23
Advance Register Pair HL to the next entry.
577A
LD DE,0000H 11 00 00
Reload Register Pair DE with 0 for the next entry's adjustment.
577D
LOOP BACK to 574CH for the next entry.
577F
LD DE,5AF0H 11 F0 5A
Point Register Pair DE at the object File Control Block at 5AF0H to write the image back.
5782
LD BC,0000H 01 00 00
Load Register Pair BC with 0, the record number to position to.
5785
GOSUB to 585DH to position the object file (@POSN) to record 0.
5788
LD HL,7300H 21 00 73
Point Register Pair HL at 7300H, the start of the rebuilt image.
Loop Start
Write the rebuilt image back to the object file, record by record, until the transfer record is reached.
578B
LD A,(HL) 7E
Load Register A with the record type at (HL).
578C
CP 0AH FE 0A
Compare Register A against 0AH (transfer record, the end of the image).
578E
RET Z C8
Return to the caller when the Z FLAG is set (the whole image has been written).
578F
INC HL 23
Advance Register Pair HL past the type byte.
5790
GOSUB to the @PUT wrapper at 5863H to write the record type (Register A) to the object file.
5793
LD A,(HL) 7E
Load Register A with the record length at (HL).
5794
INC HL 23
Advance Register Pair HL past the length byte.
5795
LD B,A 47
Load Register B with the record length (Register A) as the data count.
5796
GOSUB to 5863H to write the length byte (Register A) to the object file.
Loop Start
Write the record's data bytes.
5799
LD A,(HL) 7E
Load Register A with the next data byte at (HL).
579A
INC HL 23
Advance Register Pair HL past it.
579B
GOSUB to 5863H to write the data byte (Register A) to the object file.
579E
DECrement Register B and LOOP BACK to 5799H until the record's data is written.
57A0
LOOP BACK to 578BH to write the next record.
57A2H - Switch to the Second Pass
Ends the first (validating) pass by setting the pass flag non-zero and restarting the dispatch loop so every statement is applied on the second pass.
57A2
LD (530BH),A 32 0B 53
Store Register A (non-zero, the end-of-buffer marker seen at 57ACH) into the pass-flag operand at 530BH so the dispatch loop takes the second-pass path.
57A5
JUMP to the dispatch loop at 52FCH to reprocess the buffer, this time applying each statement.
57A8H - First-Pass Command Validation
On the first pass each statement is recognised and validated without writing the file. R and O set their flags, D falls through to the verify path, and the comment, F, Y, L and X statements are simply skipped. Reaching the end of the buffer switches to the second pass.
57A8
CP 2EH FE 2E
Compare Register A (the statement's leading character) against 2EH (ASCII ., a comment).
57AA
If the Z FLAG is set (a comment), jump to 57D1H to skip the line.
57AC
CP 03H FE 03
Compare Register A against 03H (end-of-buffer marker).
57AE
If the Z FLAG is set (all statements validated), jump to 57A2H to begin the second pass.
57B0
RES 5,A CB AF
Reset bit 5 of Register A to fold the command letter to upper case.
57B2
CP 44H FE 44
Compare Register A against 44H (ASCII D).
57B4
If the Z FLAG is set (a data statement), jump to 57D4H to verify the original bytes without writing.
57B6
CP 52H FE 52
Compare Register A against 52H (ASCII R).
57B8
If the Z FLAG is set, JUMP to the R sub-command at 5409H to set the reverse flag.
57BB
CP 4FH FE 4F
Compare Register A against 4FH (ASCII O).
57BD
If the Z FLAG is set, JUMP to the O sub-command at 54A4H to set the option flag.
57C0
CP 46H FE 46
Compare Register A against 46H (ASCII F).
57C2
If the Z FLAG is set (a find line), jump to 57D1H to skip it.
57C4
CP 59H FE 59
Compare Register A against 59H (ASCII Y).
57C6
If the Z FLAG is set (a yank keyword line), jump to 57D1H to skip it on the first pass.
57C8
CP 4CH FE 4C
Compare Register A against 4CH (ASCII L).
57CA
If the Z FLAG is set (a library line), jump to 57D1H to skip it on the first pass.
57CC
CP 58H FE 58
Compare Register A against 58H (ASCII X).
57CE
If the NZ FLAG is set (an unrecognised leading letter), JUMP to 588DH, "Patch input format error".
57D1
JUMP to 538CH to skip the rest of the line and continue the first-pass scan.
57D4
LD A,0FFH 3E FF
Self-Modifying Code
Load Register A with the option-flag operand at 57D5H (0FFH by default, 0AFH when turned on, or the OPTION parameter value planted at 5278H).
57D6
OR A B7
Test Register A; the Z FLAG is set when the option is off.
57D7
If the Z FLAG is set (the option is off), JUMP to 538CH to skip this data statement.
57DA
LD A,00H 3E 00
Self-Modifying Code
Load Register A with the reverse/remove-flag operand at 57DBH (00H normally, 0FFH after an R statement, or the REMOVE parameter value planted at 527EH).
57DC
OR A B7
Test Register A; the NZ FLAG is set when reverse/remove mode is active.
57DD
If the NZ FLAG is set (reverse/remove mode), JUMP to 581AH to verify against the replacement bytes instead of the original bytes.
57E0
LD (5AEAH),HL 22 EA 5A
Store the statement pointer (Register Pair HL) at 5AEAH so 57ECH can rescan the D statement after locating its find clause.
57E3
GOSUB to 5834H to advance Register Pair HL to the find clause (the text after the colon on this D line).
57E6
GOSUB to 57ECH to verify that the record's original bytes match the find clause before the patch is applied on the second pass.
57E9
JUMP back to the dispatch loop at 52FFH for the next statement.
57ECH - Verify a D Statement Against Its Find Clause
Confirms that the D and F parts of the statement address the same record and offset, then parses and checks the original bytes so a mismatched patch is refused with "FIND line mismatch".
57EC
LD (5897H),HL 22 97 58
Save the current statement pointer (Register Pair HL) at 5897H.
57EF
PUSH HL E5
Save Register Pair HL (the find-clause pointer) on the stack.
57F0
LD DE,(5AEAH) ED 5B EA 5A
Load Register Pair DE with the D-statement pointer saved at 5AEAH so the two clauses can be compared.
57F4
LD B,03H 06 03
Load Register B with 3, the number of address characters to compare.
Loop Start
Compare the D and F record-number characters.
57F6
INC HL 23
Advance Register Pair HL to the next find-clause character.
57F7
INC DE 13
Advance Register Pair DE to the next D-statement character.
57F8
LD A,(DE) 1A
Load Register A with the D-statement character at (DE).
57F9
CP (HL) BE
Compare it (Register A) against the find-clause character at (HL).
57FA
If the NZ FLAG is set (the record numbers differ), JUMP to 5857H, "FIND line mismatch".
57FD
DECrement Register B and LOOP BACK to 57F6H until the three characters match.
57FF
LD B,03H 06 03
Load Register B with 3, the default number of offset characters to compare.
5801
LD A,2CH 3E 2C
Load Register A with 2CH (ASCII ,) to test whether a comma follows.
5803
CP (HL) BE
Compare the comma (Register A) against the find-clause character at (HL).
5804
If the Z FLAG is set (a comma, so the shorter offset form applies), jump to 5808H.
5806
LD B,05H 06 05
Otherwise load Register B with 5, the longer count of offset characters to compare.
Loop Start
Compare the D and F byte-offset characters.
5808
INC HL 23
Advance Register Pair HL to the next find-clause character.
5809
INC DE 13
Advance Register Pair DE to the next D-statement character.
580A
LD A,(DE) 1A
Load Register A with the D-statement character at (DE).
580B
CP (HL) BE
Compare it (Register A) against the find-clause character at (HL).
580C
If the NZ FLAG is set (the offsets differ), JUMP to 5857H, "FIND line mismatch".
580F
DECrement Register B and LOOP BACK to 5808H until the offset characters match.
5811
EX (SP),HL E3
Exchange Register Pair HL with the saved find-clause pointer, so HL addresses the D statement while the find pointer returns to the stack.
5812
GOSUB to 53A6H to parse the D statement's record and offset and read that record of the object file.
5815
POP HL E1
Restore Register Pair HL to the find-clause pointer.
5816
GOSUB to 53D0H to parse and check the original bytes from the find clause against the record; a mismatch aborts through 5849H/5857H.
5819
RET C9
Return to the first-pass dispatcher at 57E9H.
581AH - Verify a Reverse Patch and Swap D/F
In reverse (remove) mode the roles of the D and F clauses are swapped: the file is verified against the replacement bytes, and the statement's leading letters are rewritten so the second pass restores the original bytes.
581A
PUSH HL E5
Save Register Pair HL (statement pointer) on the stack.
581B
GOSUB to 5834H to advance Register Pair HL to the find clause of the D line.
581E
LD (5AEAH),HL 22 EA 5A
Store the find-clause pointer (Register Pair HL) at 5AEAH so 57ECH treats the F clause as the source.
5821
POP HL E1
Restore Register Pair HL to the statement pointer.
5822
PUSH HL E5
Save Register Pair HL again for the reverse-verify call.
5823
GOSUB to 57ECH to verify the record against the replacement bytes (the D clause), confirming the patch to be removed is present.
5826
POP HL E1
Restore Register Pair HL to the statement pointer.
5827
LD (HL),2EH 36 2E
Overwrite the D statement's leading character at (HL) with 2EH (ASCII .) so it is ignored on the second pass.
5829
LD HL,(5AEAH) 2A EA 5A
Load Register Pair HL with the find-clause pointer from 5AEAH.
582C
LD (HL),44H 36 44
Overwrite the find clause's leading character at (HL) with 44H (ASCII D) so the F clause becomes the D statement that restores the original bytes.
582E
GOSUB to 5834H to advance Register Pair HL past this line.
5831
JUMP back to the dispatch loop at 52FFH for the next statement.
5834H - Line-Scan Helpers
Small helpers used by the verify and option paths: 5834H skips forward past comment lines, 583DH advances to the next carriage return, and 5844H reads one character folded to upper case.
Loop Start
Advance past the current line and skip any following comment lines.
5834
GOSUB to 583DH to advance Register Pair HL past the current line's carriage return.
5837
LD A,(HL) 7E
Load Register A with the first character of the next line at (HL).
5838
CP 2EH FE 2E
Compare Register A against 2EH (ASCII ., a comment).
583A
If the Z FLAG is set (a comment line), LOOP BACK to 5834H to skip it too.
583C
RET C9
Return with Register Pair HL at the next non-comment line.
Loop Start
Advance to the carriage return that ends the current line.
583D
LD A,(HL) 7E
Load Register A with the next character at (HL).
583E
INC HL 23
Advance Register Pair HL past it.
583F
CP 0DH FE 0D
Compare Register A against 0DH (carriage return).
5841
RET Z C8
Return when the Z FLAG is set (the end of the line was reached).
5842
LOOP BACK to 583DH until the carriage return is found.
5844
LD A,(HL) 7E
Load Register A with the character at (HL).
5845
INC HL 23
Advance Register Pair HL past it.
5846
RES 5,A CB AF
Reset bit 5 of Register A to fold the character to upper case.
5848
RET C9
Return with the upper-cased character in Register A.
5849H - Apply or Verify One Patch Byte
The workhorse of the D command. On the second pass it writes the byte to the record through the @PUT wrapper; on the first pass it reads the corresponding object-file byte and compares it, aborting with "FIND line mismatch" if they differ.
5849
LD C,A 4F
Save the patch byte in Register C.
584A
LD A,(530BH) 3A 0B 53
Load Register A with the pass flag at 530BH (zero on the first pass, non-zero on the second).
584D
OR A B7
Test Register A; the NZ FLAG is set on the second pass.
584E
LD A,C 79
Restore the patch byte into Register A from Register C without changing the flags.
584F
If the NZ FLAG is set (second pass), JUMP to the @PUT wrapper at 5863H to write the patch byte (Register A) into the record.
5852
Otherwise (first pass) GOSUB to 56F7H to read the current object-file byte into Register A for verification.
5855
CP C B9
Compare the file byte (Register A) against the expected byte in Register C.
5856
RET Z C8
Return if the Z FLAG is set (the bytes match, verification passed).
5857
LD HL,5A93H 21 93 5A
Point Register Pair HL at the "FIND line mismatch" message at 5A93H.
585A
JUMP to the message-and-abort path at 5890H to display the message (Register Pair HL) and return to DOS.
585DH - Position, Output, and Error Exits
The @POSN wrapper, the @PUT wrapper, and the shared error exits. 5867H hands an error code to @ERROR and aborts; 586CH does so with a comma error; 5870H, 5874H, 5878H, 587CH, 5880H, 5889H and 588DH each select a fixed message and abort.
585D
GOSUB to @POSN to position the object file (File Control Block in Register Pair DE) to the record in Register Pair BC.
5860
RET Z C8
Return if the Z FLAG is set (positioning succeeded).
5861
Otherwise jump to the shared error exit at 5867H.
5863
GOSUB to ROM @PUT to output the byte in Register A to the file whose File Control Block is in Register Pair DE.
5866
RET Z C8
Return if the Z FLAG is set (the byte was written).
5867
OR 40H F6 40
Set bit 6 of the error code in Register A so @ERROR returns to PATCH rather than aborting to DOS itself.
5869
JUMP to the resident @ERROR vector to display the system error message for the code in Register A.
586C
LD A,2CH 3E 2C
Load Register A with 2CH, the code reported when a comma was expected but missing.
586E
Jump to 5867H to report the error through @ERROR.
Overlapping Error-Message Table
The five entries at 5870H, 5874H, 5878H, 587CH and 5880H are each a three-byte LD HL,message separated by a single 0DDH byte. Entered at any one of them, that entry loads its message into Register Pair HL; the 0DDH turns each following LD HL that falls through into a harmless LD IX, so only the entry point's message survives. All five converge on 5883H.
5870
LD HL,59D7H 21 D7 59
Point Register Pair HL at the "Library overlay not found" message at 59D7H (entered from 56CBH and 5735H).
5873
DEFB 0DDH DD
This 0DDH byte is the IX prefix that absorbs the following LD HL into an LD IX when 5870H falls through, so only the 59D7H message is kept.
5874
LD HL,59F1H 21 F1 59
Point Register Pair HL at the "Invalid library format" message at 59F1H (entered from 56D0H and 570FH).
5877
DEFB 0DDH DD
Prefix byte that turns the following LD HL into LD IX on fall-through.
5878
LD HL,5A21H 21 21 5A
Point Register Pair HL at the "Load file format error" message at 5A21H (entered from 535AH, 5503H, 5535H and 5652H).
587B
DEFB 0DDH DD
Prefix byte that turns the following LD HL into LD IX on fall-through.
587C
LD HL,5A73H 21 73 5A
Point Register Pair HL at the "Fix file too big - partition it" message at 5A73H (entered from 52EFH).
587F
DEFB 0DDH DD
Prefix byte that turns the following LD HL into LD IX on fall-through.
5880
LD HL,5910H 21 10 59
Point Register Pair HL at the "PROGRAM file name required" message at 5910H (entered from 520EH, 5214H and 52A9H).
5883
GOSUB to @LOGOT to display the selected message (Register Pair HL) on the video screen.
5886
JUMP to the resident @ABORT vector to return to DOS after a fatal error.
5889
LD HL,5A38H 21 38 5A
Point Register Pair HL at the "Non-hex digit encountered" message at 5A38H (entered from 56AFH and 56BCH).
588C
DEFB 0DDH DD
Prefix byte that turns the following LD HL at 588DH into LD IX when 5889H falls through.
588D
LD HL,5A08H 21 08 5A
Point Register Pair HL at the "Patch input format error" message at 5A08H (the general format-error entry, reached from many tests).
5890
PUSH HL E5
Save the message pointer (Register Pair HL) while a carriage return is displayed.
5891
LD A,0DH 3E 0D
Load Register A with 0DH (carriage return) to move to a fresh line before the message.
5893
GOSUB to ROM @DSP to display the carriage return in Register A.
5896
LD HL,0000H 21 00 00
Load Register Pair HL with 0, an empty string, so the following @LOGOT emits nothing but positions the output.
5899
GOSUB to @LOGOT with the empty string (Register Pair HL) to flush the line.
589C
POP HL E1
Restore Register Pair HL to the message pointer.
589D
Jump to 5883H to display the message and abort to DOS.
589FH - Data - Default Extensions, Sign-On Banner, and Messages
Non-executable data: the default file extensions applied by @FEXT, the sign-on banner, the five status-line strings shown while a patch is processed, and every diagnostic message. The status strings are framed by video control codes (1DH, 1EH) and end with 03H so they overwrite the status line in place; the diagnostic messages end with a carriage return.
589F
DEFM "CMD" 43 4D 44
Default extension supplied to the object filespec by @FEXT at 521BH, so a bare object name becomes a /CMD file.
58A2
DEFM "FIX" 46 49 58
Default extension supplied to the patch filespec by @FEXT at 5237H, so a bare patch name becomes a /FIX file.
58A5
DEFM 0DH,0AH,"PATCH - LDOS Object File Patch Utility - Version 5.3.1",0AH,"Copyright 1991 MISOSYS, Inc., All rights reserved",0AH,0DH 0A 50 41 54 43 48 20 2D 20 4C 44 4F 53 20 4F 62 6A 65 63 74 20 46 69 6C 65 20 50 61 74 63 68 20 55 74 69 6C 69 74 79 20 2D 20 56 65 72 73 69 6F 6E 20 35 2E 33 2E 31 0A 43 6F 70 79 72 69 67 68 74 20 31 39 39 31 20 4D 49 53 4F 53 59 53 2C 20 49 6E 63 2E 2C 20 41 6C 6C 20 72 69 67 68 74 73 20 72 65 73 65 72 76 65 64 0A 0D
Sign-on banner displayed by @DSPLY at 5204H.
5910
DEFM "PROGRAM file name required",0DH 50 52 4F 47 52 41 4D 20 66 69 6C 65 20 6E 61 6D 65 20 72 65 71 75 69 72 65 64 0D
Error message displayed through 5880H when no object or patch filename is given.
592B
DEFM 1DH,"Positioning load file",1EH,1DH,03H 1D 50 6F 73 69 74 69 6F 6E 69 6E 67 20 6C 6F 61 64 20 66 69 6C 65 1E 1D 03
Status-line string shown by 5528H while the object file is positioned.
5944
DEFM 1DH,"Reading input",1EH,1DH,03H 1D 52 65 61 64 69 6E 67 20 69 6E 70 75 74 1E 1D 03
Status-line string shown at the top of the dispatch loop at 5300H.
5955
DEFM 1DH,"Generating patch",1EH,1DH,03H 1D 47 65 6E 65 72 61 74 69 6E 67 20 70 61 74 63 68 1E 1D 03
Status-line string shown by 555CH while the patch record is generated.
5969
DEFM 1DH,"Installing patch",1EH,1DH,03H 1D 49 6E 73 74 61 6C 6C 69 6E 67 20 70 61 74 63 68 1E 1D 03
Status-line string shown by 534FH and 5610H while the patch is installed.
597D
DEFM 1DH,"Re-building library map",1EH,1DH,03H 1D 52 65 2D 62 75 69 6C 64 69 6E 67 20 6C 69 62 72 61 72 79 20 6D 61 70 1E 1D 03
Status-line string shown by 5519H while the library map is rebuilt.
5998
DEFM 1DH,"Yanking patch from file",1EH,1DH,03H 1D 59 61 6E 6B 69 6E 67 20 70 61 74 63 68 20 66 72 6F 6D 20 66 69 6C 65 1E 1D 03
Status-line string shown by 5418H while a patch is removed.
59B3
DEFM 0AH,"Can't yank, patch not in load file",0DH 0A 43 61 6E 27 74 20 79 61 6E 6B 2C 20 70 61 74 63 68 20 6E 6F 74 20 69 6E 20 6C 6F 61 64 20 66 69 6C 65 0D
Message displayed through 549EH when the named patch is not found for removal.
59D7
DEFM "Library overlay not found",0DH 4C 69 62 72 61 72 79 20 6F 76 65 72 6C 61 79 20 6E 6F 74 20 66 6F 75 6E 64 0D
Message selected at 5870H when the requested library overlay is absent.
59F1
DEFM "Invalid library format",0DH 49 6E 76 61 6C 69 64 20 6C 69 62 72 61 72 79 20 66 6F 72 6D 61 74 0D
Message selected at 5874H when a library load record is malformed.
5A08
DEFM "Patch input format error",0DH 50 61 74 63 68 20 69 6E 70 75 74 20 66 6F 72 6D 61 74 20 65 72 72 6F 72 0D
General format-error message selected at 588DH.
5A21
DEFM "Load file format error",0DH 4C 6F 61 64 20 66 69 6C 65 20 66 6F 72 6D 61 74 20 65 72 72 6F 72 0D
Message selected at 5878H when the object file is not a valid load module.
5A38
DEFM "Non-hex digit encountered",0DH 4E 6F 6E 2D 68 65 78 20 64 69 67 69 74 20 65 6E 63 6F 75 6E 74 65 72 65 64 0D
Message selected at 5889H when a hexadecimal field holds a non-hex character.
5A52
DEFM 0AH,"Patch(s) successfully installed",0DH 0A 50 61 74 63 68 28 73 29 20 73 75 63 63 65 73 73 66 75 6C 6C 79 20 69 6E 73 74 61 6C 6C 65 64 0D
Default closing message displayed at 5386H after a successful install.
5A73
DEFM "Fix file too big - partition it",0DH 46 69 78 20 66 69 6C 65 20 74 6F 6F 20 62 69 67 20 2D 20 70 61 72 74 69 74 69 6F 6E 20 69 74 0D
Message selected at 587CH when the /FIX file overflows the command buffer.
5A93
DEFM "FIND line mismatch",0DH 46 49 4E 44 20 6C 69 6E 65 20 6D 69 73 6D 61 74 63 68 0D
Message selected at 5857H when a D statement's original bytes do not match the file.
5AA6
DEFM "Patch successfully yanked",0DH 50 61 74 63 68 20 73 75 63 63 65 73 73 66 75 6C 6C 79 20 79 61 6E 6B 65 64 0D
Closing message planted at 5493H after a successful patch removal.
5AC0H - Data - Run-Time Buffers and the @PARAM Keyword Table
The CLP name length cell and eight-byte name buffer (filled at run time by the patch filename), the @PARAM keyword table naming the REMOVE and OPTION parameters, and the parameter result cells. Each @PARAM entry is a six-character blank-padded keyword followed by the two-byte address of its result cell; a 00H byte ends the table.
5AC0
DEFB 03H 03
CLP name length cell, overwritten at 525AH with the length of the patch (/FIX) filename; the file image ships it holding 3, matching the default name "CLP".
5AC1
DEFM "CLP " 43 4C 50 20 20 20 20 20
CLP name buffer (8 bytes), holding the default "CLP" plus blanks in the file image but overwritten at 523DH by the patch filename used to identify an installed patch.
5AC9
DEFM "REMOVE" 52 45 4D 4F 56 45
@PARAM keyword "REMOVE", which requests removal of a patch.
5ACF
DEFW 5AECH EC 5A
Result-cell address for REMOVE; @PARAM stores the given value at 5AECH.
5AD1
DEFM "R " 52 20 20 20 20 20
@PARAM keyword "R", the accepted abbreviation of REMOVE.
5AD7
DEFW 5AECH EC 5A
Result-cell address for the R abbreviation, the same 5AECH cell as REMOVE.
5AD9
DEFM "OPTION" 4F 50 54 49 4F 4E
@PARAM keyword "OPTION", which sets the on/off option.
5ADF
DEFW 5AEEH EE 5A
Result-cell address for OPTION; @PARAM stores the given value at 5AEEH.
5AE1
DEFM "O " 4F 20 20 20 20 20
@PARAM keyword "O", the accepted abbreviation of OPTION.
5AE7
DEFW 5AEEH EE 5A
Result-cell address for the O abbreviation, the same 5AEEH cell as OPTION.
5AE9
DEFB 00H 00
Terminator byte ending the @PARAM keyword table.
5AEA
DEFW 0000H 00 00
Saved buffer position of a D statement's load-address text, written by 57E0H and 581EH.
5AEC
DEFW 0000H 00 00
REMOVE parameter result cell, read at 527BH into the reverse/remove flag.
5AEE
DEFW 0FFFFH FF FF
OPTION parameter result cell, read at 5275H into the on/off option flag.