home *** CD-ROM | disk | FTP | other *** search
/ ftp.barnyard.co.uk / 2015.02.ftp.barnyard.co.uk.tar / ftp.barnyard.co.uk / cpm / walnut-creek-CDROM / SIMTEL / CPMUG / CPMUG042.ARK / MNEMONIC.ASM < prev    next >
Assembly Source File  |  1984-04-29  |  27KB  |  1,059 lines

  1.     TITLE    '*** MNEMONIC  V. 2.0 - 3/14/79 ***'
  2.     PAGE    57
  3. ;*******************************************************************
  4. ;
  5. ;    MNEMONIC - A MULTI-PASS MEMORY TESTER FOR CP/M
  6. ;
  7. ;        COPYRIGHT 1978, BY
  8. ;        WILLIAM T. PRECHT & ASSOCIATES
  9. ;        1102 S. EDSON
  10. ;        LOMBARD, IL  60148
  11. ;
  12. ;********************************************************************
  13. ;
  14.     ORG    100H    ; ORG FOR CP/M TPA
  15. ;
  16. STAK    EQU    1000H    ; STACK ADDR - PRESERVE THIS
  17. STAKH    EQU    10H    ; STACK H/O ADDR - USED TO COMPARE TO PARMS
  18. EXITA    EQU    0F000H    ; COLD BOOT ADDR
  19. CONSD    EQU    00    ; CONSOLE DATA PORT
  20. CONST    EQU    02    ; CONSOLE STATUS PORT
  21. CONSI    EQU    04H    ; READY BIT FOR KYBD (ACTIVE HIGH)
  22. CONSO    EQU    08H    ; READY BIT FOR CONSOLE OUTPUT (ACTIVE HIGH)
  23. SSWD    EQU    20H    ; SENSE SW 5 = DETAIL ERROR LIST
  24. SSWS    EQU    10H    ; S.S. 4 = DO SLOW TEST
  25. ;
  26. ;*******************************************************************
  27. ;
  28.     JMP    START    ; BYPASS JUMP TABLE
  29. ;
  30. EXIT    JMP    EXITA    ; EXIT JUMP - GO TO COLD BOOT ADDR
  31. KEYIN    JMP    ZKEYIN    ; CUSTOM CONSOLE INPUT
  32. KSTAT    JMP    ZKSTAT    ;   "       "    READY TEST
  33. TYPE    JMP    ZTYPE    ;   "       "    OUTPUT
  34. ;
  35. ;********************************************************************
  36. ;
  37. ;        CONSOLE KEYBOARD INPUT ROUTINE
  38. ;
  39. ;********************************************************************
  40. ;
  41. ZKEYIN    EQU    $
  42.     CALL    KSTAT    ; TEST CHAR READY
  43.     JNC    KEYIN    ;  NOT READY, LOOP
  44.     IN    CONSD    ; READ CONSOLE DATA
  45.     ANI    7FH    ; STRIP PARITY
  46.     CALL    TYPE    ; ECHO IT TO TERMINAL
  47.     RET
  48. ;
  49. ZKSTAT    EQU    $
  50.     IN    CONST    ; READ CONSOLE STATUS PORT
  51.     ANI    CONSI    ;  TEST INPUT READY BIT
  52.     RZ        ;  NOPE, RET
  53.     STC        ;  YUP, SET CARRY
  54.     RET
  55. ;
  56. ;********************************************************************
  57. ;
  58. ;        CONSOLE OUTPUT ROUTINE
  59. ;
  60. ;********************************************************************
  61. ;
  62. ZTYPE    EQU    $
  63.     CALL    TYPEC    ; TYPE CHAR
  64.     CPI    0DH    ; Q. CARR RTN?
  65.     RNZ        ;  NO, RETURN
  66.     MVI    A,0AH    ; GET LINE FEED
  67.     CALL    TYPEC    ;  SEND IT
  68.     RET
  69. ;
  70. TYPEC    EQU    $
  71.     PUSH    PSW    ; SAVE CHAR 2B TYPED
  72. TYPEL    IN    CONST    ; READ CONSOLE STATUS
  73.     ANI    CONSO    ; TEST OUTPUT READY BIT
  74.     JZ    TYPEL    ;  NOPE, LOOP
  75.     POP    PSW    ;  ELSE, GET CHAR
  76.     OUT    CONSD    ;  TYPE IT
  77.     RET
  78. ;
  79.     PAGE
  80. ;
  81. ;*******************************************************************
  82. ;
  83. ;        START - PROGRAM BEGINS; DO INIT
  84. ;
  85. ;*******************************************************************
  86. ;
  87. START    EQU    $
  88.     LXI    SP,STAK    ; GET STACK ADDR
  89.     CALL    PMSG1    ; TYPE VERSION MSG
  90.     JMP    SPARM    ; BYPASS CONTINUOUS TEST 1ST TIME
  91. ;
  92. ;*******************************************************************
  93. ;
  94. ;        MAIN PROGRAM LOOP
  95. ;
  96. ;********************************************************************
  97. ;
  98. LOOP    EQU    $
  99.     CALL    KSTAT    ; TEST CONSOLE READY
  100.     JNC    CONTIN    ;  NO, LOOP TILL INTERRUPTED
  101.     IN    CONSD    ;  CLEAR INTERRUPTING DATA
  102. SPARM    EQU    $
  103.     CALL    GPARM    ; GET ADDRS TO TEST
  104.     JC    SPARM    ;  LET'S TRY GETTING THOSE PARMS AGAIN
  105.     CALL    QUICK    ; DO QUICK TEST FOR MEM PRESENT
  106. CONTIN    EQU    $
  107.     CALL    RANDS    ; SAVE RANDOM SEED
  108.     CALL    GPATT    ; GEN RANDOM PATTERNS IN EACH LOC
  109.     CALL    KSTAT    ; TEST KYBD READY
  110.     JC    LOOPP    ;  YES, PRINT MATRIX AND EXIT
  111.     CALL    RANDR    ; RESET RAND TO SEED
  112.     CALL    TPATT    ; TEST PATTERNS
  113.     CALL    KSTAT    ; TEST KYBD READY
  114.     JC    LOOPP    ;  YES, PRINT MATRIX AND EXIT
  115.     CALL    SLOW    ; DO SUPER-SLOW MEM TEST
  116.     CALL    KSTAT    ; TEST KYBD READY
  117.     JC    LOOPP    ;  YES, PRINT MATRIX AND EXIT
  118.     LHLD    PASSC    ; GET 16-BIT PASS COUNTER
  119.     INX    H    ;  PLUS 1
  120.     SHLD    PASSC    ;   AND STORE IT BACK
  121.     CALL    PRTPASS    ; PRINT PASS COUNT
  122.     JMP    LOOPX    ;  ELSE, GO TO LOOP EXIT
  123. ;
  124. LOOPP    EQU    $
  125.     CALL    PRMAT    ; PRINT ERROR MATRIX
  126. ;
  127. LOOPX    EQU    $
  128.     JMP    LOOP    ; LOOP TILL INTERRUPTED
  129. ;
  130.     PAGE
  131. ;
  132. ;********************************************************************
  133. ;
  134. ;        GPARM - GET ADDRESS PARAMETERS
  135. ;
  136. ;********************************************************************
  137. ;
  138. GPARM    EQU    $
  139.     CALL    INIT    ; INIT ERROR MATRIX
  140.     CALL    GTSTA    ; GET START ADDR
  141.     RC        ;  CARRY=ERROR, SO RETURN
  142.     CALL    GTEND    ; GET END ADDR
  143.     RC        ;  CARRY, PROBLEM
  144.     RET
  145. ;
  146. ;********************************************************************
  147. ;
  148. ;        GPATT - GET RANDOM PATTERN TO ADDRESS SPACE
  149. ;
  150. ;********************************************************************
  151. ;
  152. GPATT    EQU    $
  153.     LHLD    AEND    ; GET END ADDR TO H-L
  154.     XCHG        ;  SWAP IT TO D-E
  155.     LHLD    ASTRT    ; GET STARTING ADDR TO H-L
  156. GPAT2    EQU    $
  157.     CALL    KSTAT    ; TEST KYBD READY
  158.     RC        ;  YUP, EXIT
  159.     CALL    RANDB    ; GET RANDOM BYTE
  160.     CALL    STNDX    ; STORE CHAR, BUMP INDEX
  161.     JC    GPAT2    ;  LT MAX, LOOP
  162.     RET
  163. ;
  164. ;********************************************************************
  165. ;
  166. ;        TPATT - TEST RANDOM PATTERN PREVIOUSLY GENERATED
  167. ;
  168. ;********************************************************************
  169. ;
  170. TPATT    EQU    $
  171.     LHLD    AEND    ; GET END ADDR TO H-L
  172.     XCHG        ;  SWAP IT TO D-E
  173.     LHLD    ASTRT    ; GET STARTING ADDR
  174. TPAT2    EQU    $
  175.     CALL    RANDB    ; GET RANDOM BYTE
  176.     MOV    B,M    ; GET CHAR FROM MEM TO B
  177.     CMP    B    ; TEST EXPECTED TO ACTUAL
  178.     JZ    TPAT3    ;  EQ, ON
  179.     CALL    TYPEA    ; RECORD ADDR AND FAILURE
  180.     CALL    STMAT    ;  AND STORE IN ERROR MATRIX
  181. ;
  182. TPAT3    EQU    $
  183.     CALL    KSTAT    ; TEST KYBD STATUS
  184.     RC        ;  YES, EARLY EXIT
  185.     CALL    INDEX    ; BUMP MEM PTR
  186.     JC    TPAT2    ;  LT MAX, LOOP
  187.     RET
  188. ;
  189. ;********************************************************************
  190. ;
  191. ;        STNDX - STORE BYTE IN MEMORY, BUMP INDEX
  192. ;
  193. ;********************************************************************
  194. ;
  195. STNDX    EQU    $
  196.     MOV    M,A    ; STORE CHAR IN MEM
  197.     JMP    INDEX    ;  BUMP MEM PTR AND EXIT
  198. ;
  199. ;********************************************************************
  200. ;
  201. ;        INDEX - BUMP H-L, COMPARE TO D-E (ENDING ADDR)
  202. ;
  203. ;********************************************************************
  204. ;
  205. INDEX    EQU    $
  206.     MOV    A,H    ; GET H/O OF CURR ADDR
  207.     CMP    D    ; TEST TO H/O OF END
  208.     JC    INXIT    ;  LT, ONWARD
  209.     JNZ    INXIT    ;  NOT ZERO, END
  210.     MOV    A,L    ; TEST L/O
  211.     CMP    E    ;  TO L/O OF END
  212.     JC    INXIT    ;  LT, ON
  213. ;
  214. ;        H-L = D-E
  215. ;            RESET ZERO AND CARRY FLAGS
  216. ;
  217.     MVI    A,0    ; GET ZERO
  218.     DCR    A    ; RESET ZERO FLAG
  219.     ORA    A    ;  AND CARRY
  220.     RET
  221. ;
  222. INXIT    EQU    $
  223.     INX    H    ; BUMP MEM PTR
  224.     RET
  225. ;
  226. ;********************************************************************
  227. ;
  228. ;        STMAT - STORE BIT DIFFERENCES IN ERROR MATRIX
  229. ;
  230. ;********************************************************************
  231. ;
  232. STMAT    EQU    $
  233.     PUSH    PSW    ; SAVE CHAR
  234.     PUSH    H    ; SAVE H-L
  235.     PUSH    D    ;  AND
  236.     PUSH    B    ;   REST
  237.     MOV    B,A    ; MOVE BYTE READ TO B
  238.     MOV    C,M    ; MOVE BYTE WRITTEN TO C
  239.     MOV    A,H    ; GET H/O ERROR ADDR
  240.     PUSH    PSW    ; SAVE H/O
  241.     LHLD    ASTRT    ; STARTING TEST ADDR
  242.     MOV    A,H    ; GET H/O TO ACC
  243.     ANI    0FCH    ; STRIP L/O 2 BITS
  244.     MOV    H,A    ; REPLACE H/O
  245.     POP    PSW    ; RESTORE H/O ERR ADDR
  246.     SUB    H    ; 256-BYTE DIFF
  247.     ANI    0FCH    ; CLEAR L/O 2 BITS
  248.     MVI    H,0    ; SETUP H-L
  249.     MOV    L,A    ;  TO FORM
  250.     DAD    H    ;   K INDEX TO MATRIX
  251.     DAD    H    ;    AGAIN
  252.     LXI    D,MATRX    ; MATRIX START
  253.     DAD    D    ; FORM K INDEX
  254.     SHLD    MINDX    ; STORE MATRIX INDEX
  255.     LHLD    ERRCT    ; GET ERROR COUNT
  256.     INX    H    ;  PLUS 1
  257.     SHLD    ERRCT    ;   AND STORE IT BACK
  258.     LXI    D,8    ; BIT COUNT TO D
  259. STMA2    EQU    $
  260.     MOV    A,B    ; GET BYTE READ
  261.     RRC        ; SHIFT L/O INTO CARRY
  262.     MOV    B,A    ; RETURN BYTE READ
  263.     MOV    A,C    ; GET BYTE WRITTEN
  264.     JC    STMC1    ; BIT WAS SET IN READ - SEE IF WRITTEN
  265.     RRC        ; SHIFT BYTE WRITTEN L/O BIT INTO CARRY
  266.     MOV    C,A    ; RETURN BYTE WRITTEN
  267.     JNC    STMCO    ;  NOT CARRY, BIT MATCHES
  268.     JMP    STMBT    ;  CARRY, FLAG ERR
  269. STMC1    EQU    $
  270.     RRC        ; SHIFT WRITTEN BIT INTO CARRY
  271.     MOV    C,A    ; RETURN BYTE WRITTEN
  272.     JC    STMCO    ;  CARRY, BIT MATCHES
  273. STMBT    EQU    $
  274.     PUSH    D    ; SAVE ERR CTR
  275.     MVI    H,0    ; SETUP
  276.     MOV    L,E    ;  H-L
  277.     DCR    L    ; TAKE BIT COUNT - 1
  278.     DAD    H    ;  * 2
  279.     XCHG        ; SWAP TO D-E
  280.     LHLD    MINDX    ; MATRIX K INDEX
  281.     DAD    D    ;  DISPLACE BIT LOC
  282.     MOV    E,M    ; GET L/O OF ERROR CTR
  283.     INX    H    ; BUMP PTR
  284.     MOV    D,M    ; GET H/O 
  285.     INX    D    ; INCR DBL CTR
  286.     MOV    M,D    ; REPLACE H/O
  287.     DCX    H    ; DECR MEM PTR
  288.     MOV    M,E    ; REPLACE L/O
  289.     POP    D    ; RESTORE D-E
  290. ;
  291. STMCO    EQU    $
  292.     DCR    E    ; MINUS BIT COUNTER
  293.     JNZ    STMA2    ;  LOOP TILL ALL BITS TESTED
  294.     POP    B    ; RESTORE
  295.     POP    D    ;  ALL
  296.     POP    H    ;   REGS
  297.     POP    PSW    ;    AND CHAR
  298.     RET
  299. ;
  300. ;********************************************************************
  301. ;
  302. ;        PMSG1 - TYPE VERSION MESSAGE AND INSTRUCTIONS
  303. ;
  304. ;********************************************************************
  305. ;
  306. PMSG1    EQU    $
  307.     LXI    H,MSG1    ; GET VERSION MESSAGE
  308.     CALL    LINE    ; TYPE LINE
  309.     RET
  310. ;
  311. MSG1    DB    0DH
  312.     DB    'WTP&A MNEMONIC  - VERSION 2.0',0DH
  313.     DB    0DH
  314.     DB    'ANY MEMORY FROM 1000H TO FFFFH CAN BE TESTED.',0DH
  315.     DB    'TEST WILL RUN CONTINUOUSLY '
  316.     DB    'UNTIL A KEY IS STRUCK.',0DH
  317.     DB    'TURN ON S.S. 5 TO GET DETAILED ERROR LIST;',0DH
  318.     DB    ' S.S. 4 TO DO SUPER-SLOW TEST.',0DH
  319.     DB    0DH
  320.     DB    'WHEN A KEY IS STRUCK, ALL CUMULATIVE ERRORS',0DH
  321.     DB    ' WILL BE SUMMARIZED BY BIT POSITION',0DH
  322.     DB    ' WITHIN 1K BOUNDARIES.',0DH
  323.     DB    0DH
  324.     DB    '(ALL INPUTS AND OUTPUTS ARE IN HEX.)',0DH
  325.     DB    0DH
  326.     DB    00
  327. ;
  328. ;********************************************************************
  329. ;
  330. ;        PMSGS - PRINT STARTING ADDR REQ MSG
  331. ;
  332. ;********************************************************************
  333. ;
  334. PMSGS    EQU    $
  335.     LXI    H,MSGS    ; GET START ADDR REQ MSG
  336.     CALL    LINE    ; TYPE LINE
  337.     RET
  338. ;
  339. MSGS    DB    'START ADDR (HEX) ?',0DH,00
  340. ;
  341. ;********************************************************************
  342. ;
  343. ;        PMSGE - TYPE ENDING ADDR REQ MSG
  344. ;
  345. ;********************************************************************
  346. ;
  347. PMSGE    EQU    $
  348.     LXI    H,MSGE    ; GET ENDING ADDR REQ MSG
  349.     CALL    LINE    ; TYPE LINE
  350.     RET
  351. ;
  352. MSGE    DB    'END ADDR (HEX) ?',0DH,00
  353. ;
  354. ;********************************************************************
  355. ;
  356. ;        LINE - TYPE A LINE TERMINATED BY X'00'
  357. ;
  358. ;********************************************************************
  359. ;
  360. LINE    EQU    $
  361.     MOV    A,M    ; GET CHAR FROM MSG
  362.     CPI    00    ; Q. MSG END?
  363.     JZ    LINEX    ;  YUP, WRAP UP
  364.     CALL    TYPE    ;  ELSE, TYPE CHAR
  365.     INX    H    ; BUMP PTR
  366.     JMP    LINE    ;   LOOP TILL MSG END
  367. ;
  368. LINEX    EQU    $
  369.     RET
  370. ;
  371. ;********************************************************************
  372. ;
  373. ;        GTSTA - GET MEMORY STARTING ADDRESS
  374. ;
  375. ;********************************************************************
  376. ;
  377. GTSTA    EQU    $
  378.     CALL    PMSGS    ; SEND STARTING REQ MSG
  379.     CALL    RDADR    ; READ ADDR FROM CONSOLE
  380.     JC    GTSTA    ;  CARRY=ERROR, SO REPROMPT
  381.     CALL    PACKA    ; PACK ADDR INTO ADDRH
  382.     LHLD    ADDRH    ; GET PACKED ADDR
  383.     SHLD    ASTRT    ;  SAVE IT IN STARTING ADDR
  384.     MOV    A,H    ; GET H/O OF START ADDR
  385.     CPI    STAKH    ; TEST TO STACK ADDR
  386.     RET
  387. ;
  388. ;********************************************************************
  389. ;
  390. ;        GTEND - GET ENDING ADDRESS
  391. ;
  392. ;********************************************************************
  393. ;
  394. GTEND    EQU    $
  395.     CALL    PMSGE    ; SEND ENDING REQ MSG
  396.     CALL    RDADR    ; READ ADDR FROM CONSOLE
  397.     JC    GTEND    ;  CARRY=ERROR, SO REPROMPT
  398.     CALL    PACKA    ; PACK ADDR INTO ADDRH
  399.     LHLD    ADDRH    ; GET PACKED ADDR
  400.     SHLD    AEND    ;  SAVE IT IN ENDING ADDR
  401.     XCHG        ; SWAP TO D-E
  402.     LHLD    ASTRT    ; GET STARTING ADDR TO H-L
  403.     MOV    A,D    ; GET H/O OF ENDING ADDR
  404.     CMP    H    ; TEST TO H/O OF START
  405.     RC        ;  LT, ERROR
  406.     RNZ        ;  NOT ZERO, GO ON
  407.     MOV    A,E    ; GET L/O OF END
  408.     CMP    L    ; TEST TO L/O OF START
  409.     RC        ;  LT, ERROR
  410.     ORA    A    ; CLEAR CARRY
  411.     RET
  412. ;
  413. ;********************************************************************
  414. ;
  415. ;        RDADR - READ 4-BYTE ADDRESS FROM CONSOLE,
  416. ;            CONVERT IT TO HEX AND STORE IT.
  417. ;
  418. ;********************************************************************
  419. ;
  420. RDADR    EQU    $
  421.     LXI    H,NRAND    ; RANDOMLY CREATE NRAND
  422.     LXI    D,ADDRA    ; ADDR TO FILL
  423.     MVI    B,4    ; CHAR COUNT
  424. ;
  425. RDSTA    EQU    $
  426.     CALL    KSTAT    ; TEST KYBD STATUS
  427.     JC    RDBYT    ;  CARRY= CHAR READY
  428.     INR    M    ;  ELSE, ADD TO NRAND DIGIT
  429.     JMP    RDSTA    ;  LOOP TILL CHAR
  430. ;
  431. RDBYT    EQU    $
  432.     CALL    KEYIN    ; READ CHAR
  433.     CALL    TESTK    ; TEST VALIDITY
  434.     JC    RDERR    ;  NG, RESTART
  435.     STAX    D    ;  OK, STORE CHAR
  436.     INX    D    ; BUMP ADDRA PTR
  437.     INX    H    ;  AND NRAND PTR
  438.     DCR    B    ; MINUS LTH COUNTER
  439.     JNZ    RDSTA    ;  LOOP TILL DONE
  440.     MVI    A,0DH    ; CARR RTN
  441.     CALL    TYPE    ;  TYPE IT
  442.     RET
  443. ;
  444. RDERR    EQU    $
  445.     PUSH    H    ; SAVE H-L (NRAND DIGIT)
  446.     LXI    H,MSGKE    ; GET ERR MSG ADDR
  447.     CALL    LINE    ; TYPE LINE
  448.     POP    H    ; RESTORE H-L
  449.     STC        ; SHOW ERROR
  450.     RET
  451. ;
  452. MSGKE    DB    0DH,'YOU WANTA TRY THAT AGAIN?',0DH,00
  453. ;
  454. ;********************************************************************
  455. ;
  456. ;        TESTK - TEST KEYIN CHARACTER.
  457. ;            IF CTL-C, DO COLD BOOT
  458. ;
  459. ;********************************************************************
  460. ;
  461. TESTK    EQU    $
  462.     CPI    03H    ; CTL-C?
  463.     JZ    EXIT    ;  YUP, GET OUT
  464.     CPI    '0'    ; NUMERIC
  465.     JC    TSKNG    ;  NOPE, ERR
  466.     CPI    '9'+1    ; REALLY NUMERIC?
  467.     JNC    TSKAF    ;  NO, TEST A-F
  468.     SUI    30H    ; ADJUST TO BINARY
  469.     ORA    A    ; RESET CARRY
  470.     RET
  471. ;
  472. TSKAF    EQU    $
  473.     CPI    'A'    ; TEST "A"
  474.     JC    TSKNG    ;  LT, ERR
  475.     CPI    'F'+1    ; TEST "F"
  476.     JNC    TSKNG    ;  GT F, ERR
  477.     SUI    37H    ; SUBTRACT 55
  478.     ORA    A    ; RESET CARRY
  479.     RET
  480. ;
  481. TSKNG    EQU    $
  482.     STC
  483.     RET
  484. ;
  485. ;********************************************************************
  486. ;
  487. ;        PACKA - PACK ADDRESS KEYED-IN
  488. ;
  489. ;********************************************************************
  490. ;
  491. PACKA    EQU    $
  492.     LXI    H,ADDRA    ; GET PARTIALLY-CONVERTED ADDR
  493.     CALL    PACKB    ; PACK A BYTE
  494.     MOV    D,A    ; PUT IT OVER THERE FOR THE NONCE
  495.     CALL    PACKB    ; PACK 2ND BYTE
  496.     MOV    E,A    ; COMBINE
  497.     XCHG        ;  THEM INTO H-L
  498.     SHLD    ADDRH    ; SAVE THEM IN ADDRH
  499.     RET
  500. ;
  501. PACKB    EQU    $
  502.     MOV    A,M    ; GET CHAR FROM INPUT
  503.     RLC        ; ROTATE
  504.     RLC        ;  IT
  505.     RLC        ;   TO
  506.     RLC        ;    H/O
  507.     ANI    0F0H    ; CLEAR L/O
  508.     MOV    B,A    ; SAVE IT IN B
  509.     INX    H    ; BUMP MEM PTR
  510.     MOV    A,M    ; GET NEXT CHAR
  511.     ORA    B    ;  OR ON H/O FROM B
  512.     INX    H    ;  BUMP MEM PTR AGAIN
  513.     RET
  514. ;
  515. ;********************************************************************
  516. ;
  517. ;        RANDS - SAVE RANDOM NUMBER FOR LATER RESTORATION
  518. ;
  519. ;********************************************************************
  520. ;
  521. RANDS    EQU    $
  522.     LXI    H,NRAND+3    ; PT TO L/O OF 4-BYTE RANDOM NUMBER
  523.     MVI    A,01        ; ENSURE
  524.     ORA    M        ;  THAT L/O OF NRAND
  525.     MOV    M,A        ;   ENDS IN 1
  526.     LXI    D,NRNDS+3    ;  POINT D TO RAND SAVE
  527.     JMP    RNDS2        ; GO TO COMMON MOVE RTN
  528. ;
  529. RANDR    EQU    $
  530.     LXI    H,NRNDS+3    ; FROM ADDR = RAND SAVE
  531.     LXI    D,NRAND+3    ;  TO ADDR = RANDOM NUMBER
  532. ;
  533. RNDS2    EQU    $
  534.     MVI    B,4    ; COUNT = 4
  535. ;
  536. RNDSL    EQU    $
  537.     MOV    A,M    ; GET CHAR FROM SOURCE
  538.     STAX    D    ; COPY IT TO DEST
  539.     DCX    D    ; DECR
  540.     DCX    H    ;  BOTH PTRS
  541.     DCR    B    ; MINUS COUNT
  542.     JNZ    RNDSL    ;  LOOP TILL DONE
  543.     RET
  544. ;
  545.     PAGE
  546. ;
  547. ;********************************************************************
  548. ;
  549. ;        DATA AREAS
  550. ;
  551. ;********************************************************************
  552. ;
  553. NRAND    DS    4    ; PSEUDO-RANDOM NUMBER
  554. NRNDS    DS    4    ; RAND SAVE AREA
  555. ;
  556. MLTPR    DW    0A5A5H    ; RANDOM MULTIPLIER
  557. ;
  558. PRDAD    DW    0    ; PARTIAL PRODUCT A*D
  559. PRDBD    DW    0    ;   "        "    B*D
  560. PRDBC    DW    0    ;   "        "    B*C
  561. ;
  562. ADDRA    DS    4    ; ADDR INPUT
  563. ADDRH    DS    2    ; HEX EQUIV. OF ADDRA
  564. ;
  565. ASTRT    DS    2    ; HEX STARTING ADDR
  566. AEND    DS    2    ; HEX ENDING ADDR
  567. ATEST    DS    2    ; HEX TEST ADDR FOR "SLOW"
  568. ;
  569. MINDX    DW    0    ; K INDEX TO ERROR MATRIX
  570. ;
  571. PASSC    DW    0    ; PASS COUNTER
  572. ERRCT    DW    0    ; ERROR COUNTER
  573. ;
  574.     DS    2
  575. MATRX    DS    1024    ; ERROR MATRIX (64K * 16)
  576.     DS    2
  577. ;
  578.     PAGE
  579. ;
  580. ;********************************************************************
  581. ;
  582. ;        GENERATE RANDOM BYTE
  583. ;
  584. ;********************************************************************
  585. ;
  586. RANDB    EQU    $
  587.     PUSH    D    ; SAVE
  588.     PUSH    H    ;   REGS
  589.     LDA    MLTPR+1    ; GET MULTIPLIER L/O
  590.     MOV    C,A    ;  SAVE IN C
  591.     LDA    NRAND+3    ; GET NRAND L/O
  592.     MOV    B,A    ;  SAVE IN B
  593.     CALL    MULT    ; GET 16-BIT PRODUCT IN H-L
  594.     SHLD    PRDBD    ;  STORE 1ST PARTIAL PRODUCT
  595.     LDA    MLTPR+1    ; GET MULTIPLIER H/O
  596.     MOV    C,A    ;  SAVE IN C
  597.     LDA    NRAND+2    ; GET NRAND DIG
  598.     MOV    B,A    ;  SAVE IN B
  599.     CALL    MULT    ; DO MULTIPLICATION
  600.     SHLD    PRDBC    ;  SAVE PARTIAL PRODUCT
  601.     LDA    MLTPR    ; GET MULTIPLIER L/O
  602.     MOV    C,A    ;  SAVE IN C
  603.     LDA    NRAND+3    ; GET NRAND L/O
  604.     MOV    B,A    ;  SAVE IN B
  605.     CALL    MULT    ; DO MULTIPLICATION
  606.     SHLD    PRDAD    ;  SAVE 3RD PARTIAL PROD
  607.     LDA    PRDBD    ; GET NEW L/O DIGIT
  608.     STA    NRAND+3    ;  UPDATE NRAND L/O
  609.     LXI    H,0    ; GET CLEAR SUM
  610.     MVI    B,0    ; CLEAR H/O OF ADDEND
  611.     LDA    PRDBD+1    ; GET H/O OF PROD BD
  612.     MOV    C,A    ;  TO L/O OF ADDEND
  613.     DAD    B    ; ADD INTO SUM
  614.     LDA    PRDBC    ; GET L/O OF PROD BC
  615.     MOV    C,A    ;  TO L/O OF ADDEND
  616.     DAD    B    ; ADD INTO SUM
  617.     LDA    PRDAD    ; GET L/O OF PROD AD
  618.     MOV    C,A    ;  TO L/O OF ADDEND
  619.     DAD    B    ; ADD INTO SUM
  620.     MOV    A,L    ; GET L/O OF SUM
  621.     STA    NRAND+2    ; UPDATE NRAND TO NEW VALUE
  622.     POP    H    ; RESTORE
  623.     POP    D    ;  REGS
  624.     RET
  625. ;
  626. ;********************************************************************
  627. ;
  628. ;        MULT B * C = PROD IN H-L
  629. ;
  630. ;********************************************************************
  631. ;
  632. MULT    EQU    $
  633.     PUSH    D    ; SAVE D-E
  634.     MOV    A,B    ; COPY MULTIPLICAND TO A
  635.     MVI    B,0    ; CLEAR UPPER ADDEND
  636.     LXI    H,0    ; INIT PRODUCT TO ZERO
  637.     MVI    D,8    ; MULTIPLIER BIT COUNT
  638. MULT2    EQU    $
  639.     DAD    H    ; SHIFT PRODUCT LEFT
  640.     RLC        ; MULTIPLIER BIT TO CARRY
  641.     JNC    MULTC    ;  SKIP IF BIT ZERO
  642.     DAD    B    ;  ELSE, ADD MPCND TO PARTIAL PRODUCT
  643. MULTC    EQU    $
  644.     DCR    D    ; DECR BIT COUNT
  645.     JNZ    MULT2    ;  LOOP TILL DONE
  646.     POP    D    ; RESTORE D-E
  647.     RET
  648. ;
  649. ;********************************************************************
  650. ;
  651. ;        PRMAT - PRINT ERROR BIT MATRIX
  652. ;
  653. ;********************************************************************
  654. ;
  655. PRMAT    EQU    $
  656.     CALL    PRTPASS    ; PRINT PASS COUNT
  657.     LHLD    ERRCT    ; GET ERROR COUNT
  658.     MOV    A,H    ; GET H/O
  659.     ORA    A    ; Q. 0?
  660.     JNZ    PRMAH    ;  NO, GO THRU MATRIX
  661.     MOV    A,L    ; GET L/O
  662.     ORA    A    ; Q. ZERO?
  663.     JZ    PRMAX    ;  YES, BYPASS MATRIX SEARCH
  664. PRMAH    EQU    $
  665.     LXI    H,MSGBH    ; GET BIT ERR MSG HEADER
  666.     CALL    LINE    ;  TYPE IT
  667.     LHLD    ASTRT    ; GET STARTING ADDR
  668.     MOV    A,H    ; GET H/O
  669.     ANI    0FCH    ; MASK OFF L/O 2 BITS
  670.     MOV    H,A    ;  AND MOVE IT BACK
  671.     XCHG        ;  MOVE TO D-E
  672.     LXI    H,MATRX    ; POINT TO ERROR MATRIX
  673.     MVI    B,64    ; COUNT OF K'S TO SEARCH
  674. PRMA3    EQU    $
  675.     MVI    C,8    ; # OF BIT COUNTERS PER K
  676.     PUSH    H    ; SAVE CURRENT K INDEX TO MATRIX
  677. PRMA4    EQU    $
  678.     MOV    A,M    ; GET BIT COUNTER
  679.     ORA    A    ; Q. ZERO?
  680.     JNZ    PRMA5    ;  NO, MUST PRINT THIS K
  681.     INX    H    ;  ELSE, BUMP TO NEXT BIT CTR
  682.     MOV    A,M    ; GET H/O OF BIT CTR
  683.     ORA    A    ; TEST ZERO
  684.     JNZ    PRMA5    ;  NO, PRINT K
  685.     INX    H    ;  YES, BUMP MEM PTR
  686.     DCR    C    ; MINUS BIT COUNTER
  687.     JNZ    PRMA4    ;  NOT DONE TESTING THIS K, LOOP
  688.     JMP    PRMA7    ;  ELSE, TRY NEXT K
  689. PRMA5    EQU    $
  690.     POP    H    ; RESTORE STARTING K INDEX
  691.     MVI    C,8    ; RESTART BIT COUNTER
  692.     XCHG        ; GET CURR K ADDR
  693.     PUSH    H    ;  SAVE IT
  694.     MVI    L,0    ; PRINT K ADDR ON EVEN BOUNDARY
  695.     MVI    A,' '    ; BLANK FOR SPACING
  696.     CALL    TYPE    ;  TYPE IT
  697.     CALL    TYPEB    ; TYPE IT
  698.     LXI    H,MSG2B    ; 2 BLANKS
  699.     CALL    LINE    ;  TYPE THEM
  700.     POP    H    ; RESTORE K ADDR
  701.     XCHG        ;  THEN SWAP BACK
  702. PRMA6    EQU    $
  703.     PUSH    D    ; SAVE TARGET ADDR
  704.     MOV    E,M    ; GET 1ST BYTE TO E
  705.     INX    H    ; BUMP MEM PTR
  706.     MOV    D,M    ; GET 2ND BYTE
  707.     XCHG        ; SWAP TO H-L
  708.     CALL    TYPEB    ; TYPE CTR AS THO ADDR
  709.     XCHG        ; SWAP BACK
  710.     POP    D    ; RESTORE D-E
  711.     INX    H    ; BUMP MEM PTR
  712.     DCR    C    ; MINUS COUNT
  713.     JNZ    PRMA6    ;  LOOP TILL DONE
  714.     MVI    A,0DH    ; CARR RTN
  715.     CALL    TYPE    ; TYPE IT
  716.     JMP    PRMA8    ;  AND GO TEST NEXT MATRIX LVL
  717. ;
  718. PRMA7    EQU    $
  719.     POP    H    ; RESTORE H-L
  720.     PUSH    B    ; SAVE COUNTERS
  721.     LXI    B,16    ; GET OFFSET TO NEXT K
  722.     DAD    B    ; BUMP H-L
  723.     POP    B    ; RESTORE COUNTERS
  724. PRMA8    EQU    $
  725.     DCR    B    ; MINUS K COUNTER
  726.     JZ    PRMAX    ; ZERO, DONE
  727.     XCHG        ; GET START ADDR
  728.     PUSH    B    ; SAVE BIT COUNTERS
  729.     LXI    B,400H    ; GET K BOUNDARY
  730.     DAD    B    ; ADJUST START ADDR
  731.     XCHG        ; SWAP BACK
  732.     POP    B    ; RESTORE BIT COUNTERS
  733.     JMP    PRMA3    ;  LOOP TILL DONE
  734. ;
  735. PRMAX    EQU    $
  736.     RET
  737. ;
  738. MSGBH    DB    'K ADDR   B7   B6   B5   B4'
  739.     DB    '   B3   B2   B1   B0'
  740.     DB    0DH,00
  741. ;
  742. ;********************************************************************
  743. ;
  744. ;        PRTPASS - PRINT PASS COUNTER AND TOTAL ERRORS
  745. ;
  746. ;********************************************************************
  747. ;
  748. PRTPASS    EQU    $
  749.     LXI    H,MSGPC    ; GET PASS COUNT MSG ADDR
  750.     CALL    LINE    ; TYPE IT
  751.     LHLD    PASSC    ; GET PASS COUNTER
  752.     CALL    TYPEB    ;  TYPE IT
  753.     LXI    H,MSGER    ; ERROR COUNT MESSAGE
  754.     CALL    LINE    ; TYPE LINE
  755.     LHLD    ERRCT    ; GET ERROR COUNTER
  756.     CALL    TYPEB    ;  TYPE COUNT OF ERRORS
  757.     MVI    A,0DH    ; CARR RTN
  758.     CALL    TYPE    ;  END LINE
  759.     RET
  760. ;
  761. MSGPC    DB    'PASSES COMPLETED = ',00
  762. MSGER    DB    '; COUNT OF ERROR BYTES = ',00
  763.     DB    00
  764. ;
  765. ;********************************************************************
  766. ;
  767. ;        TYPEH - TYPE A BYTE IN 2-DIGIT HEX
  768. ;
  769. ;********************************************************************
  770. ;
  771. TYPEH    EQU    $
  772.     PUSH    B    ; SAVE COUNT
  773.     MOV    B,A    ; SAVE CHAR IN B
  774.     ANI    0F0H    ; STRIP L/O
  775.     RRC        ; SHIFT
  776.     RRC        ;  TO
  777.     RRC        ;   L/O
  778.     RRC        ;    4 BITS
  779.     CALL    TYPHH    ; TYPE HEX
  780.     MOV    A,B    ; GET CHAR BACK
  781.     ANI    0FH    ; NOW STRIP H/O
  782.     CALL    TYPHH    ; TYPE HEX
  783.     POP    B    ; RESTORE COUNT
  784.     RET
  785. ;
  786. TYPHH    EQU    $
  787.     ADI    90H    ; DO
  788.     DAA        ;  HEX TO ASCII
  789.     ACI    40H    ;   ADJUSTMENT
  790.     DAA        ;    TRICK
  791.     CALL    TYPE    ; TYPE ADJUSTED HEX CHAR
  792.     RET
  793. ;
  794. ;********************************************************************
  795. ;
  796. ;        QUICK - DO QUICK TEST OF MEMORY RANGE
  797. ;            USING X'FF' AND X'00'
  798. ;
  799. ;********************************************************************
  800. ;
  801. QUICK    EQU    $
  802.     MVI    C,0FFH    ; USE FOXES FIRST
  803.     CALL    QTEST    ; DO QUICK TEST
  804.     CALL    KSTAT    ; TEST KYBD READY
  805.     RC        ;  YES, EXIT
  806.     MVI    C,00H    ; NOW USE ZEROS
  807.     CALL    QTEST    ; DO QUICK TEST AGAIN
  808.     RET
  809. ;
  810. QTEST    EQU    $
  811.     LHLD    AEND    ; GET END ADDR TO H-L
  812.     XCHG        ;  SWAP IT TO D-E
  813.     LHLD    ASTRT    ; GET STARTING ADDR
  814. QTES2    EQU    $
  815.     CALL    KSTAT    ; TEST KYBD READY
  816.     RC        ;  YES, EXIT
  817.     MOV    A,C    ; GET STORING VALUE
  818.     CALL    STNDX    ; STORE CHAR IN MEM, BUMP INDEX
  819.     JC    QTES2    ;  LT, MORE
  820.     LHLD    ASTRT    ; GET START ADDR AGAIN
  821. QTES3    EQU    $
  822.     CALL    KSTAT    ; TEST KYBD READY
  823.     RC        ;  YES, EXIT
  824.     MOV    A,C    ; GET STORED VALUE
  825.     MOV    B,M    ;  GET CHAR FROM MEM
  826.     CMP    B    ;  TEST EACH DIGIT AGAINST EXPECTED
  827.     JZ    QTES4    ;  EQ, ON
  828.     CALL    TYPEA    ;  ELSE, TYPE ERR VALS
  829.     CALL    STMAT    ; STORE BIT ERRORS IN MATRIX
  830. QTES4    EQU    $
  831.     CALL    INDEX    ; BUMP INDEX
  832.     JC    QTES3    ;  LT, AGAIN
  833.     RET
  834. ;
  835. ;********************************************************************
  836. ;
  837. ;        SLOW - DO SUPER-SLOW MEM TEST.
  838. ;            FIRST, MARCH A 1 BIT THRU A FLD OF ZEROS,
  839. ;            TESTING EACH OTHER BYTE IN THE RANGE FOR
  840. ;            A CHANGE.
  841. ;            THEN, MARCH A ZERO BIT THRU A FLD OF ONES,
  842. ;            TESTING AS ABOVE.
  843. ;
  844. ;********************************************************************
  845. ;
  846. SLOW    EQU    $
  847.     IN    255    ; READ SENSE SWS
  848.     ANI    SSWS    ; TEST SLOW SELECTED
  849.     RZ        ;  NO, EXIT
  850.     MVI    B,00    ; ZEROS TO MEM FOR 1ST PHASE
  851.     CALL    SETMEM    ;  CLEAR ADDR SPACE
  852.     MVI    C,01    ; BIT REG
  853. SLOW2    EQU    $
  854.     CALL    SLOWT    ; DO SLOW TEST
  855.     CALL    KSTAT    ; TEST FOR INTERRUPTION
  856.     RC        ;  YES, GO
  857.     MOV    A,C    ; GET BIT REG
  858.     RLC        ; SHIFT BIT
  859.     JC    SLOW3    ; WHEN BIT REACHES CARRY, DONE
  860.     MOV    C,A    ; REPLACE BIT
  861.     JMP    SLOW2    ;  NOT DONE, CONTINUE
  862. SLOW3    EQU    $
  863.     MVI    B,0FFH    ; ALL ONES
  864.     CALL    SETMEM    ;  TO ADDR SPACE
  865.     MVI    C,0FEH    ; BIT REG TO A L/O ZERO
  866. SLOW4    EQU    $
  867.     CALL    SLOWT    ; DO SLOW TEST
  868.     CALL    KSTAT    ; TEST FOR INTERRUPTION
  869.     RC        ;  YES, GO
  870.     MOV    A,C    ; GET BIT REG
  871.     RLC        ; SHIFT 0 BIT LEFTWARDS
  872.     JNC    SLOW5    ; WHEN ZERO REACHES CARRY, DONE
  873.     MOV    C,A    ; REPLACE BIT REG
  874.     JMP    SLOW4    ;  NOT DONE, CONTINUE
  875. ;
  876. SLOW5    EQU    $
  877.     MVI    B,08    ; COUNT OF BELLS
  878. SLOWB    EQU    $
  879.     MVI    A,07H    ; BELL CHAR
  880.     CALL    TYPE    ;  SOUND IT
  881.     CALL    KSTAT    ; TEST KYBD READY
  882.     JC    SLOWX    ;  YES, CLEANUP
  883.     LXI    H,0    ; LONG WAIT
  884. SLOW6    EQU    $
  885.     DCR    L    ;
  886.     JNZ    SLOW6    ;
  887.     DCR    H    ;
  888.     JNZ    SLOW6    ;
  889.     DCR    B    ; MINUS BELL COUNT
  890.     JNZ    SLOWB    ;  NOT DONE, RING AGAIN
  891. SLOWX    EQU    $
  892.     MVI    A,0DH    ; CR
  893.     CALL    TYPE    ; TYPE IT
  894.     RET
  895. ;
  896. SLOWT    EQU    $
  897.     LHLD    ASTRT    ; GET STARTING ADDR FOR TEST
  898.     SHLD    ATEST    ; STORE IT AT TEST ADDR
  899. SLOWT2    EQU    $
  900.     LHLD    ATEST    ; GET TEST ADDR
  901.     MOV    M,C    ; STORE BIT REG AT TEST BYTE
  902.     LHLD    AEND    ; ENDING ADDR TO H-L
  903.     XCHG        ;  SWAP IT TO D-E
  904.     LHLD    ASTRT    ; GET STARTING ADDR
  905. SLOWS2    EQU    $
  906.     MOV    A,M    ; GET BYTE FROM MEM
  907.     CMP    B    ; TEST TO EXPECTED
  908.     JZ    SLOWS5    ;  EQ, ON
  909.     PUSH    B    ; SAVE B-C
  910.     MOV    C,A    ;  SAVE CHAR READ (ERROR)
  911.     XCHG        ; CURRENT ADDR TO D-E
  912.     LHLD    ATEST    ; GET TEST ADDR TO H-L
  913.     MOV    A,H    ; GET H/O ADDR OF TEST BYTE
  914.     CMP    D    ;  TEST TO D
  915.     JNZ    SLOWS3    ;   NOT EQ, ON
  916.     MOV    A,L    ; GET L/O
  917.     CMP    E    ;  TEST L/O OF TEST ADDR
  918.     JNZ    SLOWS3    ;  NOT EQUAL, PRT ERROR
  919.     JMP    SLOWS4    ;  AND BYPASS ERROR PRT
  920. SLOWS3    EQU    $
  921.     MOV    A,B    ; SWAP EXPECTED TO ACC
  922.     MOV    B,C    ; INSERT VALUE READ IN ERROR
  923.     CALL    TYPEA    ; TYPE ADDR
  924.     CALL    STMAT    ; STORE IN ERR MATRIX
  925. SLOWS4    EQU    $
  926.     POP    B    ; RESTORE B-C
  927.     LHLD    AEND    ; GET ENDING ADDR
  928.     XCHG        ; CURRENT ADDR BACK TO H-L
  929. SLOWS5    EQU    $
  930.     INX    H    ; BUMP MEM PTR
  931.     MOV    A,H    ; GET H/O OF CURR ADDR
  932.     CMP    D    ; TEST TO H/O OF END ADDR
  933.     JC    SLOWS2    ;  LT, CONTINUE
  934.     MOV    A,L    ; GET L/O OF CURR ADDR
  935.     CMP    E    ; TEST TO L/O OF END ADDR
  936.     JC    SLOWS2    ;  LT, ON
  937. SLOWSX    EQU    $
  938.     CALL    KSTAT    ; TEST FOR INTERRUPTION
  939.     RC        ;  YES, GO
  940.     LHLD    ATEST    ; GET TEST ADDR
  941.     MOV    M,B    ; REPLACE TEST BYTE
  942.     INX    H    ; BUMP TEST ADDR
  943.     SHLD    ATEST    ;  AND RESAVE IT
  944.     XCHG        ; SWAP TEST ADDR TO D-E
  945.     LHLD    AEND    ; GET END ADDR TO H-L
  946.     MOV    A,D    ; GET H/O OF TEST ADDR
  947.     CMP    H    ; TEST TO H/O OF END ADDR
  948.     JC    SLOWT2    ;  LT, ON
  949.     JNZ    SLOWTX    ;  NOT EQ, DONE
  950.     MOV    A,E    ; GET L/O OF TEST ADDR
  951.     CMP    L    ;  TEST TO L/O OF END ADDR
  952.     JC    SLOWT2    ;  LT, ON
  953.     JZ    SLOWT2    ;  EQ, 1 MORE TIME
  954. SLOWTX    EQU    $
  955.     RET
  956. ;
  957. ;********************************************************************
  958. ;
  959. ;        SETMEM - SET ADDR SPACE TO VALUE IN B
  960. ;
  961. ;********************************************************************
  962. ;
  963. SETMEM    EQU    $
  964.     LHLD    AEND    ; GET ENDING ADDR
  965.     XCHG        ;  TO D-E
  966.     LHLD    ASTRT    ; GET STARTING ADDR
  967. SETM2    EQU    $
  968.     MOV    M,B    ; FILL MEM BYTE
  969.     CALL    INDEX    ; BUMP PTR
  970.     JC    SETM2    ;  LT, LOOP
  971.     RET
  972. ;
  973. ;********************************************************************
  974. ;
  975. ;        INIT - SETUP MATRIX
  976. ;
  977. ;********************************************************************
  978. ;
  979. INIT    EQU    $
  980.     LXI    H,MATRX    ; GET ERROR MATRIX ADDR
  981.     LXI    B,1024    ;  GET MATRIX LENGTH
  982.     XRA    A    ; GET ZERO
  983. INIT2    EQU    $
  984.     MOV    M,A    ; STORE ZERO IN ERROR MATRIX BYTE
  985.     INX    H    ; BUMP MEM PTR
  986.     DCR    C    ; MINUS L/O OF COUNT
  987.     JNZ    INIT2    ; INNER LOOP
  988.     DCR    B    ; MINUS COUNT
  989.     JNZ    INIT2    ;  LOOP TILL DONE
  990.     LXI    H,0    ; ZEROS TO
  991.     SHLD    PASSC    ;  PASS COUNTER
  992.     SHLD    ERRCT    ;   AND ERROR COUNTER
  993.     RET
  994. ;
  995. ;********************************************************************
  996. ;
  997. ;        TYPEA - TYPE ERROR ADDR, WROTE, READ
  998. ;
  999. ;********************************************************************
  1000. ;
  1001. TYPEA    EQU    $
  1002.     PUSH    PSW    ; SAVE CHAR 2B TYPED
  1003.     IN    255    ; READ SENSE SWS
  1004.     ANI    SSWD    ; TEST DETAIL LIST SENSE SW
  1005.     JZ    TYPAX    ;  YES, DON'T DETAIL ERRS
  1006.     PUSH    H    ; SAVE ADDR OF ERROR
  1007.     LHLD    ERRCT    ; GET ERROR COUNTER
  1008.     MOV    A,H    ; GET H/O
  1009.     ORA    A    ; Q. ZERO?
  1010.     JNZ    TYPA2    ;  NO, ALREADY PRINTED HEADER
  1011.     MOV    A,L    ; GET L/O
  1012.     ORA    A    ; Q. ZERO?
  1013.     JNZ    TYPA2    ;  NO, BYPASS
  1014.     LXI    H,MSGEH    ; GET ERROR HEADER MSG
  1015.     CALL    LINE    ;  TYPE IT
  1016. TYPA2    EQU    $
  1017.     POP    H    ; RESTORE ERROR ADDR
  1018.     CALL    TYPEB    ; CONVERT AND TYPE H-L
  1019.     PUSH    H    ; SAVE H-L AGAIN
  1020.     LXI    H,MSG2B    ; 2 BLANKS
  1021.     CALL    LINE    ;  TYPE IT
  1022.     POP    H    ; RESTORE H-L
  1023.     POP    PSW    ; GET CHAR
  1024.     PUSH    PSW    ;  RESAVE IT
  1025.     CALL    TYPEH    ; TYPE IT
  1026.     PUSH    H    ; SAVE H-L AGAIN
  1027.     LXI    H,MSG3B    ; 3 BLANKS
  1028.     CALL    LINE    ;  TYPE IT
  1029.     POP    H    ; RESTORE H-L
  1030.     MOV    A,B    ; GET CHAR READ
  1031.     CALL    TYPEH    ; TYPE IT
  1032.     MVI    A,0DH    ; CARR RTN
  1033.     CALL    TYPE    ;  SEND IT
  1034. TYPAX    EQU    $
  1035.     POP    PSW    ; RESTORE CHAR
  1036.     RET
  1037. ;
  1038. MSGEH    DB    'ADDR WROTE READ',0DH
  1039.     DB    00
  1040. MSG3B    DB    ' '
  1041. MSG2B    DB    '  ',00
  1042. ;
  1043. ;********************************************************************
  1044. ;
  1045. ;        TYPEB - TYPE 2-BYTE ADDRESS IN H-L
  1046. ;
  1047. ;********************************************************************
  1048. ;
  1049. TYPEB    EQU    $
  1050.     MOV    A,H    ; GET H/O OF ADDR
  1051.     CALL    TYPEH    ; TYPE IT
  1052.     MOV    A,L    ; GET L/O
  1053.     CALL    TYPEH    ;  TYPE IT
  1054.     MVI    A,' '    ; BLANK
  1055.     CALL    TYPE    ;  FOR SEPARATION
  1056.     RET
  1057. ;
  1058.     END
  1059.