TITLE 'CBIOS FOR CP/M 2.2' PAGE 60 ; CP/M BASIC INPUT/OUTPUT OPERATING SYSTEM (BIOS) ; TARBELL ELECTRONICS ; 2.2 VERSION OF 12-5-79 ; MODIFIED BY RICHARD B. KOLBLY ; 10-01-80 ; 10-31-80 ; ; THIS BIOS MODULE IS THE CPM V2.2 ; CBIOS. THIS BIOS READS SINGLE DENSITY ; DISK.. TRACK 0 = SINGLE DENSITY (IBM COMPATABLE) ; TRACKS 1 - 76 SINGLE DENSITY 52 SECTORS. ; ; THIS SECTION DEFINES THE I/O PORTS AND ; STATUS BITS. BY SETTING THE PROPER VALUES ; FOR THE EQU STATEMENTS, THE I/O MAY BE ; AUTOMATICALLY RECONFIGURED TO FIT MOST ; SITUATIONS. THE TRUE AND FALSE ONES ; CONTROL CONDITIONAL ASSEMBLIES OF DIFFERENT ; SECTIONS OF I/O ROUTINES TO FIT DIFFERENT ; INTERFACE REQUIREMENTS. TRUE EQU 0FFFFH ;DEFINE VALUE OF TRUE. FALSE EQU NOT TRUE ;DEFINE VALUE OF FALSE. ;*************************************************** ;*** THIS BEGINS THE AREA WHICH REQUIRES CHANGES *** ;*** FOR DIFFERENT CONSOLE I/O SYSTEMS *** ;*************************************************** MSIZE EQU 56 ;MEMORY SIZE IN KBYTES. NDISK EQU 2 ;DEFINES THE NUMBER DRIVES IN SYSTEM. CDATA EQU 0 ;USED TO CLEAR CONSOLE STATUS. HLAB EQU 0 ;8 FOR HD LD AT BEG OF SEEK. STPRAT EQU 3 ;RATE 1=6MS, 2=10MS, 3=20MS. ;******************************************************* ;*** THIS IS THE END OF THE AREA WHICH NORMALLY NEED *** ;*** BE CHANGED FOR MOST CONSOLE I/O SYSTEMS *** ;******************************************************* RDYLO EQU TRUE ;STATUS READY WHEN LOW. RDYHI EQU NOT RDYLO DISK EQU 0F8H ;DISK BASE ADDRESS. DCOM EQU DISK ;DISK COMMAND PORT. DSTAT EQU DISK ;DISK STATUS PORT. TRACK EQU DISK+1 ;DISK TRACK PORT. SECTP EQU DISK+2 ;DISK SECTOR PORT. DDATA EQU DISK+3 ;DISK DATA PORT. WAIT EQU DISK+4 ;DISK WAIT PORT. DCONT EQU DISK+4 ;DISK CONTROL PORT. RTCNT EQU 10 ;RETRY COUNT. IOBYTE EQU 3 ;ADDRESS OF I/O BYTE. FF EQU 0CH ;ASCII FORM FEED CHARACTER LF EQU 0AH ;ASCII LINE FEED CHARACTER CR EQU 0DH ;ASCII CARRIAGE RETURN ; ; VALUES OF I/O FUNCTIONS ; @CONIN EQU 0F803H ;GET CHARACTER FROM CONSOLE @READER EQU 0F806H ;GET CHARACTER FROM READER @CONOT EQU 0F809H ;WRITE TO CONSOLE DEVICE @PUNCH EQU 0F80CH ;WRITE TO PUNCH DEVICE @LIST EQU 0F80FH ;CHARACTER TO LIST DEVICE @CONST EQU 0F812H ;GET STATUS OF CONSOLE KEYBOARD @PRSTAT EQU 0F815H ;STATUS OF LIST DEVICE @PMSG EQU 0F818H ;PRINT MESSAGE IN (HL) TIL ZERO @ERROR EQU 0F81BH ;ERROR REPORTING ROUTINE ; CBASE EQU (MSIZE-20)*1024 ;BIAS FOR LARGER THAN 20K. CPMB EQU CBASE+3400H ;START OF CPM 2.2 BDOS EQU CPMB+806H ;START OF BDOS 2.2. BIOS EQU CPMB+1600H ;START OF CBIOS IO. CDISK EQU 4 ;LOCATION 4 IS CURRENT DISK. NSECTS EQU 17 ;NUMBER OF SECTORS IN IT. ORG CPMB+16 ; SMSG: DB 0DH,0AH,0DH,'SBMS/K6HIJ',0AH,0DH DB MSIZE/10+'0',MSIZE MOD 10+'0' DB 'K CP/M V2.2 of 10-31-80',0 ; ; BOOT ; THIS SECTION IS EXECUTED WHENEVER RESET AND RUN ; IS PUSHED, AFTER THE COLDSTART LOADER READS IN ; THE CPM SYSTEM. ; BOOT: LXI SP,80H ;SET STACK POINTER. JMP BOOTF ;FINISH BOOT. ORG BIOS-64 ;HIDE REST OF BOOT HERE. BOOTF: XRA A ;CLEAR SCRATCH AREA. STA CDISK ;SELECT DRIVE ZERO STA LATCH ;SET LATCH FOR DRIVE A. LXI H,IOBYTE ;POINT TO IOBYTE. MVI M,01H ;SET UP IOBYTE. MVI B,ENDZ-STARTZ ;GET LENGTH OF ZERO AREA. LXI H,STARTZ ;GET SCRATCH ADDRESS. BOOTL: MOV M,A ;PUT ZERO IN MEMORY. INX H ;INCREMENT POINTER. DCR B ;DECREMENT COUNTER. JNZ BOOTL ;LOOP TILL DONE. IN CDATA ;CLEAR CONSOLE STATUS. LXI H,SMSG ;POINT TO SIGN ON. PMSG1: MOV A,M ;GET A BYTE OF THE MESSAGE INX H ;BUMP MEMORY POINTER. ORA A ;IS IT A ZERO? JZ GOCPM ;YES, WE ARE DONE, JMP TO CPM. MOV C,A ;NOPE, PRINT MORE MESSAGE. CALL @CONOT ;USE THE CONOT ROUTINE. JMP PMSG1 ;AND LOOP TILL DONE. ORG BIOS ;START OF CBIOS STRUCTURE. ; ; I/O JUMP VECTOR ; THIS IS WHERE CPM CALLS WHENEVER IT NEEDS ; TO DO ANY INPUT/OUTPUT OPERATION. ; USER PROGRAMS MAY USE THESE ENTRY POINTS ; ALSO, BUT NOTE THAT THE LOCATION OF THIS ; VECTOR CHANGES WITH THE MEMORY SIZE. ; DMAENT: JMP BOOT ;FROM SBOOT LOADER,CHANGED FOR DMA. WBOOTE: JMP WBOOT ;FROM WARM BOOT. JMP @CONST ;CHECK CONSOLE KB STATUS. JMP @CONIN ;READ CONSOLE CHARACTER. JMP @CONOT ;WRITE CONSOLE CHARACTER. JMP LIST ;WRITE LISTING CHAR. JMP @PUNCH ;WRITE PUNCH CHAR. JMP @READER ;READ READER CHAR. JMP HOME ;MOVE DISK TO TRACK ZERO. JMP SELDSK ;SELECT DISK DRIVE. JMP SETTRK ;SEEK TO TRACK IN REG A. JMP SETSEC ;SET SECTOR NUMBER. JMP SETDMA ;SET DISK STARTING ADR. JMP READ ;READ SELECTED SECTOR. JMP WRITE ;WRITE SELECTED SECTOR. JMP @PRSTAT ;LIST STATUS CHECK. JMP SECTRAN ;SECTOR TRANSLATE ROUTINE. ; THIS SECTION DEFINES THE THE DISK PARAMETERS ; NOTE: ; IF YOU HAVE THE MACRO ASSEMBLER (MAC) FROM ; DIGITAL RESEARCH, YOU MAY ELIMINATE THIS SECTION ; STARTING AT **AA** TO **BB** AND USE THE MACRO ; FILE "DISKDEF" TO CUSTOM TAILOR YOUR SYSTEM TO ; ALLOW DIFFERENT TYPES OF DRIVES OR MORE THAN 4 ; DRIVES. ; ;**AA** ; DPBASE EQU $ ;BASE OF DISK PARAMETER BLOCK DPE0: DW XLT0,0000H ;TRANSLATE TABLE DW 0000H,0000H ;SCRATCH AREA DW DIRBUF,SDTAB+2 ;DIR BUFF, PARM BLOCK DW CSV0,ALV0 ;CHECK, ALLOC VECTORS ; DPE1: DW XLT1,0000H DW 0000H,0000H DW DIRBUF,DPB1 DW CSV1,ALV1 ; ;THE FOLLOWING DESCRIBES THE DISK PHYSICAL ;NATURE, SUCH AS SECTORS/TRACK,DIRECTORY SIZE. ;THE FOLLOWING TABLE DEFINES A SINGLE DENSITY DRIVE. ; SDTAB: EQU $ ;ONE OF 4 DISK PARM. BLOCKS DW XLT0 ;USE SINGLE DENSITY TRANSLATE TAB. DW 26 ;SECTORS/TRACK DB 3 ;BLOCK SHIFT DB 7 ;BLOCK MASK DB 0 ;EXTNT MASK DW 242 ;DISK SIZE - 1 DW 63 ;DIRECTORY MAX. DB 192 ;ALLOC0 DB 0 ;ALLOC1 DW 16 ;CHECK SIZE DW 2 ;NUMBER OF SYSTEM TRACKS ; ;SECTOR TRANSLATION TABLE ; XLT0 EQU $ ;START OF TRANS. TABLE DB 1,7,13,19,25 DB 5,11,17,23,3 DB 9,15,21,2,8 DB 14,20,26,6,12 DB 18,24,4,10,16,22 ; DPB1 EQU SDTAB+2 ;EQUIVALENT PARAMETERS XLT1 EQU XLT0 ;SAME TRANSLATE TABLE ; ;**BB** ; ; ; WARM-BOOT: READ ALL OF CPM BACK IN ; EXCEPT BIOS, THEN JUMP TO CCP. ; WBOOT: LXI SP,80H ;SET STACK POINTER. LDA CDISK ;SAVE DISK NUMBER. STA TEMP MVI C,0 ;SELECT DISK 0. CALL SELDSK CALL HOME ;MOVE TO TRACK ZERO. JNZ RDERR1 ;IF ERROR, PRINT MESSAGE. MVI D,NSECTS ;GET # SECTORS FOR CPM READ. LXI B,2 ;TRACK (B)=0, SECTOR (C)=2. LXI H,CPMB ;GET STARTING ADDRESS. RDBLK: MOV A,B ;GOTO TRACK IN B. CALL SEEK JNZ RDERR1 ;IF ERROR, PRINT MESSAGE. MOV A,C ;READ STARTING AT SECTOR IN C. CALL READ1 RBLK1: JNZ RDERR1 ;IF ERROR, PRINT MESSAGE. DCR D ;DECREMENT SECTOR COUNT. JZ ALDON ;ALL DONE WHEN ZERO. INR C ;INCREMENT SECTOR NUMBER. MOV A,C ;IF SECTOR NUMBER CPI 27 ; IS NOT 27, JC RBLK2 ; HOP OUT OF LOOP. MVI C,1 ;OTHERWISE, RESET SECTOR=1 INR B ; INCREMENT TRACK NUMBER, JMP RDBLK ; AND READ NEXT TRACK. ALDON: LDA TEMP ;RESTORE DISK NUMBER. STA CDISK JMP GOCPM ;GO BACK TO CPM. RBLK2: CALL READ2 ;READ ANOTHER TRACK. JMP RBLK1 GOCPM: ; ; SET UP JUMPS INTO CP/M IN LOWER MEMORY. ; MVI A,0C3H ;PUT JMP TO WBOOT STA 0 ;ADR AT ZERO. LXI H,WBOOTE SHLD 1 STA 5 LXI H,BDOS ;PUT JUMP TO BDOS SHLD 6 ;AT ADR 5,6,7. LXI H,80H ;SET DEFAULT DMA ADR. SHLD DMAADD LDA CDISK ;GET DISK NUMBER TO MOV C,A ;PASS TO CCP IN C. JMP CPMB ;JUMP TO CCP. ; ; LISTING ROUTINE - REQUIRED TO HANDLE FORMFEED CHARACTERS ; LIST: LDA IOBYTE ;GET STATUS ANI 40H ;SEE IF IT IS TTY JNZ @LIST ;IF NOT, NO SPECIAL HANDLING MOV A,C ;GET CHARACTER TO BE LISTED CPI FF ;IS IT A FORM FEED? JZ FFEED ;YES, DO A FORM FEED CPI LF ;IS IT LINE FEED? JNZ @LIST ;NO, SO LIST IT LIST1: LDA COUNT ;GET LINES COUNT INR A ;UP THE COUNT CPI 66 ;MAX LINES PER PAGE JNZ $+4 ;NOT MAX, CONTINUE XRA A ;ZERO COUNT STA COUNT ;SAVE FOR NEXT TIME JMP @LIST ;NOW SEND LF ; FFEED: LDA COUNT ;GET COUNT ORA A ;SET FLAGS RZ ;ZERO,MUST BE AT TOP OF FORM ALREADY MVI C,LF ;GET LINE FEED TO SEND CALL LIST1 ;SEND TO PRINTER JMP FFEED ;KEEP SENDING LF'S TIL TOP OF FORM ; ; SELECT DISK NUMBER ACCORDING TO REGISTER C. ; SELDSK: LXI H,0 ;SET UP FOR ERROR CODE MOV A,C ;GET NEW DRIVE. CPI NDISK ;CALLING UNDEFINED DRIVE ? RNC ;IF NO CY, H,L TELLS CPM YES. STA CDISK ;WE ARE OK, SAVE NEW DISK NUMB. LXI H,DISKNO ;GET OLD DRIVE NUMBER. SELMOR: MOV A,M ;GET OLD DISK NUMBER. MOV E,A ;PUT OLD DISK NO. IN D&E. MVI D,0 LXI H,TRTAB ;GET ADDRESS OF TRACK TABLE. PUSH H ;SAVE ADDRESS OF TRTAB. DAD D ;ADD DISK NO. TO ADDRESS. IN TRACK ;READ 1771 TRACK REGISTER. MOV M,A ;PUT INTO TABLE. MOV A,C ;GET NEW DISK NUMBER. MOV E,A ;PUT NEW DISK NO. IN D&E. POP H ;RESTORE ADDRESS OF TRTAB. DAD D ;ADD DISK NO. TO ADDRESS. MOV A,M ;GET NEW TRACK NUMBER. OUT TRACK ;PUT INTO 1771 TRACK REG. SELD1: MOV A,C ;UPDATE OLD DISK NUMBER. STA DISKNO CMA ADD A ;PUT BITS 1&2 AT 4&5. ADD A ADD A ADD A ORI 2 STA LATCH ;SAVE NEW LATCH CODE. ; ;SELECT DRIVE AS A FUNCTION OF H,L ; PARINDX:LHLD DISKNO ;LOAD DISK NUMBER AND ZERO BYTE LXI D,DPBASE ;POINT TO DISK PARM START. DAD H ;*2 DAD H ; *4 DAD H ; *8 DAD H ; *16 DAD D ;COMPUTE INDEX FOR THE DRIVE XRA A ;SET A = 0. RET ;RETURN FROM SELDSK. ; ; MOVE DISK TO TRACK ZERO. ; HOME: MVI C,0 ;SEEK TO TRACK ZERO. MVI A,0D0H ;RESTORE COMMAND OUT DCOM ;TELL CONTROLLER. ; ; SET TRACK NUMBER TO WHATEVER IS IN REGISTER C. ; ALSO PERFORM MOVE TO THE CORRECT TRACK (SEEK). SETTRK: PUSH H ;SAVE H&L. LHLD LATCH ;GET NEW & OLD LATCH. MOV A,L ;GET NEW LATCH. OUT DCONT ;SELECT DRIVE NOW. STA CLATCH ;REMEMBER CURRENT LATCH. CMP H ;IS NEW SAME AS OLD? MVI A,0FFH ;IF NOT, SET FLAG = FF. JNZ SFLAG CMA ;IF NEW = OLD, FLAG = 0. SFLAG: STA HLSF ;SET HEAD-LOAD/SELECT FLAG. POP H ;RESTORE H&L. MOV A,C ;GET NEW TRACK NUMBER. STA TRK ;UPDATE OLD WITH NEW. ; ; MOVE THE HEAD TO THE TRACK IN REGISTER A. ; SEEK: PUSH B ;SAVE B&C. MOV B,A ;SAVE DESTINATION TRACK. MVI A,RTCNT ;GET RETRY COUNT. STA SERCNT ;STORE IN ERROR COUNTER. PUSH PSW SRETRY: POP PSW IN TRACK ;READ PRESENT TRACK NO. CMP B ;SAME AS NEW TRACK NO.? JNZ NOTHR ;JUMP IF NOT THERE. THERE: POP B ;RESTORE B&C. RET ;RETURN FROM SEEK. NOTHR: ;DELAY LOOP TO ALLOW TUNNEL ;ERASE TO END DURING WRITE. ; MVI A,0D0H ;COUNT = 208 BUSY1: DCR A ;LOOP JNZ BUSY1 ; TILL = ZER0 MOV A,B ;RESTORE A FROM B. OUT DDATA ;TRACK TO DATA REGISTER. BUSY: IN DSTAT ;READ DISK STATUS. RRC ;LOOK AT BIT 0. JC BUSY ;WAIT TILL NOT BUSY. MVI A,14H+STPRAT+HLAB ;GET STEP RATE, DO OUT DCOM ;SEEK WITH VERIFY. IN WAIT ;WAIT FOR INTRQ. IN DSTAT ;READ STATUS. ANI 98H ;LOOK AT BITS. JZ THERE ;OK IF ZERO. PUSH PSW LDA SERCNT ;GET ERROR COUNT. DCR A ;DECREMENT COUNT. JZ DABRT STA SERCNT JMP SRETRY DABRT: POP PSW CALL TP1ERR POP B DABRT1: LXI D,DABORT CALL PRINT JMP ABORT TP1ERR: RLC PUSH PSW LXI D,MSG1 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG2 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG3 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG6 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG4 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG5 CC PRINT POP PSW RET ; ; SET DISK SECTOR NUMBER. ; SETSEC: MOV A,C ;GET SECTOR NUMBER. STA SECT ;PUT AT SECT # ADDRESS. RET ;RETURN FROM SETSEC. ; ;TRANSLATE THE SECTOR GIVEN B,C ;USING THE TRANSLATE TABLE ;GIVEN BY D,E ; SECTRAN: XCHG ;H,L = TRANS DAD B ;H,L = TRANS (SECTOR) MOV L,M ;L = TRANS (SECTOR) MVI H,0 ;CLEAR REG H RET ;H,L = TRANSLATED SECTOR ; ; SET DISK DMA ADDRESS. ; SETDMA: MOV H,B ;MOVE B&C TO H&L. MOV L,C SHLD DMAADD ;PUT AT DMA ADR ADDRESS. RET ;RETURN FROM SETDMA. ; ; HDLD - GET HEAD-LOAD BIT IF REQUIRED. ; HDLD: LDA HLSF ;GET HEAD-LOAD FLAG. ORA A ;IS A = ZERO? JZ HDLD1 ;HOP IF SO. CMA ;SET A = 0. STA HLSF ;SET FLAG = 0 IF NOT. HDLDY: MVI A,4 ;SET BIT TO LOAD HEAD. RET ;RETURN FROM HDLD. HDLD1: IN DSTAT ;READ 1771 STATUS. ANI 20H ;LOOK AT HL BIT. JZ HDLDY ;LOAD IF NOT LOADED. XRA A ;OTHERWISE, A=0. RET ;RETURN FROM HDLD. ; READ A SECTOR WITHOUT LOADING HEAD FIRST. ; READ1: OUT SECTP ;SET SECTOR NUMBER INTO 1771. MVI A,8CH ;GET CODE FOR READ W/O HLD. JMP READE ;READ A SECTOR. READ2: OUT SECTP MVI A,88H JMP READE ; ; READ THE SECTOR AT SECT, FROM THE PRESENT TRACK. ; USE STARTING ADDRESS AT DMAADD. ; READ: MVI A,RTCNT ;GET RETRY COUNT. RRETRY: ;STOR IN ERROR CTR. CALL DSKSET ADI 88H READE: OUT DCOM ;SEND COMMAND TO 1771. RLOOP: IN WAIT ;WAIT FOR DRQ OR INTRQ. ORA A ;SET FLAGS. JP RDDONE ;DONE IF INTRQ. IN DDATA ;READ A DATA BYTE FROM DISK. MOV M,A ;PUT BYTE INTO MEMORY. INX H ;INCREMENT MEMORY POINTER. JMP RLOOP ;KEEP READING. RDDONE: IN DSTAT ;READ DISK STATUS. ANI 9CH ;LOOK AT ERROR BITS. RZ ;RETURN IF NONE. CALL ERCHK ;CHECK FOR SEEK ERROR. LDA ERCNT ;GET ERROR COUNT. DCR A ;DECREMENT COUNT. JNZ RRETRY ;TRY TO READ AGAIN. JMP DABRT1 RDERR: RLC PUSH PSW LXI D,MSG1 CC PRINT POP PSW RLC RLC RLC PUSH PSW LXI D,MSG7 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG4 CC PRINT POP PSW RLC PUSH PSW LXI D,MSG5 CC PRINT POP PSW RET RDERR1: MVI C,'B' CALL @CONOT JMP 0E000H PRINT PUSH H MVI C,09 CALL BDOS POP H RET ABORT: MVI A,10 STA ERCNT STA SERCNT MVI A,1 JMP WBOOT ; ; ERCHK - CHECK FOR RECORD NOT FOUND ERROR. ; ERCHK: MOV D,A ;SAVE ERROR BITS ON STACK. ANI 10H ;IF RECORD NOT FOUND, JNZ CHKSK ;DO A CHECK ON SEEK. MOV A,D ;RESTORE ERROR BITS. ORA A RET ;AND RETURN. ;CHECK FOR SEEK TO CORRECT TRACK, ;AND CHANGE IF NECESSARY. CHKSK: MVI A,0C4H ;SEND COMMAND TO 1771 OUT DCOM ;TO READ ADDRESS. IN WAIT ;WAIT FOR DRQ OR INTRQ. IN DDATA ;READ THE TRACK ADDRESS. MOV B,A ;SAVE IN REGISTER B. CHKS2: IN WAIT ;WAIT FOR INTRQ. ORA A JP CHKS3 ;NOT IF DRQ. IN DDATA ;READ ANOTHER BYTE. JMP CHKS2 ;DO IT AGAIN. CHKS3: IN DSTAT ;READ DISK STATUS. ANI 09CH JZ CHKS4 ;READ ADR OK IF 0. PUSH D CALL RDERR CALL HOME ;OTHERWISE, HOME FIRST. POP D JMP CHKS5 CHKS4: MOV A,B ;UPDATE TRACK REGISTER. OUT TRACK CHKS5: LDA TRK ;GET REQUIRED TRACK NO. CALL SEEK ;MOVE THE HEAD TO IT. MOV A,D ORA A RET ; ;DISK SET UP ROUTINE. ;THIS ROUTINE IS COMMON TO ;BOTH THE READ AND WRITE ;ROUTINES. ; DSKSET: STA ERCNT ;STORE IN ERROR CTR. MVI A,0D0H ;CAUSE INTERRUPT. OUT DCOM XTHL ;SOME XTHL ; DELAY LHLD DMAADD ;GET STARTING ADDR. LDA SECT ;GET SECTOR NUMBER. OUT SECTP ;SET SECTOR INTO 1771. JMP HDLD ;GET HEAD-LOAD BIT? ; ; WRITE THE SECTOR AT SECT, ON THE PRESENT TRACK. ; USE STARTING ADDRESS AT DMAADD. ; WRITE: MVI A,RTCNT ;GET RETRY COUNT. WRETRY: CALL DSKSET ;SET UP DISK. ADI 0A8H ;ADD CODE TOR WRITE. WRITE2: OUT DCOM WLOOP: IN WAIT ;WAIT FOR READY. ORA A ;SET FLAGS. JP WDONE ;HOP OUT WHEN DONE. MOV A,M ;GET BYTE FROM MEM. OUT DDATA ;WRITE ONTO DISK. INX H ;INCREMENT MEM PTR. JMP WLOOP ;KEEP WRITING. WDONE: IN DSTAT ;READ DISK STATUS. ANI 0E4H ;LOOK AT THESE BITS. RZ ;RETURN IF NO ERR. CALL ERCHK ;CHECK/CORRECT SEEK ERR. CALL TP1ERR LDA ERCNT ;GET ERROR COUNT. DCR A ;DECREMENT COUNT. JNZ WRETRY ;TRY TO WRITE AGAIN. JMP DABRT1 ; ; MSG1: DB CR,LF,'NOT READY','$' MSG2: DB CR,LF,'WRITE PROTECT','$' MSG3: DB CR,LF,'WRITE FAULT','$' MSG4: DB CR,LF,'CRC ERROR','$' MSG5: DB CR,LF,'LOST DATA','$' MSG6: DB CR,LF,'SEEK ERROR.','$' MSG7: DB CR,LF,'NOT FOUND','$' DABORT: DB CR,LF,'ABORTED','$' ; ;NOTE: AS THERE ARE ONLY SIX (6) SECTORS ;AVAILABLE FOR CBIOS ON THE SECOND SYSTEM TRACK (1), ;THE LAST ADDRESS BEFORE THIS POINT SHOULD BE NO ;GREATER THAN THE CBIOS STARTING ADDRESS + 037F (HEX). ;THIS WILL NORMALLY BE XD7F (HEX). ; ; BIOS SCRATCH AREA ; ; THE NEXT SEVERAL BYTES, BETWEEN STARTZ AND ; ENDZ, ARE SET TO ZERO AT COLD BOOT TIME. ; STARTZ: DMAADD: DW 0000H ;DISK TRANSFER ADDRESS TRK: DB 0 ;CURRENT TRACK NUMBER. SECT: DB 1 ;CURRENT SECTOR NUMBER. DISKNO: DB 0 ;DISK NUMBER DB 0 PDISK: DB 0 ; SPECIAL FLAGS. HLSF: DB 0 ;HEAD-LOAD SELECT FLAG. LFCNT: DB 0 ;PAGING LINE-FEED COUNT. ; ; TRTAB - DISK TRACK TABLE - PRESENT POSITION OF ; HEADS FOR UP TO 4 DRIVES. ; TRTAB: DB 00 DB 00 COUNT: DB 00 ;LINE COUNT ENDZ: ;END OF ZEROED AREA. ERCNT: DS 1 ;ERROR COUNT FOR RETRIES. SERCNT: DS 1 ;SEEK RETRY COUNTER. TEMP: DS 1 ;TEMPORARY STORAGE. LATCH: DS 1 ;NEW CODE FOR LATCH. CLATCH: DS 1 ;CURRENT CODE IN LATCH. BEGDAT EQU $ DIRBUF: DS 128 ;DIRECTORY BUFFER ALV0: DS 31 CSV0: DS 24 ALV1: DS 31 CSV1: DS 24 ALV2: DS 31 CSV2: DS 24 ALV3: DS 31 CSV3: DS 24 ENDDAT EQU $ DATSIZ EQU $-BEGDAT ;TOTAL SIZE OF DISK PARM STORAGE. ; END