AppleIISd/Firmware/src/ProDOS.s

259 lines
5.8 KiB
ArmAsm
Raw Normal View History

;*******************************
;
; Apple][Sd Firmware
2020-06-04 16:06:07 +00:00
; Version 1.2.2
; ProDOS functions
;
2021-02-20 12:59:37 +00:00
; (c) Florian Reitz, 2017 - 2021
;
; X register usually contains SLOT16
; Y register is used for counting or SLOT
;
;*******************************
2018-05-13 15:58:41 +00:00
2018-05-13 20:46:17 +00:00
.export PRODOS
.export STATUS
.export READ
.export WRITE
.import COMMAND
.import SDCMD
.import GETBLOCK
2020-06-04 16:06:07 +00:00
.import CARDDET
.import INITED
.import INIT
.import WRPROT
.import GETR1
.import GETR3
.include "AppleIISd.inc"
.segment "EXTROM"
2018-05-13 15:58:41 +00:00
;*******************************
;
; ProDOS command dispatcher
;
; $42-$47 MLI input locations
; X Slot*16
; Y Slot
;
; C Clear - No error
; Set - Error
; A $00 - No error
; $01 - Unknown command
;
;*******************************
2018-05-13 20:46:17 +00:00
PRODOS: LDA DCMD ; get command
2018-05-13 15:58:41 +00:00
BEQ @STATUS ; branch if cmd is 0
CMP #1
BEQ @READ
CMP #2
BEQ @WRITE
2018-05-22 19:53:11 +00:00
LDA #ERR_BADCMD ; unknown command
2018-05-13 15:58:41 +00:00
SEC
RTS
@STATUS: JMP STATUS
@READ: JMP READ
@WRITE: JMP WRITE
;*******************************
;
; Status request
; $43 Unit number DSSS000
; $44-45 Unused
; $46-47 Unused
;
; C Clear - No error
; Set - Error
; A $00 - No error
2020-06-04 16:06:07 +00:00
; $28 - No card inserted
; $2B - Card write protected
; X - Blocks avail (low byte)
; Y - Blocks avail (high byte)
;
;*******************************
2018-07-07 15:28:30 +00:00
STATUS: LDA #NO_ERR ; Thanks for this one, Antoine!
2020-06-04 16:06:07 +00:00
JSR CARDDET
BCC @WRPROT
LDA #ERR_NODRIVE; no card inserted
BNE @DONE
@WRPROT: JSR WRPROT
BCC @DONE
2018-05-22 19:53:11 +00:00
LDA #ERR_NOWRITE; card write protected
@DONE: LDX #$FF ; 32 MB partition
LDY #$FF
RTS
;*******************************
;
; Read 512 byte block
; $43 Unit number DSSS0000
; $44-45 Address (LO/HI) of buffer
; $46-47 Block number (LO/HI)
;
; C Clear - No error
; Set - Error
; A $00 - No error
; $27 - Bad block number
2020-06-04 16:06:07 +00:00
; $28 - No card inserted
;
;*******************************
2020-06-04 16:06:07 +00:00
READ: JSR CARDDET ; check for card
BCS @NDERROR ; no card
JSR INITED ; check for initialization
BCC @GETBLOCK
JSR INIT ; initialize card
BCS @NDERROR ; init failed
@GETBLOCK: JSR GETBLOCK ; calc block address
LDA SS,X ; enable /CS
AND #<~SS0
STA SS,X
LDA #$51 ; send CMD17
JSR COMMAND ; send command
CMP #0
2020-06-04 16:06:07 +00:00
BNE @IOERROR ; check for error
@GETTOK: LDA #DUMMY ; get data token
STA DATA,X
LDA DATA,X ; get response
CMP #$FE
BNE @GETTOK ; wait for $FE
LDA CTRL,X ; enable FRX
ORA #FRX
STA CTRL,X
LDA #DUMMY
STA DATA,X
LDY #0
@LOOP1: LDA DATA,X ; read data from card
STA (BUFFER),Y
INY
BNE @LOOP1
INC BUFFER+1 ; inc msb on page boundary
@LOOP2: LDA DATA,X
STA (BUFFER),Y
INY
BNE @LOOP2
DEC BUFFER+1
@CRC: LDA DATA,X ; read two bytes crc
LDA DATA,X ; and ignore
LDA DATA,X ; read a dummy byte
LDA CTRL,X ; disable FRX
AND #<~FRX
STA CTRL,X
CLC ; no error
2018-05-22 19:53:11 +00:00
LDA #NO_ERR
@DONE: PHP
PHA
LDA SS,X
ORA #SS0
STA SS,X ; disable /CS
PLA
PLP
RTS
2020-06-04 16:06:07 +00:00
@IOERROR: SEC ; an error occured
2018-05-22 19:53:11 +00:00
LDA #ERR_IOERR
BRA @DONE
2020-06-04 16:06:07 +00:00
@NDERROR: SEC ; an error occured
LDA #ERR_NODRIVE
BRA @DONE
;*******************************
;
; Write 512 byte block
; $43 Unit number DSSS0000
; $44-45 Address (LO/HI) of buffer
; $46-47 Block number (LO/HI)
;
; C Clear - No error
; Set - Error
; A $00 - No error
; $27 - I/O error or bad block number
; $2B - Card write protected
;
;*******************************
WRITE: JSR WRPROT
BCS @WPERROR ; card write protected
JSR GETBLOCK ; calc block address
LDA SS,X ; enable /CS
AND #<~SS0
STA SS,X
LDA #$58 ; send CMD24
JSR COMMAND ; send command
CMP #0
BNE @IOERROR ; check for error
LDA #DUMMY
STA DATA,X ; send dummy
LDA #$FE
STA DATA,X ; send data token
LDY #0
@LOOP1: LDA (BUFFER),Y
STA DATA,X
INY
BNE @LOOP1
INC BUFFER+1
@LOOP2: LDA (BUFFER),Y
STA DATA,X
INY
BNE @LOOP2
DEC BUFFER+1
@CRC: LDA #DUMMY
STA DATA,X ; send 2 dummy crc bytes
STA DATA,X
STA DATA,X ; get data response
LDA DATA,X
AND #$1F
CMP #$05
BNE @IOERROR ; check for write error
CLC ; no error
2018-09-06 18:05:53 +00:00
LDA #NO_ERR
@DONE: PHP
PHA
@WAIT: LDA #DUMMY
STA DATA,X ; wait for write cycle
LDA DATA,X ; to complete
BEQ @WAIT
LDA SS,X ; disable /CS
ORA #SS0
STA SS,X
PLA
PLP
RTS
@IOERROR: SEC ; an error occured
2018-05-22 19:53:11 +00:00
LDA #ERR_IOERR
BRA @DONE
@WPERROR: SEC
2018-05-22 19:53:11 +00:00
LDA #ERR_NOWRITE
BRA @DONE