Fix register r/w timing
This commit is contained in:
committed by
Oliver Schmidt
parent
b300b7ac8b
commit
9e87e558d2
@@ -239,33 +239,34 @@ SER_FLAG_CH_B = %00000111
|
|||||||
|
|
||||||
.code
|
.code
|
||||||
|
|
||||||
; Read a register
|
; Read register value to A.
|
||||||
; Input: X as channel
|
; Input: X as channel
|
||||||
; Output result in A
|
; Y as register
|
||||||
.macro rra In,Reg
|
; Output: A
|
||||||
lda Reg
|
readSSCReg:
|
||||||
sta In,x
|
cpx #0
|
||||||
lda In,x
|
bne ReadAreg
|
||||||
.endmacro
|
sty SCCBREG
|
||||||
|
lda SCCBREG
|
||||||
|
rts
|
||||||
|
ReadAreg:
|
||||||
|
sty SCCAREG
|
||||||
|
lda SCCAREG
|
||||||
|
rts
|
||||||
|
|
||||||
; Write value of A to a register.
|
; Write value of A to a register.
|
||||||
; Input: X as channel
|
; Input: X as channel
|
||||||
.macro wra Out,Reg
|
; Y as register
|
||||||
pha
|
writeSCCReg:
|
||||||
lda Reg
|
cpx #0
|
||||||
sta Out,x
|
bne WriteAreg
|
||||||
pla
|
sty SCCBREG
|
||||||
sta Out,x
|
sta SCCBREG
|
||||||
.endmacro
|
rts
|
||||||
|
WriteAreg:
|
||||||
; Write value passed as parameter to a register.
|
sty SCCAREG
|
||||||
; Input: X as channel
|
sta SCCAREG
|
||||||
.macro wrr Out,Reg,Val
|
rts
|
||||||
lda Reg
|
|
||||||
sta Out,x
|
|
||||||
lda Val
|
|
||||||
sta Out,x
|
|
||||||
.endmacro
|
|
||||||
|
|
||||||
;----------------------------------------------------------------------------
|
;----------------------------------------------------------------------------
|
||||||
; SER_INSTALL: Is called after the driver is loaded into memory. If possible,
|
; SER_INSTALL: Is called after the driver is loaded into memory. If possible,
|
||||||
@@ -291,8 +292,13 @@ SER_CLOSE:
|
|||||||
|
|
||||||
; Deactivate interrupts
|
; Deactivate interrupts
|
||||||
sei
|
sei
|
||||||
wrr SCCBREG, #WR_MASTER_IRQ_RST, #MASTER_IRQ_SHUTDOWN
|
ldy #WR_MASTER_IRQ_RST
|
||||||
wrr SCCBREG, #WR_TX_RX_MODE_CTRL, #TX_RX_MODE_OFF
|
lda #MASTER_IRQ_SHUTDOWN
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
|
ldy #WR_TX_RX_MODE_CTRL
|
||||||
|
lda #TX_RX_MODE_OFF
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
; Reset SerFlag to what it was
|
; Reset SerFlag to what it was
|
||||||
lda SerFlagOrig
|
lda SerFlagOrig
|
||||||
@@ -303,14 +309,13 @@ SER_CLOSE:
|
|||||||
; Clear external interrupts (twice)
|
; Clear external interrupts (twice)
|
||||||
ldy #WR_INIT_CTRL
|
ldy #WR_INIT_CTRL
|
||||||
lda #INIT_CTRL_CLEAR_EIRQ
|
lda #INIT_CTRL_CLEAR_EIRQ
|
||||||
|
jsr writeSCCReg
|
||||||
sty SCCBREG
|
jsr writeSCCReg
|
||||||
sta SCCBREG
|
|
||||||
sty SCCBREG
|
|
||||||
sta SCCBREG
|
|
||||||
|
|
||||||
; Reset MIE for firmware use
|
; Reset MIE for firmware use
|
||||||
wrr SCCBREG, #WR_MASTER_IRQ_RST, #MASTER_IRQ_MIE_RST
|
ldy #WR_MASTER_IRQ_RST
|
||||||
|
lda #MASTER_IRQ_MIE_RST
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
ldx #$00
|
ldx #$00
|
||||||
stx Slot ; Mark port as closed
|
stx Slot ; Mark port as closed
|
||||||
@@ -346,6 +351,8 @@ SetupErrOut:
|
|||||||
rts
|
rts
|
||||||
|
|
||||||
HardwareFound:
|
HardwareFound:
|
||||||
|
sei ; Disable interrupts
|
||||||
|
|
||||||
; Check if the handshake setting is valid
|
; Check if the handshake setting is valid
|
||||||
ldy #SER_PARAMS::HANDSHAKE ; Handshake
|
ldy #SER_PARAMS::HANDSHAKE ; Handshake
|
||||||
lda (ptr1),y
|
lda (ptr1),y
|
||||||
@@ -370,7 +377,12 @@ SetupBufs:
|
|||||||
|
|
||||||
ldx Channel
|
ldx Channel
|
||||||
|
|
||||||
rra SCCBREG,#$00 ; Hit rr0 once to sync up
|
ldy #RR_INIT_STATUS ; Hit rr0 once to sync up
|
||||||
|
jsr readSSCReg
|
||||||
|
|
||||||
|
ldy #WR_MISC_CTRL ; Turn everything off
|
||||||
|
lda #$00
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
ldy #SER_PARAMS::STOPBITS
|
ldy #SER_PARAMS::STOPBITS
|
||||||
lda (ptr1),y ; Stop bits
|
lda (ptr1),y ; Stop bits
|
||||||
@@ -388,19 +400,24 @@ SetupBufs:
|
|||||||
|
|
||||||
ora #TX_RX_CLOCK_MUL
|
ora #TX_RX_CLOCK_MUL
|
||||||
|
|
||||||
wra SCCBREG,#WR_TX_RX_CTRL
|
ldy #WR_TX_RX_CTRL ; Setup stop & parity bits
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
cpx #$00
|
cpx #$00
|
||||||
bne ClockA
|
bne ClockA
|
||||||
ClockB:
|
ClockB:
|
||||||
wrr SCCBREG,#WR_CLOCK_CTRL,#CLOCK_CTRL_CH_B
|
ldy #WR_CLOCK_CTRL
|
||||||
|
lda #CLOCK_CTRL_CH_B
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda #INTR_PENDING_RX_EXT_B ; Store which IRQ bits we'll check
|
lda #INTR_PENDING_RX_EXT_B ; Store which IRQ bits we'll check
|
||||||
sta CurChanIrqFlags
|
sta CurChanIrqFlags
|
||||||
|
|
||||||
bra SetBaud
|
bra SetBaud
|
||||||
ClockA:
|
ClockA:
|
||||||
wrr SCCBREG,#WR_CLOCK_CTRL,#CLOCK_CTRL_CH_A
|
ldy #WR_CLOCK_CTRL
|
||||||
|
lda #CLOCK_CTRL_CH_A
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda #INTR_PENDING_RX_EXT_A ; Store which IRQ bits we'll check
|
lda #INTR_PENDING_RX_EXT_A ; Store which IRQ bits we'll check
|
||||||
sta CurChanIrqFlags
|
sta CurChanIrqFlags
|
||||||
@@ -416,50 +433,58 @@ SetBaud:
|
|||||||
lda BaudLowTable,y ; Get low byte
|
lda BaudLowTable,y ; Get low byte
|
||||||
bmi InvParam ; Branch if rate not supported
|
bmi InvParam ; Branch if rate not supported
|
||||||
|
|
||||||
wra SCCBREG,#WR_BAUDL_CTRL
|
phy
|
||||||
|
ldy #WR_BAUDL_CTRL
|
||||||
|
jsr writeSCCReg
|
||||||
|
ply
|
||||||
|
|
||||||
lda BaudHighTable,y ; Get high byte
|
lda BaudHighTable,y ; Get high byte
|
||||||
wra SCCBREG,#WR_BAUDH_CTRL
|
ldy #WR_BAUDH_CTRL
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda #$00
|
ldy #WR_MISC_CTRL ; Time to turn this thing on
|
||||||
wra SCCBREG,#WR_MISC_CTRL
|
lda #MISC_CTRL_RATE_GEN_ON
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
ora #MISC_CTRL_RATE_GEN_ON ; Time to turn this thing on
|
|
||||||
wra SCCBREG,#WR_MISC_CTRL
|
|
||||||
|
|
||||||
; Final write to RX_CTRL
|
|
||||||
ldy #SER_PARAMS::DATABITS
|
ldy #SER_PARAMS::DATABITS
|
||||||
lda (ptr1),y ; Data bits
|
lda (ptr1),y ; Data bits
|
||||||
tay
|
tay
|
||||||
lda RxBitTable,y ; Data bits for RX
|
lda RxBitTable,y ; Data bits for RX
|
||||||
ora #RX_CTRL_ON ; Plus turn on
|
ora #RX_CTRL_ON ; and turn RX on
|
||||||
wra SCCBREG,#WR_RX_CTRL
|
|
||||||
|
phy
|
||||||
|
ldy #WR_RX_CTRL
|
||||||
|
jsr writeSCCReg
|
||||||
|
ply
|
||||||
|
|
||||||
lda TxBitTable,y ; Data bits for TX
|
lda TxBitTable,y ; Data bits for TX
|
||||||
ora #TX_CTRL_ON ; Plus turn on
|
ora #TX_CTRL_ON ; and turn TX on
|
||||||
and #TX_DTR_ON
|
and #TX_DTR_ON
|
||||||
|
|
||||||
sta RtsOff ; Save value for flow control
|
sta RtsOff ; Save value for flow control
|
||||||
|
|
||||||
ora #TX_RTS_ON
|
ora #TX_RTS_ON
|
||||||
wra SCCBREG,#WR_TX_CTRL
|
|
||||||
|
|
||||||
wrr SCCBREG,#WR_IRQ_CTRL,#IRQ_CLEANUP_EIRQ
|
ldy #WR_TX_CTRL
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda #WR_INIT_CTRL ; Clear ext status (write twice)
|
ldy #WR_IRQ_CTRL
|
||||||
sta SCCBREG,x
|
lda #IRQ_CLEANUP_EIRQ
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
|
ldy #WR_INIT_CTRL ; Clear ext status (write twice)
|
||||||
lda #INIT_CTRL_CLEAR_EIRQ
|
lda #INIT_CTRL_CLEAR_EIRQ
|
||||||
sta SCCBREG,x
|
jsr writeSCCReg
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda #WR_INIT_CTRL
|
ldy #WR_TX_RX_MODE_CTRL ; Activate RX IRQ
|
||||||
sta SCCBREG,x
|
lda #TX_RX_MODE_RXIRQ
|
||||||
lda #INIT_CTRL_CLEAR_EIRQ
|
jsr writeSCCReg
|
||||||
sta SCCBREG,x
|
|
||||||
|
|
||||||
; Activate RX IRQ
|
lda SCCBREG ; Activate master IRQ
|
||||||
wrr SCCBREG,#WR_TX_RX_MODE_CTRL,#TX_RX_MODE_RXIRQ
|
ldy #WR_MASTER_IRQ_RST
|
||||||
|
lda #MASTER_IRQ_SET
|
||||||
wrr SCCBREG,#WR_MASTER_IRQ_RST,#MASTER_IRQ_SET
|
jsr writeSCCReg
|
||||||
|
|
||||||
lda SER_FLAG ; Get SerFlag's current value
|
lda SER_FLAG ; Get SerFlag's current value
|
||||||
sta SerFlagOrig ; and save it
|
sta SerFlagOrig ; and save it
|
||||||
@@ -502,7 +527,9 @@ SER_GET:
|
|||||||
|
|
||||||
lda RtsOff
|
lda RtsOff
|
||||||
ora #TX_RTS_ON
|
ora #TX_RTS_ON
|
||||||
wra SCCBREG,#WR_TX_CTRL
|
|
||||||
|
ldy #WR_TX_CTRL
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
: ldy RecvHead ; Get byte from buffer
|
: ldy RecvHead ; Get byte from buffer
|
||||||
lda RecvBuf,y
|
lda RecvBuf,y
|
||||||
@@ -597,8 +624,10 @@ SER_IOCTL:
|
|||||||
; was handled, otherwise with carry clear.
|
; was handled, otherwise with carry clear.
|
||||||
|
|
||||||
SER_IRQ:
|
SER_IRQ:
|
||||||
ldx #$00 ; IRQ status is always in A reg
|
ldx #$01 ; IRQ status is always in A reg
|
||||||
rra SCCAREG,#RR_INTR_PENDING_STATUS
|
ldy #RR_INTR_PENDING_STATUS
|
||||||
|
jsr readSSCReg
|
||||||
|
|
||||||
and CurChanIrqFlags ; Is this ours?
|
and CurChanIrqFlags ; Is this ours?
|
||||||
beq Done
|
beq Done
|
||||||
|
|
||||||
@@ -620,7 +649,8 @@ SER_IRQ:
|
|||||||
CheckSpecial:
|
CheckSpecial:
|
||||||
; Always check IRQ special flags from Channel B (Ref page 5-24)
|
; Always check IRQ special flags from Channel B (Ref page 5-24)
|
||||||
; X is still 0 there.
|
; X is still 0 there.
|
||||||
rra SCCBREG,#RR_IRQ_STATUS
|
ldy #RR_IRQ_STATUS
|
||||||
|
jsr readSSCReg
|
||||||
|
|
||||||
and #IRQ_MASQ
|
and #IRQ_MASQ
|
||||||
cmp #IRQ_SPECIAL
|
cmp #IRQ_SPECIAL
|
||||||
@@ -628,19 +658,28 @@ CheckSpecial:
|
|||||||
|
|
||||||
; Clear exint
|
; Clear exint
|
||||||
ldx Channel
|
ldx Channel
|
||||||
wrr SCCBREG,#WR_INIT_CTRL,#INIT_CTRL_CLEAR_EIRQ
|
|
||||||
|
ldy #WR_INIT_CTRL
|
||||||
|
lda #INIT_CTRL_CLEAR_EIRQ
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
sec
|
sec
|
||||||
rts
|
rts
|
||||||
|
|
||||||
Flow: ldx Channel ; Assert flow control if buffer space too low
|
Flow: ldx Channel ; Assert flow control if buffer space too low
|
||||||
|
|
||||||
|
ldy #WR_TX_CTRL
|
||||||
lda RtsOff
|
lda RtsOff
|
||||||
wra SCCBREG,#WR_TX_CTRL
|
jsr writeSCCReg
|
||||||
|
|
||||||
sta Stopped
|
sta Stopped
|
||||||
sec ; Interrupt handled
|
sec ; Interrupt handled
|
||||||
Done: rts
|
Done: rts
|
||||||
|
|
||||||
Special:
|
Special:ldx Channel
|
||||||
rra SCCBREG,#RR_SPEC_COND_STATUS
|
ldy #RR_SPEC_COND_STATUS
|
||||||
|
jsr readSSCReg
|
||||||
|
|
||||||
tax
|
tax
|
||||||
and #SPEC_COND_FRAMING_ERR
|
and #SPEC_COND_FRAMING_ERR
|
||||||
bne BadChar
|
bne BadChar
|
||||||
@@ -648,7 +687,10 @@ Special:
|
|||||||
and #SPEC_COND_OVERRUN_ERR
|
and #SPEC_COND_OVERRUN_ERR
|
||||||
beq BadChar
|
beq BadChar
|
||||||
|
|
||||||
wrr SCCBREG,#WR_INIT_CTRL,#INIT_CTRL_CLEAR_ERR
|
ldy #WR_INIT_CTRL
|
||||||
|
lda #INIT_CTRL_CLEAR_ERR
|
||||||
|
jsr writeSCCReg
|
||||||
|
|
||||||
sec
|
sec
|
||||||
rts
|
rts
|
||||||
|
|
||||||
@@ -669,14 +711,19 @@ Again: lda SendFreeCnt ; Anything to send?
|
|||||||
lda Stopped ; Check for flow stopped
|
lda Stopped ; Check for flow stopped
|
||||||
bne Quit ; Bail out if it is
|
bne Quit ; Bail out if it is
|
||||||
|
|
||||||
|
Wait:
|
||||||
lda SCCBREG,x ; Check that we're ready to send
|
lda SCCBREG,x ; Check that we're ready to send
|
||||||
tay
|
tay
|
||||||
and #INIT_STATUS_READY
|
and #INIT_STATUS_READY
|
||||||
bne Send
|
beq NotReady
|
||||||
|
|
||||||
tya
|
tya
|
||||||
and #INIT_STATUS_RTS ; Ready to send
|
and #INIT_STATUS_RTS ; Ready to send
|
||||||
|
bne Send
|
||||||
|
|
||||||
|
NotReady:
|
||||||
bit tmp1 ; Keep trying if must try hard
|
bit tmp1 ; Keep trying if must try hard
|
||||||
bmi Again
|
bmi Wait
|
||||||
Quit: rts
|
Quit: rts
|
||||||
|
|
||||||
Send: ldy SendHead ; Send byte
|
Send: ldy SendHead ; Send byte
|
||||||
|
|||||||
Reference in New Issue
Block a user