Browse Source

Final Tweaks to KBD Interrupt Support

Related to PR #460
pull/470/head
Wayne Warthen 1 year ago
parent
commit
007e8a372a
  1. 67
      Source/HBIOS/kbd.asm
  2. 60
      Source/HBIOS/ps2iface.inc

67
Source/HBIOS/kbd.asm

@ -113,18 +113,14 @@ KBD_INIT:
CP KBDMODE_VRC ; VRC?
JR Z,KBD_INIT1 ; IF SO, MUST ASSUME PRESENT
;
#IF ((INTMODE == 2) & KBDINTS)
HB_DI ; DISABLE INTERRUPTS WHILE WE PROBE
#ENDIF
LD A,$AA ; CONTROLLER SELF TEST
CALL KBD_PUTCMD ; SEND IT
CALL KBD_GETDATA_P ; CONTROLLER SHOULD RESPOND WITH $55 (ACK)
HB_EI ; RESTORE INTERRUPTS
;
CP $55 ; IS IT THERE?
JR Z,KBD_INIT1 ; IF SO, CONTINUE
#IF ((INTMODE == 2) & KBDINTS)
HB_EI ; RESTORE INTERRUPTS
#ENDIF
PRTS(" NOT PRESENT$") ; DIAGNOSE PROBLEM
RET ; BAIL OUT
;
@ -133,7 +129,6 @@ KBD_INIT1:
; CALL KBDQINIT ; INITIALIZE QUEUE
LD HL,KBD_INT ; INSTALL VECTOR
LD (IVT(INT_PS2KB)),HL ; IVT INDEX
HB_EI ; ENABLE INTERUPTS
#ENDIF
PRTS(" MODE=$") ; TAG
LD A,(IY+KBD_MODE) ; GET MODE VALUE
@ -268,22 +263,22 @@ KBD_PUTDATA2:
RET
;
;__________________________________________________________________________________________________
KBD_GETDATA:
;
KBD_GETDATA_P:
;
; GET A RAW DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH TIMEOUT.
; DEPENDING ON ASSEMBLY CONFIGURATION KBD_GETDATA READS A BYTE FROM
; EITHER THE INTERRUPT QUEUE OR FROM THE KEYBOARD CONTROLLER PORT.
; KBD_GETDATA_P ALWAYS READS A BYTE FROM THE KEYBOARD CONTROLLER PORT.
;
LD B,KBD_WAITTO ; SETUP TO LOOP
KBD_GETDATA0:
CALL KBD_IST ; GET INPUT REGISTER STATUS
JR NZ,KBD_GETDATA1 ; BYTE PENDING, GO GET IT
KBD_GETDATA0_P:
CALL KBD_IST_P ; GET INPUT REGISTER STATUS
JR NZ,KBD_GETDATA1_P ; BYTE PENDING, GO GET IT
CALL DELAY ; WAIT A BIT
DJNZ KBD_GETDATA0 ; LOOP UNTIL COUNTER EXHAUSTED
DJNZ KBD_GETDATA0_P ; LOOP UNTIL COUNTER EXHAUSTED
XOR A ; NO DATA, RETURN ZERO
RET
KBD_GETDATA1:
CALL KBD_IN ; GET A KEY
KBD_GETDATA1_P:
CALL KBD_IN_P ; GET A KEY
#IF (KBDTRACE >= 2)
PUSH AF
CALL PC_SPACE
@ -294,36 +289,52 @@ KBD_GETDATA1:
OR A ; SET FLAGS
RET
;
;__________________________________________________________________________________________________
KBD_GETDATA_P:
KBD_GETDATA_Q:
;
; GET A RAW DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH TIMEOUT.
; KBD_GETDATA_P ALWAYS READS A BYTE FROM THE KEYBOARD CONTROLLER PORT.
; GET A QUEUED DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH TIMEOUT.
; KBD_GETDATA_Q ALWAYS READS A BYTE FROM THE KEYBOARD INTERRUPT QUEUE.
;
#IF ((INTMODE == 2) & KBDINTS))
;
LD B,KBD_WAITTO ; SETUP TO LOOP
KBD_GETDATA0_P:
CALL KBD_IST_P ; GET INPUT REGISTER STATUS
JR NZ,KBD_GETDATA1_P ; BYTE PENDING, GO GET IT
KBD_GETDATA0_Q:
CALL KBD_IST_Q ; GET INPUT REGISTER STATUS
JR NZ,KBD_GETDATA1_Q ; BYTE PENDING, GO GET IT
CALL DELAY ; WAIT A BIT
DJNZ KBD_GETDATA0_P ; LOOP UNTIL COUNTER EXHAUSTED
DJNZ KBD_GETDATA0_Q ; LOOP UNTIL COUNTER EXHAUSTED
XOR A ; NO DATA, RETURN ZERO
RET
KBD_GETDATA1_P:
CALL KBD_IN_P ; GET A KEY
#IF (KBDTRACE >= 2)
KBD_GETDATA1_Q:
CALL KBD_IN_Q ; GET A KEY
#IF (KBDTRACE >= 2)
PUSH AF
CALL PC_SPACE
CALL PC_LT
CALL PRTHEXBYTE
POP AF
#ENDIF
#ENDIF
OR A ; SET FLAGS
RET
;
#ENDIF
;
; GET A DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH TIMEOUT.
; DEPENDING ON ASSEMBLY CONFIGURATION KBD_GETDATA READS A BYTE FROM
; EITHER THE INTERRUPT QUEUE OR FROM THE KEYBOARD CONTROLLER PORT.
;
#IF ((INTMODE == 2) & KBDINTS))
KBD_GETDATA .EQU KBD_GETDATA_Q
KBD_GETDATA1 .EQU KBD_GETDATA1_Q
#ELSE
KBD_GETDATA .EQU KBD_GETDATA_P
KBD_GETDATA1 .EQU KBD_GETDATA1_P
#ENDIF
;
;__________________________________________________________________________________________________
KBD_GETDATAX:
;
; GET A RAW DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH NOTIMEOUT
; GET A DATA BYTE FROM KEYBOARD INTERFACE INTO A WITH NO TIMEOUT
; IF NOTHING AVAILABLE, RETURN 0.
;
CALL KBD_IST ; GET INPUT REGISTER STATUS
RET Z ; NOTHING THERE, DONE

