You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

715 lines
17 KiB

;
;==================================================================================================
; PPIDE DISK DRIVER
;==================================================================================================
;
; 11/29/2011 dwg - DOUGDEBUG controls the embedded NOPs which adjust for
; recovery time while using the parallel port to talk to the PPIDE and IDE
; device. Using this stabilized by Zeta (8MHz) with a CF chip.
;
; 12/02/2011 wbw - renamed DOUGDEBUG to PPIDESLOW and exposed in config
; PPIDESLOW now controls the RECOVERY macro definition.
;
#IF (PPIDESLOW)
#DEFINE RECOVERY NOP\ NOP\ NOP\ NOP
#ELSE
#DEFINE RECOVERY ;
#ENDIF
;
; MAP PPI PORTS TO PPIDE PORTS
;
IDELSB .EQU PPIDEIOB + 0 ; LSB
IDEMSB .EQU PPIDEIOB + 1 ; MSB
IDECTL .EQU PPIDEIOB + 2 ; CONTROL SIGNALS
PPICTL .EQU PPIDEIOB + 3 ; PPI (8255) CONTROL PORT
;
; PPI control bytes for read and write to IDE drive
;
RD_IDE_8255 .EQU %10010010 ; IDE_8255_CTL OUT, IDE_8255_LSB/MSB INPUT
WR_IDE_8255 .EQU %10000000 ; ALL THREE PORTS OUTPUT
;
; IDE CONTROL LINES FOR USE WITH IDE_8255_CTL. CHANGE THESE 8
; CONSTANTS TO REFLECT WHERE EACH SIGNAL OF THE 8255 EACH OF THE
; IDE CONTROL SIGNALS IS CONNECTED. ALL THE CONTROL SIGNALS MUST
; BE ON THE SAME PORT, BUT THESE 8 LINES LET YOU CONNECT THEM TO
; WHICHEVER PINS ON THAT PORT.
;
PPIDE_A0_LINE .EQU $01 ; DIRECT FROM 8255 TO IDE INTERFACE
PPIDE_A1_LINE .EQU $02 ; DIRECT FROM 8255 TO IDE INTERFACE
PPIDE_A2_LINE .EQU $04 ; DIRECT FROM 8255 TO IDE INTERFACE
PPIDE_CS0_LINE .EQU $08 ; INVERTER BETWEEN 8255 AND IDE INTERFACE
PPIDE_CS1_LINE .EQU $10 ; INVERTER BETWEEN 8255 AND IDE INTERFACE
PPIDE_WR_LINE .EQU $20 ; INVERTER BETWEEN 8255 AND IDE INTERFACE
PPIDE_RD_LINE .EQU $40 ; INVERTER BETWEEN 8255 AND IDE INTERFACE
PPIDE_RST_LINE .EQU $80 ; INVERTER BETWEEN 8255 AND IDE INTERFACE
;
;------------------------------------------------------------------
; MORE SYMBOLIC CONSTANTS... THESE SHOULD NOT BE CHANGED, UNLESS OF
; COURSE THE IDE DRIVE INTERFACE CHANGES, PERHAPS WHEN DRIVES GET
; TO 128G AND THE PC INDUSTRY WILL DO YET ANOTHER KLUDGE.
;
; SOME SYMBOLIC CONSTANTS FOR THE IDE REGISTERS, WHICH MAKES THE
; CODE MORE READABLE THAN ALWAYS SPECIFYING THE ADDRESS PINS
;
PPIDE_DATA .EQU PPIDE_CS0_LINE
PPIDE_ERROR .EQU PPIDE_CS0_LINE + PPIDE_A0_LINE
PPIDE_FEATURE .EQU PPIDE_CS0_LINE + PPIDE_A0_LINE
PPIDE_SEC_CNT .EQU PPIDE_CS0_LINE + PPIDE_A1_LINE
PPIDE_SECTOR .EQU PPIDE_CS0_LINE + PPIDE_A1_LINE + PPIDE_A0_LINE
PPIDE_CYL_LSB .EQU PPIDE_CS0_LINE + PPIDE_A2_LINE
PPIDE_CYL_MSB .EQU PPIDE_CS0_LINE + PPIDE_A2_LINE + PPIDE_A0_LINE
PPIDE_HEAD .EQU PPIDE_CS0_LINE + PPIDE_A2_LINE + PPIDE_A1_LINE
PPIDE_COMMAND .EQU PPIDE_CS0_LINE + PPIDE_A2_LINE + PPIDE_A1_LINE + PPIDE_A0_LINE
PPIDE_STTS .EQU PPIDE_CS0_LINE + PPIDE_A2_LINE + PPIDE_A1_LINE + PPIDE_A0_LINE
PPIDE_CONTROL .EQU PPIDE_CS1_LINE + PPIDE_A2_LINE + PPIDE_A1_LINE
PPIDE_ASTTS .EQU PPIDE_CS1_LINE + PPIDE_A2_LINE + PPIDE_A1_LINE + PPIDE_A0_LINE
;
; IDE COMMAND CONSTANTS. THESE SHOULD NEVER CHANGE.
;
PPIDE_CMDRECAL .EQU $10
PPIDE_CMDREAD .EQU $20
PPIDE_CMDWRITE .EQU $30
PPIDE_CMDINIT .EQU $91
PPIDE_CMDID .EQU $EC
PPIDE_CMDSPINDOWN .EQU $E0
PPIDE_CMDSPINUP .EQU $E1
PPIDE_CMDSETFEAT .EQU $EF
;
PPIDE_RCOK .EQU 0
PPIDE_RCCMDERR .EQU 1
PPIDE_RCRDYTO .EQU 2
PPIDE_RCBUFTO .EQU 3
;
; UNIT CONFIGURATION
;
PPIDE_UNIT0 .DB %11100000 ; LBA, MASTER DEVICE
PPIDE_UNIT1 .DB %11110000 ; LBA, SLAVE DEVICE
;
;
;
PPIDE_DISPATCH:
LD A,B ; GET REQUESTED FUNCTION
AND $0F
JR Z,PPIDE_RD
DEC A
JR Z,PPIDE_WR
DEC A
JR Z,PPIDE_ST
DEC A
JR Z,PPIDE_MED
CALL PANIC
;
PPIDE_RD:
LD A,PPIDE_CMDREAD
LD (PPIDEP_CMD),A
JP PPIDE_RW
;
PPIDE_WR:
LD A,PPIDE_CMDWRITE
LD (PPIDEP_CMD),A
JP PPIDE_RW
;
PPIDE_ST:
LD A,(PPIDE_STAT) ; LOAD STATUS
OR A ; SET FLAGS
RET
;
PPIDE_MED:
LD A,MID_HD
RET
;
;
;
PPIDE_INIT:
PRTS("PPIDE: IO=0x$")
LD A,IDELSB
CALL PRTHEXBYTE
PRTS(" UNITS=2$")
#IF (PPIDE8BIT)
PRTS(" 8BIT$")
#ENDIF
#IF (PPIDESLOW)
PRTS(" SLOW$")
#ENDIF
CALL PPIDE_RESET
XOR A
DEC A ; INITIAL STATUS IS NOT READY $FF
LD (PPIDE_STAT),A ; SAVE IT
RET
;
;
;
PPIDE_RW:
; INIT REQUIRED?
LD A,(PPIDE_STAT)
OR A ; SET FLAGS
JR Z,PPIDE_RW0 ; IF STATUS OK, BYPASS RESET
CALL PPIDE_RESET ; DO THE RESET
; NEED TO CHECK STATUS HERE!!!
PPIDE_RW0:
; CLEAR RESULTS
XOR A ; A = 0
LD (PPIDE_RC),A ; CLEAR RETURN CODE
LD (PPIDEP_STTS),A ; CLEAR SAVED STTS
LD (PPIDEP_ERR),A ; CLEAR SAVED ERR
CALL PPIDE_WAITRDY ; WAIT FOR DRIVE READY
JP NC,PPIDE_ERR
CALL PPIDE_SETUP ; SETUP CYL, TRK, HEAD
LD C,PPIDE_COMMAND ; IDE COMMAND REGISTER
LD A,(PPIDEP_CMD) ; COMMAND VALUE
CALL PPIDE_WRITE ; DO IT
CALL PPIDE_WAITRDY ; WAIT FOR DRIVE READY
JP NC,PPIDE_ERR
CALL PPIDE_CHKERR ; CHECK FOR ERRORS
JP NC,PPIDE_ERR
CALL PPIDE_WAITBUF ; WAIT FOR BUFFER READY
JP NC,PPIDE_ERR
LD A,(PPIDEP_CMD) ; DISPATCH TO READ OR WRITE SPECIFIC LOGIC
CP PPIDE_CMDWRITE
JP Z,PPIDE_RW1
CALL PPIDE_BUFRD ; READ BUFFER
CALL PPIDE_WAITRDY ; WAIT FOR DRIVE READY
JP NC,PPIDE_ERR
CALL PPIDE_CHKERR ; CHECK FOR ERRORS
JP NC,PPIDE_ERR
JP PPIDE_OK
PPIDE_RW1:
CALL PPIDE_BUFWR ; WRITE BUFFER
CALL PPIDE_WAITRDY ; WAIT FOR DRIVE READY
JP NC,PPIDE_ERR
CALL PPIDE_CHKERR ; CHECK FOR ERRORS
JP NC,PPIDE_ERR
JP PPIDE_OK
PPIDE_ERR:
XOR A
DEC A ; A = $FF TO SIGNAL ERROR
LD (PPIDE_STAT),A ; SAVE IT
#IF (PPIDETRACE >= 1)
PUSH AF
CALL PPIDE_PRT
POP AF
#ENDIF
RET
PPIDE_OK:
#IF (PPIDETRACE >= 2)
CALL PPIDE_PRT
#ENDIF
XOR A
RET
;
;
;
PPIDE_RESET:
#IF (PPIDETRACE >= 2)
CALL NEWLINE
PRTX(PPIDESTR_PREFIX)
PRTS(" RESET$")
#ENDIF
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
LD C,PPIDE_CONTROL ; IDE CONTROL REGISTER
LD A,000001110B ; NO INTERRUPTS, ASSERT RESET BOTH DRIVES
CALL PPIDE_WRITE ; DO IT
LD DE,8 ; DELAY ABOUT 200ms
CALL VDELAY
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
LD C,PPIDE_CONTROL ; IDE CONTROL REGISTER
LD A,000000010B ; NO INTERRUPTS, DEASSERT RESET
CALL PPIDE_WRITE ; DO IT
XOR A ; STATUS OK
LD (PPIDE_STAT),A ; SAVE IT
#IF (PPIDE8BIT)
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
CALL PPIDE_WAITRDY
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
LD C,PPIDE_FEATURE ; IDE FEATURE REGISTER
LD A,01H ; VALUE := 1
CALL PPIDE_WRITE ; DO IT
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
LD C,PPIDE_COMMAND ; IDE COMMAND REGISTER
LD A,PPIDE_CMDSETFEAT ; SET FEATURE
CALL PPIDE_WRITE ; DO IT
#IF (PPIDETRACE >= 2)
CALL PC_PERIOD
#ENDIF
#ENDIF
RET
;
;
;
PPIDE_WAITRDY:
LD DE,0 ; TIMEOUT IS 250us * 65536 = 15 SECONDS
PPIDE_WBSY:
PUSH DE
LD DE,10 ; INNER LOOP DELAY IS 250us (25us * 10)
CALL VDELAY
POP DE
DEC DE
LD A,D
OR E
JP Z,PPIDE_TO
LD C,PPIDE_STTS ; IDE STATUS REGISTER
CALL PPIDE_READ ; READ ID
LD (PPIDEP_STTS),A ; SAVE IT
AND 011000000B ; ISOLATE BUSY AND RDY BITS
XOR 001000000B ; WE WANT BUSY(7) TO BE 0 AND RDY(6) TO BE 1
JP NZ,PPIDE_WBSY
SCF ; CARRY 1 = OK
RET
PPIDE_TO:
LD A,PPIDE_RCRDYTO
LD (PPIDE_RC),A
XOR A ; CARRY 0 = TIMEOUT
RET
;
;
;
PPIDE_CHKERR:
LD C,PPIDE_STTS ; IDE STATUS REGISTER
CALL PPIDE_READ ; READ IT
LD (PPIDEP_STTS),A ; SAVE IT
AND 000000001B ; ERROR BIT SET?
SCF ; ASSUME NO ERR
RET Z ; NO ERR, RETURN WITH CF SET
;
LD C,PPIDE_ERROR ; IDE ERROR REGISTER
CALL PPIDE_READ ; READ IT
LD (PPIDEP_ERR),A ; SAVE IT
;
LD A,PPIDE_RCCMDERR ; COMMAND ERROR
LD (PPIDE_RC),A ; SAVE IT
;
OR A ; CLEAR CF TO SIGNAL ERROR
RET
;
;
;
PPIDE_WAITBUF:
LD DE,0
PPIDE_WDRQ:
CALL DELAY
INC DE
LD A,D
OR E
JP Z,PPIDE_TO2
LD C,PPIDE_STTS ; IDE STATUS REGISTER
CALL PPIDE_READ ; READ IT
LD (PPIDEP_STTS),A ; SAVE IT
AND 010001000B ; TO FILL (OR READY TO FILL)
XOR 000001000B
JP NZ,PPIDE_WDRQ
SCF ; CARRY 1 = OK
RET
PPIDE_TO2:
LD A,PPIDE_RCBUFTO
LD (PPIDE_RC),A
XOR A ; CARRY 0 = TIMED OUT
RET
;
;
;
PPIDE_BUFRD:
; SETUP PPI TO READ
LD A,RD_IDE_8255 ; READ CONFIG
OUT (PPICTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; SELECT READ/WRITE IDE REGISTER
LD A,PPIDE_DATA ; DATA REGISTER
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
LD E,A ; E := READ UNASSERTED
XOR PPIDE_RD_LINE ; SWAP THE READ LINE BIT
LD D,A ; D := READ ASSERTED
;
; LOOP SETUP
LD HL,(DIOBUF) ; LOCATION OF BUFFER
LD B,0 ; 256 ITERATIONS
LD C,IDELSB ; SETUP C WITH IO PORT (LSB)
;
CALL PPIDE_BUFRD1 ; FIRST PASS (FIRST 256 BYTES)
CALL PPIDE_BUFRD1 ; SECOND PASS (LAST 256 BYTES)
;
; CLEAN UP
XOR A ; ZERO A
OUT (IDECTL),A ; RELEASE ALL BUS SIGNALS
RECOVERY ; OPTIONAL SMALL DELAY
RET
;
PPIDE_BUFRD1: ; START OF READ LOOP
LD A,D ; ASSERT READ
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
INI ; GET AND SAVE NEXT BYTE
RECOVERY ; OPTIONAL SMALL DELAY
#IF (!PPIDE8BIT)
INC C ; LSB -> MSB
INI ; GET AND SAVE NEXT BYTE
RECOVERY ; OPTIONAL SMALL DELAY
PUSH AF
DEC C ; MSB -> LSB
POP AF
#ENDIF
LD A,E ; DEASSERT READ
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
JR NZ,PPIDE_BUFRD1 ; LOOP UNTIL DONE
RET
;
;
;
PPIDE_BUFWR:
; SETUP PPI TO WRITE
LD A,WR_IDE_8255 ; WRITE CONFIG
OUT (PPICTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; SELECT READ/WRITE IDE REGISTER
LD A,PPIDE_DATA ; DATA REGISTER
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
LD E,A ; E := WRITE UNASSERTED
XOR PPIDE_WR_LINE ; SWAP THE WRITE LINE BIT
LD D,A ; D := WRITE ASSERTED
;
; LOOP SETUP
LD HL,(DIOBUF) ; LOCATION OF BUFFER
LD B,0 ; 256 ITERATIONS
LD C,IDELSB ; SETUP C WITH IO PORT (LSB)
;
CALL PPIDE_BUFWR1 ; FIRST PASS (FIRST 256 BYTES)
CALL PPIDE_BUFWR1 ; SECOND PASS (LAST 256 BYTES)
;
; CLEAN UP
XOR A ; ZERO A
OUT (IDECTL),A ; RELEASE ALL BUS SIGNALS
RECOVERY ; OPTIONAL SMALL DELAY
RET
;
PPIDE_BUFWR1: ; START OF WRITE LOOP
OUTI ; SEND NEXT BYTE OF BUFFER
RECOVERY ; OPTIONAL SMALL DELAY
#IF (!PPIDE8BIT)
INC C ; LSB -> MSB
OUTI ; SEND NEXT BYTE OF BUFFER
PUSH AF
DEC C ; MSB -> LSB
POP AF
RECOVERY ; OPTIONAL SMALL DELAY
#ENDIF
;
; TOGGLE THE WRITE LINE
LD A,D ; WRITE ASSERTED VALUE
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
LD A,E ; WRITE UNASSERTED VALUE
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
JR NZ,PPIDE_BUFWR1 ; LOOP UNTIL DONE
RET
;
;
;
PPIDE_SETUP:
LD C,PPIDE_SEC_CNT ; IDE SECTOR COUNT REGISTER
LD A,1 ; 1 SECTOR
CALL PPIDE_WRITE ; DO IT
LD A,(HSTDSK) ; HSTDSK -> HEAD BIT 4 TO SELECT UNIT
AND 0FH
CP 0
JP Z,PPIDE_SETUP_UNIT0
CP 1
JP Z,PPIDE_SETUP_UNIT1
CALL PANIC
PPIDE_SETUP_UNIT0:
LD A,(PPIDE_UNIT0)
JP PPIDE_SETUP1
PPIDE_SETUP_UNIT1:
LD A,(PPIDE_UNIT1)
JP PPIDE_SETUP1
PPIDE_SETUP1:
LD C,PPIDE_HEAD ; IDE HEAD REGISTER
LD (PPIDEP_HEAD),A ; SAVE HEAD VALUE
CALL PPIDE_WRITE ; WRITE IT
LD HL,(HSTTRK) ; HSTTRK -> IDECYLHI/LO
LD C,PPIDE_CYL_MSB ; IDE MSB CYL REGISTER
LD A,H ; MSB CYL VALUE
LD (PPIDEP_CYLHI),A ; SAVE IT
CALL PPIDE_WRITE ; WRITE IT
LD C,PPIDE_CYL_LSB ; IDE LSB CYL REGISTER
LD A,L ; LSB CYL VALUE
LD (PPIDEP_CYLLO),A ; SAVE IT
CALL PPIDE_WRITE ; WRITE IT
LD HL,(HSTSEC) ; HSTSEC -> IDESECTN
LD C,PPIDE_SECTOR ; IDE SECTOR REGISTER
LD A,L ; SECTOR VALUE
LD (PPIDEP_SEC),A ; SAVE IT
CALL PPIDE_WRITE ; WRITE IT
#IF (DSKYENABLE)
CALL PPIDE_DSKY
#ENDIF
RET
;
;
;
PPIDE_READ:
;
; SET PPI MODE TO READ CONFIGURATION
LD A,RD_IDE_8255 ; PPI MODE TO READ
OUT (PPICTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; SELECT REQUESTED IDE REGISTER, THEN ASSERT READ
LD A,C ; REGISTER SELECTION -> A
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
OR PPIDE_RD_LINE ; ASSERT READ
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; READ THE BYTE
IN A,(IDELSB) ; READ LSB
RECOVERY ; OPTIONAL SMALL DELAY
PUSH AF ; SAVE IT FOR NOW
;
; ; DUMMY READ OF MSB
; IN A,(IDEMSB) ; READ LSB
; RECOVERY ; OPTIONAL SMALL DELAY
;
; CLEAN UP AND RETURN
LD A,C ; DEASSERT READ
OUT (IDECTL),A ; DO IT
XOR A ; RELEASE ALL BUS SIGNALS
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
POP AF ; RECOVER THE DATA BYTE
RET ; RETURN
;
;
;
PPIDE_WRITE:
;
; SAVE THE INCOMING VALUE TO WRITE
PUSH AF
;
; SET PPI MODE TO WRITE CONFIGURATION
LD A,WR_IDE_8255 ; PPI MODE TO WRITE
OUT (PPICTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; SELECT REQUESTED IDE REGISTER
LD A,C ; REGISTER SELECTION -> A
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
; SET THE VALUE TO WRITE
POP AF ; GET VALUE BACK
OUT (IDELSB),A ; SET IDE LSB
RECOVERY ; OPTIONAL SMALL DELAY
;
; ; MSB ALWAYS GETS ZERO
; XOR A ; ZERO A
; OUT (IDEMSB),A ; SET IDE MSB
; RECOVERY ; OPTIONAL SMALL DELAY
;
; PULSE THE WRITE LINE
LD A,C ; REGISTER SELECTION -> A
OR PPIDE_WR_LINE ; ASSERT WRITE
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
LD A,C
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
; CLEAN UP AND RETURN
XOR A ; RELEASE ALL BUS SIGNALS
OUT (IDECTL),A ; DO IT
RECOVERY ; OPTIONAL SMALL DELAY
;
RET ; RETURN
;
;
;
#IF (DSKYENABLE)
PPIDE_DSKY:
LD HL,DSKY_HEXBUF
LD A,(PPIDEP_HEAD)
LD (HL),A
INC HL
LD A,(PPIDEP_CYLHI)
LD (HL),A
INC HL
LD A,(PPIDEP_CYLLO)
LD (HL),A
INC HL
LD A,(PPIDEP_SEC)
LD (HL),A
CALL DSKY_HEXOUT
RET
#ENDIF
;
;
;
PPIDE_PRT:
CALL NEWLINE
LD DE,PPIDESTR_PREFIX
CALL WRITESTR
CALL PC_SPACE
LD DE,PPIDESTR_CMD
CALL WRITESTR
LD A,(PPIDEP_CMD)
CALL PRTHEXBYTE
CALL PC_SPACE
CALL PC_LBKT
LD A,(PPIDEP_CMD)
LD DE,PPIDESTR_READ
CP PPIDE_CMDREAD
JP Z,PPIDE_PRTCMD
LD DE,PPIDESTR_WRITE
CP PPIDE_CMDWRITE
JP Z,PPIDE_PRTCMD
LD DE,PPIDESTR_UNKCMD
PPIDE_PRTCMD:
CALL WRITESTR
CALL PC_RBKT
CALL PC_SPACE
LD A,(PPIDEP_HEAD)
CALL PRTHEXBYTE
LD A,(PPIDEP_CYLHI)
CALL PRTHEXBYTE
LD A,(PPIDEP_CYLLO)
CALL PRTHEXBYTE
LD A,(PPIDEP_SEC)
CALL PRTHEXBYTE
CALL PC_SPACE
LD DE,PPIDESTR_ARROW
CALL WRITESTR
CALL PC_SPACE
LD C,PPIDE_STTS ; IDE STATUS REGISTER
CALL PPIDE_READ ; READ IT
CALL PRTHEXBYTE
CALL PC_SPACE
LD C,PPIDE_ERROR ; IDE ERROR REGISTER
CALL PPIDE_READ ; READ IT
CALL PRTHEXBYTE
CALL PC_SPACE
LD DE,PPIDESTR_RC
CALL WRITESTR
LD A,(PPIDE_RC)
CALL PRTHEXBYTE
CALL PC_SPACE
CALL PC_LBKT
LD A,(PPIDE_RC)
LD DE,PPIDESTR_RCOK
CP PPIDE_RCOK
JP Z,PPIDE_PRTRC
LD DE,PPIDESTR_RCCMDERR
CP PPIDE_RCCMDERR
JP Z,PPIDE_PRTRC
LD DE,PPIDESTR_RCRDYTO
CP PPIDE_RCRDYTO
JP Z,PPIDE_PRTRC
LD DE,PPIDESTR_RCBUFTO
CP PPIDE_RCBUFTO
JP Z,PPIDE_PRTRC
LD DE,PPIDESTR_RCUNK
PPIDE_PRTRC:
CALL WRITESTR
CALL PC_RBKT
RET
;
;
;
PPIDESTR_PREFIX .TEXT "PPIDE:$"
PPIDESTR_CMD .TEXT "CMD=$"
PPIDESTR_RC .TEXT "RC=$"
PPIDESTR_ARROW .TEXT "-->$"
PPIDESTR_READ .TEXT "READ$"
PPIDESTR_WRITE .TEXT "WRITE$"
PPIDESTR_UNKCMD .TEXT "UNKCMD$"
PPIDESTR_RCOK .TEXT "OK$"
PPIDESTR_RCCMDERR .TEXT "COMMAND ERROR$"
PPIDESTR_RCRDYTO .TEXT "READY TIMEOUT$"
PPIDESTR_RCBUFTO .TEXT "BUFFER TIMEOUT$"
PPIDESTR_RCUNK .TEXT "UNKNOWN ERROR$"
;
;==================================================================================================
; PPIDE DISK DRIVER - DATA
;==================================================================================================
;
PPIDE_STAT .DB 0
PPIDE_RC .DB 0
;
; PPIDE PARAMETERS
;
PPIDEP_CMD .DB 0
PPIDEP_HEAD .DB 0
PPIDEP_CYLHI .DB 0
PPIDEP_CYLLO .DB 0
PPIDEP_SEC .DB 0
PPIDEP_STTS .DB 0
PPIDEP_ERR .DB 0
;
; Error Register (ERR bit being set in the Status Register)
;
; Bit 7: BBK (Bad Block Detected) Set when a Bad Block is detected.
; Bit 6: UNC (Uncorrectable Data Error) Set when Uncorrectable Error is encountered.
; Bit 5: MC (Media Changed) Set to 0.
; Bit 4: IDNF (ID Not Found) Set when Sector ID not found.
; Bit 3: MCR (Media Change Request) Set to 0.
; Bit 2: ABRT (Aborted Command) Set when Command Aborted due to drive error.
; Bit 1: TKONF (Track 0 Not Found) Set when Executive Drive Diagnostic Command.
; Bit 0: AMNF (Address mark Not Found) Set in case of a general error.
;
; Status Register (When the contents of this register are read by the host, the IREQ# bit is cleared)
;
; Bit 7: BSY (Busy) Set when the drive is busy and unable to process any new ATA commands.
; Bit 6: DRDY (Data Ready) Set when the device is ready to accept ATA commands from the host.
; Bit 5: DWF (Drive Write Fault) Always set to 0.
; Bit 4: DSC (Drive Seek Complete) Set when the drive heads have been positioned over a specific track.
; Bit 3: DRQ (Data Request) Set when device is ready to transfer a word or byte of data to or from the host and the device.
; Bit 2: CORR (Corrected Data) Always set to 0.
; Bit 1: IDX (Index) Always set to 0.
; Bit 0: ERR (Error) Set when an error occurred during the previous ATA command.