;>>>>>>>>>>>>>>>>>>>>>>> REMDRIVER.TEXT >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> ; ; For an introduction see the file REMDR.DOC.TEXT ; ;---------------------------------------------------------------------- ; ; Serial card driver for Kermit-UCSD RUG/PT V1.0 ; ;---------------------------------------------------------------------- ; ; LABEL DEFINITIONS ; SLOT .EQU 20 ; various slot 2 labels SLT2MSB .EQU 0C2 SLOT2ADR .EQU 0C200 ; ; addresses of the offset bytes to calculate : FSTATUS .EQU SLOT2ADR+10 ; entry point for a serial firmware card status FREAD .EQU SLOT2ADR+0E ; " " " " " " " read ; DUMMY .EQU 0FFFF ; dummy address. will be filled in at cold boot. ; AP2COMM .EQU 0C08E+SLOT ; IBS AP2 serial card (6551 acia) command register. AP2STREG .EQU 0C08D+SLOT ; " " " " " " status " AP2IOREG .EQU 0C08C+SLOT ; " " " " " " I/O " ; COMSTREG .EQU 0C08E+SLOT ; Apple Com Card (6850 acia) status register. COMIOREG .EQU 0C08F+SLOT ; " " " " " I/O " ; HAYSTREG .EQU 0C086+SLOT ; Hayes Micromodem (6850 acia) status register. HAYIOREG .EQU 0C087+SLOT ; " " " " I/O " ; (Com Card registers may also work.) SPEAKER .EQU 0C030 SPCHAR .EQU 0BF1C ; system location for special keyboard character ; checking. SLT2TYP .EQU 0BF27+2 ; system location with serial card type ; 0 = no card. ; 1 = not recognized by system. ; 3 = Apple Com card ; California 7710 ASI1 card ; Hayes Micromodem card? ; 4 = serial card ( IBS AP2 ) ; 6 = Firmware card ( Super Serial Card ) ; NUMSERID .EQU 02-1 ; number(-1) of serial cards this driver checks. ; ACJVAFOLD .EQU 0E2 ; pointer to attached copy of BIOS jump vector. JVAFOLD .EQU 0EE ; pointer to BIOS jump vector. ; CONCK .EQU DUMMY ; address of BIOS keyboard check routine. RINIT .EQU DUMMY ; address of BIOS Remote Init routine. INPORTSTAT.EQU DUMMY ; address of this driver's Remote status routine. ; STATREC .EQU 00 ; temp. zero page pointer to status record. ; ;---------------------------------------------------------------------- ; .PROC REMDRIVER ; ;---------------------------------------------------------------------- JMP CONCKHDL ; The first 3 instructions of CONCK will ; be patched by SYSTEM.ATTACH to point here. ;---------------------------------------------------------------------- ; ; Calls to REMREAD, REMSTATUS and REMINIT will be handled here : ; TXA ; X=0 : Remote Read request. BEQ REMREAD CMP #004 ; X=4 : Remote Status request. BEQ REMSTATUS CMP #002 BNE ERROR ; X=2 : Remote Init request. ;---------------- ; ; Remote Init routine : ; LDX REMRPTR ; Empty remote input buffer. STX REMWPTR ; ( read-pointer = write-pointer ) LDX #000 ; zero buffer counter. STX BUFCOUNT PATCH3 JMP ONCERINIT ; if called for the first time ( cold boot ) then ; do the cold boot init routine. This routine ; patches the JMP instruction to NOP,NOP,NOP so ; later init calls (warm boot) will only empty the ; remin buffer. RTS ;---------------- ERROR LDX #003 ; for any other request return error code. RTS ;---------------------------------------------------------------------- ; ; Remote read routine ( reads only the remin buffer ). ; REMREAD JSR CONCKHDL ; check keyboard and remote input port. LDX REMRPTR ; if remin buffer is empty : keep checking remote CPX REMWPTR ; input port until something arrives. BEQ REMREAD INX ; read char from remin buffer, bump read-pointer STX REMRPTR ; decrease buffer count and put char in accu. DEC BUFCOUNT LDA REMBUF,X READY LDX #000 ; no error. RTS ;---------------------------------------------------------------------- ; ; Remote status routine ( implements UNITSTATUS. see KERM.DOC2.TEXT ) ; REMSTATUS JSR CONCKHDL ; check keyboard and remote input port. PLA ; save return address. STA RETURN PLA STA RETURN+1 ;------------ PLA ; save address of statusrecord on zero page. STA STATREC PLA STA STATREC+1 ;------------ PLA ; save controlword. STA CONTROLW PLA STA CONTROLW+1 ;------------ LDA RETURN+1 ; push return address back on stack. PHA LDA RETURN PHA ;---------------------------------- REMINSTAT LDX #000 ; zero registers. LDY #000 ;---------------- ; ; Decipher Controlword. ; LDA CONTROLW ; if bit 1 = 0 then the purpose is statusrequest. AND #002 ; if bit 1 = 1 then the purpose is controlrequest. ; bit 0 (direction) is not checked. BNE REMCNTROL LDA CONTROLW+1 ; if bit 13 = 0 then a "normal" request. AND #020 BNE PEEK ; if bit 13 = 1 then a "special" request. ;---------------- ; ; Normal Status Request: load in statusrecord ( 2 bytes ) the number ; of characters currently in the remin buffer. ; LDA BUFCOUNT LOAD STA @STATREC,Y LDA #00 INY STA @STATREC,Y RTS ;--------------- ; ; Special Status Request: statusrecord first to bytes contain an ; address. Return in statusrecord last 2 bytes the value of the ; requested location. ; PEEK LDA @STATREC,Y STA ADR1+1 INY LDA @STATREC,Y STA ADR1+2 ADR1 LDA DUMMY ; DUMMY will be changed to the requested address. INY BNE LOAD ; value returned is a Pascal Integer! ;---------------- ; ; Control Requests : ; REMCNTROL LDA CONTROLW+1 ; if bit 13 = 0 then a normal controlrequest. AND #020 BNE POKE ;---------------- ; Normal Control Request ; ; first byte of statusrecord contains ; 0..3 : store this byte in SPCHAR. ; SPCHAR=0 : CONCK checks class 1 and class 2 special chars. ; SPCHAR=1 : " " only class 2 " " ; SPCHAR=2 : " " only class 1 " " ; SPCHAR=3 : " " no " " ; ( see KERM.DOC2.TEXT ) ; ; first byte of statusrecord contains ; 4 : 7 bit characters in remin buffer. ; 5 : 8 bit " " " " ; LDA @STATREC,Y CMP #004 BCS BIT78 STA SPCHAR RTS ;----------------- ; ; Special Control Request : statusrecord first 2 bytes contain a ; address. Statusrecord third byte contains the value the location ; should contain. ; POKE LDA @STATREC,Y STA ADR2+1 INY LDA @STATREC,Y STA ADR2+2 INY LDA @STATREC,Y ADR2 STA DUMMY ; DUMMY will be filled in at run time. RTS ;---------------- BIT78 CMP #005 ; set the flag LOCALPAR for the remin input routine. BEQ EIGHTBIT ; default startup setting is seven bit remin chars. LDA #000 BEQ SETLOCPAR EIGHTBIT LDA #080 SETLOCPAR STA LOCALPAR RTS ;---------------------------------------------------------------------- ; ; Calls to the system CONCK routine come here. A call to this ; driver's remin check routine is inserted so that every time the system ; does any I/O call both the keyboard and the remote input port will be checked. ; CONCKHDL PHP ; repeat first 6 instructions of CONCK. PHA TXA PHA TYA PHA JSR REMINCK ; check the remote input port. PATCH2 JMP CONCK ; enter CONCK at start+6 and return from there to ; system. The 2 bytes after the JMP will be filled ; in at first initialization of this driver. ;---------------------------------------------------------------------- ; ; REMINCK : checks remote input port. If it finds a char, it will put it ; in the remin buffer. ; REMINCK JSR INPORTST ; checks remote inputport. Carry is set when a char ; is waiting. Returns with char in accu. ; The address INPORTST will be filled in at cold boot ; initialization time to point at the correct status ; routine. BCC EMPTY BIT LOCALPAR ; depending on LOCALPAR : strip bit 8 of incomimg char. BMI NOCHANGE AND #07F NOCHANGE LDX REMWPTR ; bump writepointer. INX CPX REMRPTR ; if writepointer = readpointer then buffer is full! BNE BUFOK ;---------- PHA ; in case of buffer overflow : TXA ; give a high pitched bell sound. PHA BELL LDY #060 BELL1 LDX #020 BELL2 DEX BNE BELL2 LDA SPEAKER DEY BNE BELL1 LDA #0FF ; set buffer count to -1. STA BUFCOUNT ; buffer will thus be emptied. PLA TAX PLA ;------------ BUFOK STX REMWPTR ; save new writepointer. INC BUFCOUNT ; bump buffer count and STA REMBUF,X ; store received char in buffer. EMPTY RTS ;----------------------------------------------------------------------- ; ; Remote status routines for different serial cards. ; Only one of these is active after cold boot initialization. ; ; The status routine returns with the received character (if any) in accu ; and with the carry set if a character was received. ; ;----------------------------------------------------------------------- ; ; Status routine for an IBS AP2 serial card with a 6551 acia. ; AP2STAT LDA AP2COMM ORA #008 STA AP2COMM LDA AP2STREG CLC AND #028 EOR #008 BNE NOTHING1 SEC LDA AP2IOREG NOTHING1 PHA LDA AP2COMM AND #0F3 STA AP2COMM PLA RTS ;---------------------------------------------------------------------- ; ; Status routine for Hayes Micromodem Card with a 6850 acia. ; ( Identical to Apple Com Card. Can probably be replaced by Com Card routine ; if Hayes card is also recognized by the Pascal system as an Apple Com ; card. ) ; HAYESTAT LDA HAYSTREG LSR A BCC NOTHING2 LDA HAYIOREG NOTHING2 RTS ;----------------------------------------------------------------------- ; ; Status routine for an Apple Communications Card or California 7710 ; ASI1 card , both with a 6850 acia. ; COMSTAT LDA COMSTREG LSR A BCC NOTHING3 LDA COMIOREG NOTHING3 RTS ;----------------------------------------------------------------------- ; ; Status routine for a "firmware" card like the Apple Super Serial Card. ; Firmware cards have there own status and read routines in ROM. ; The final addresses of the status and read routines will be calculated ; at cold boot initialization and filled in directly here at PATCH4 and ; PATCH5. ; FIRMSTAT LDX #SLT2MSB ; do the required initialization. LDY #SLOT STY 06F8 STA 0CFFF LDA SLOT2ADR LDA #001 PATCH4 JSR FSTATUS BCC NOTHING LDX #SLT2MSB PATCH5 JSR FREAD ; returns with char in accu. SEC NOTHING RTS ;------------------------ ; ; If you have extended FINDSER to recognize more serial cards then insert ; here the code for the new serial card's status routine. ; ;---------------------------------------------------------------------------- ; ; Local variables ; RETURN .WORD 00 LOCALPAR .BYTE 00 REMRPTR .BYTE 00 REMWPTR .BYTE 00 CONTROLW .WORD 00 BUFCOUNT .BYTE 00 ; ; ;---------------------------------------------------------------------------- ;---------------------------------------------------------------------------- ; ; START OF THE REMIN BUFFER AREA ; ; Contains cold boot initialization code. ; REMBUF .BYTE 00 ;---------------------------------------------------------------------------- ; PBOTABLE .BYTE 01.,02.,04.,05.,07.,08.,28.,29.,43.,44. ; offset bytes to patch ; back the BIOS jump ; vector. AP2STPTR .WORD AP2STAT ; pointers to the various status routines. COMSTPTR .WORD COMSTAT HAYESTPTR.WORD HAYESTAT FIRMSTPTR.WORD FIRMSTAT ; OFFSET1 .BYTE 04E,01A ; offset and identification bytes to recognize OFFSET2 .BYTE 065,02A ; different serial cards : IDBYTE1 .BYTE 04D,09C ; first row = IBS AP2 serial card. IDBYTE2 .BYTE 0A3,051 ; second row = Hayes Micromodem card. ; ; Insert more offset and Id-bytes for other serial cards here. ; Adjust NUMSERID correspondingly. ; ;------------------------- ONCERINIT LDX #009 ; cold boot init jumps here. PATCHBACK LDA PBOTABLE,X ; get normal BIOS addresses from the attached copy TAY ; and patch back the BIOS jump vector, except LDA @ACJVAFOLD,Y ; remote status, read and init. STA @JVAFOLD,Y DEX BPL PATCHBACK ;-------------------------- CLC ; get address of CONCK, add 6 to it and patch LDY #055. ; this code. LDA @ACJVAFOLD,Y ADC #006 STA PATCH2+1 INY LDA @ACJVAFOLD,Y ADC #000 STA PATCH2+2 ;-------------------------- LDY #031. ; get address of Remote INIT and patch this code. LDA @ACJVAFOLD,Y STA PATCH1+1 INY LDA @ACJVAFOLD,Y STA PATCH1+2 ;-------------------------- LDA #0EA ; patch the instruction JMP ONCERINIT to NOP(3x). STA PATCH3 ; ONCERINIT will be done only once. STA PATCH3+1 STA PATCH3+2 ;-------------------------- ;-------------------------- LDA SLT2TYP ; find out which serial card there is in slot 2. CMP #003 BNE NXTTYP2 LDX COMSTPTR ; Apple Com Card : save pointer to status routine LDY COMSTPTR+1 ; in X and Y registers. BNE TORINIT NXTTYP2 CMP #006 BNE NXTTYP3 LDA FSTATUS ; firmware card : get offset bytes from card's ROM STA PATCH4+1 ; and patch the status and read routine entry LDA FREAD ; points in the FIRMSTAT routine. STA PATCH5+1 LDX FIRMSTPTR LDY FIRMSTPTR+1 BNE TORINIT NXTTYP3 CMP #004 BNE NOTKNOWN JSR FINDSER ; if it is a serial card try to recognize it. BMI NOTKNOWN ; FINDSER returns with minus flag on if card was TYA ; not recognized. Y = ID number of serial card. BEQ AP2SER ; Y=0 : IBS AP2 card. HAYSER CMP #001 ; Y=1 : Hayes micromodem card. ; If Hayes card is already recognized as an Apple ; Com card (I don't know), then this part can be ; deleted. BNE NOTKNOWN ; If FINDSER recognizes more serial cards then ; insert here extra code for other cards. LDX HAYESTPTR LDY HAYESTPTR+1 BNE TORINIT AP2SER LDX AP2STPTR LDY AP2STPTR+1 ;-------------------------- TORINIT STX REMINCK+1 ; Patch INPORTSTAT to point to the adress of status STY REMINCK+2 ; routine. PATCH1 JMP RINIT ; Initialize once the serial card according to the ; card's normal init routine. NOTKNOWN LDX #009 ; If card was not recognized then return to system LDY #SLOT ; with error code 9 ( volume not found ). RTS ;------------------------------------------------------------------------- ; ; Serial card recognition routine. ; ; Checks two unique bytes in the cards ROM space ( C200-C2FF ). ; FINDSER LDY #NUMSERID FNDNEXT1 LDA OFFSET1,Y TAX LDA SLOT2ADR,X CMP IDBYTE1,Y BEQ CONFIRM FNDNEXT2 DEY BPL FNDNEXT1 RTS CONFIRM LDA OFFSET2,Y TAX LDA SLOT2ADR,X CMP IDBYTE2,Y BNE FNDNEXT2 CODEND RTS ;--------------------------------------------------------------------------- .BLOCK 256.+REMBUF-CODEND,00 ; adjusts buffer if init codelength ; is changed. ;--------------------------------------------------------------------------- .END