60
Source/HBIOS/ps2iface.inc

@ -82,16 +82,24 @@ KBDQFULL: ; RETURN Z IF QUEUE IS FULL
SUB KBDQSIZ
RET
#ENDIF
;
;__________________________________________________________________________________________________
; KEYBOARD READ
;__________________________________________________________________________________________________
;
#IF ((INTMODE == 2) & KBDINTS))
; READ DIRECT FROM PORT
;
; RETURN A BYTE TO FROM KEYBOARD QUEUE
; NOTE THE QUEUE INDEX'S NEVER DECREASE IN SIZE.
KBD_IN_P:
LD C,(IY+KBD_DAT) ; DATA PORT
EZ80_IO
IN A,(C) ; GET THE DATA VALUE
RET
;
KBD_IN:
; READ FROM INTERRUPT QUEUE
;
#IF ((INTMODE == 2) & KBDINTS))
;
KBD_IN_Q:
KBDQPOP:
CALL KBDQLEN
RET Z ; EXIT IF THE QUEUE IS EMPTY
@ -110,38 +118,50 @@ KBDQPOP:
;
RET
;
#ELSE
#ENDIF
;
; RETURN A BYTE FROM THE KEYBOARD PORT
; RETURN A BYTE TO FROM KEYBOARD QUEUE
; NOTE THE QUEUE INDEX'S NEVER DECREASE IN SIZE.
;
KBD_IN:
#IF ((INTMODE == 2) & KBDINTS))
KBD_IN .EQU KBD_IN_Q
#ELSE
KBD_IN .EQU KBD_IN_P
#ENDIF
KBD_IN_P:
LD C,(IY+KBD_DAT) ; DATA PORT
EZ80_IO
IN A,(C) ; GET THE DATA VALUE
RET
;
;__________________________________________________________________________________________________
; KEYBOARD INPUT STATUS
;__________________________________________________________________________________________________
;
; DIRECT PORT STATUS READ
;
KBD_IST_P:
LD C,(IY+KBD_ST) ; STATUS PORT
EZ80_IO
IN A,(C) ; GET STATUS
AND $01 ; ISOLATE INPUT PENDING BIT
RET
;
; STATUS FROM INTERRUPT QUEUE
;
#IF ((INTMODE == 2) & KBDINTS))
KBD_IST:
;
KBD_IST_Q:
KBDQLEN: ; EXIT WITH NUMBER OF CHARACTERS IN QUEUE
LD A,(KBDQPUTX) ; Z STATUS AND ZERO IF NONE
LD HL,KBDQGETX
SUB (HL)
RET
;
#ENDIF
;
; RETURN INDICATION OF KEYBOARD DATA READY
;
#IF ((INTMODE == 2) & KBDINTS))
KBD_IST .EQU KBD_IST_Q
#ELSE
KBD_IST:
KBD_IST .EQU KBD_IST_P
#ENDIF
KBD_IST_P: ; A=0, Z SET FOR NOTHING PENDING, OTHERWISE DATA PENDING
LD C,(IY+KBD_ST) ; STATUS PORT
EZ80_IO
IN A,(C) ; GET STATUS
AND $01 ; ISOLATE INPUT PENDING BIT
RET
;
;__________________________________________________________________________________________________
; OUTPUT TO KEYBOARD COMMAND PORT

Loading…
Cancel
Save