( INTERRUPT DRIVEN SERIAL IO FOR HC11/65C52 ( RICK VANNORMAN ( NEW MICROS, INC ( 1601 CHALK HILL ROAD ( DALLAS, TX 75212 ( 214/339-2204 ( 14JUL95 COLD HEX 404 DP ! CODE-SUB CLI ( ENABLE INTERRUPTS 0E C, ( CLI ) 39 C, ( RTS ) END-CODE CODE-SUB SEI ( DISABLE INTERRUPTS 0F C, ( SEI ) 39 C, ( RTS ) END-CODE ( ACIA ADDRESSES ( ----- 8000 CONSTANT IER1 8001 CONSTANT STAT1 8003 CONSTANT DATA1 8004 CONSTANT IER2 8005 CONSTANT STAT2 8007 CONSTANT DATA2 ( BUFFERS=256 BYTES EACH ( CHANGE THESE ADDRESSES TO INCREASE/DECREASE BUFFER SIZES OR LOCATIONS 1000 CONSTANT IBUF ( INPUT BUFFER AND 1100 CONSTANT IEND ( ITS END 1100 CONSTANT OBUF ( OUTPUT BUFFER AND 1200 CONSTANT OEND ( ITS END ( THESE ARE HEAD AND TAIL POINTERS FOR THE BUFFERS. THEY MUST RESIDE ( IN RAM, BUT COULD BE INTERNAL RAM IF DESIRED 0FF0 CONSTANT IHEAD 0FF2 CONSTANT ITAIL 0FF4 CONSTANT OHEAD 0FF6 CONSTANT OTAIL 0FFF CONSTANT OSTAT ( SAVE A COPY OF THE ORIGINAL CODE VECTORS OF KEY, ETC SO WE CAN RESTORE ( THEM IF NEEDED. THE PLACE THEY ARE STORED IS NOT SACRED AND COULD BE ROM TIB 6 - 0FF8 6 CMOVE ( ----- ( RECEIVER ( A CHAR IS WAITING, PUT IT INTO BUFFER, WRAP WITH NO ERRORS ( CHARS ARE WRITTEN TO THE ADDRESS IN IHEAD. AFTER WRITING, IHEAD ( IS INCREMENTED [OR RESET]. IHEAD ALWAYS POINTS TO NEXT LOCATION CODE-SUB IRCV1 FE C, IHEAD , ( LDX IHEAD ;POINT TO THE NEXT BUFFER LOCATION B6 C, DATA1 , ( LDAA DATA1 ;READ THE CHAR A7 C, 0 C, ( STAA 0,X ;WRITE IT INTO THE BUFFER 08 C, ( INX ;INCREMENT THE POINTER 8C C, IEND , ( CPX #IERD ;CHECK FOR END OF BUFFER 26 C, 03 C, ( BNE X: ; CE C, IBUF , ( LDX #IBUF ;RESET POINTER FF C, IHEAD , ( X: STX IHEAD ;SAVE NEW POINTER VALUE 39 C, ( RTS ;AND RETURN END-CODE ( TRANSMITTER ( GETS CALLED WHEN THE CURRENT CHARACTER IS FINISHED. IF OHEAD IS ( EQUAL TO OTAIL, THERE ARE NO MORE CHARS, SO EXIT ( IF CHARS WAITING, WRITE THE NEXT ONE, INCREMENT TAIL, AND CONTINUE CODE-SUB IXMT1 FE C, OTAIL , ( LDX OTAIL ;GET TAIL POINTER BC C, OHEAD , ( CPX OHEAD ;HEAD. 26 C, 06 C, ( BNE Z ;IF HEAD=TAIL, RETURN 86 C, FF C, ( LDAA #FF B7 C, OSTAT , ( STAA OSTAT ;SET THE "IM DONE" FLAG 39 C, ( RTS A6 C, 00 C, ( Z: LDAA 0,X ;READ CHAR FROM BUFFER AT TAIL B7 C, DATA1 , ( STAA DATA1 ;WRITE TO SERIAL CHANNEL 08 C, ( INX ;INCREMENT POINTER 8C C, OEND , ( CPX #OEND ;CHECK FOR WRAP 26 C, 03 C, ( BEQ Y ;BRANCH IF OK CE C, OBUF , ( LDX #OBUF ;RESET TO START OF BUFFER FF C, OTAIL , ( Y: STX OTAIL ;SAVE NEW POINTER 39 C, ( RTS END-CODE ( SERVICE THE SCI INTERRUPT. WE ARE ONLY ALLOWING FOR TRANSMIT ( AND RECEIVE INTERRUPTS, SO THE ROUTINE IGNORES ALL OTHERS ( RUN IN CIRCLES UNTIL THE LOAD OF STAT HAS NO BITS OF INTEREST SET CODE-SUB ISERV B6 C, IER1 , ( W LDAA IER1 ;GET SERIAL STATUS 84 C, 41 C, ( ANDA #41 ;LEAVE ONLY RCV AND XMT STAT 27 C, 07 C, ( BEQ X ;EXIT IF NONE SET 84 C, 01 C, ( ANDA #01 ;CHECK THE RCV BIT 27 C, 04 C, ( BEQ Y ;IF NOT RCV, WE KNOW IT IS XMT BD C, ' IRCV1 @ , ( JSR IRCV ;GET A CHAR 3B C, ( X RTI BD C, ' IXMT1 @ , ( Y JSR IXMT ;SEND A CHAR 3B C, ( RTI END-CODE ( NON-INTERRUPT INTERFACES TO THE INTERRUPT ROUTINES ( ----- ( CHARS ARE WAITING IF IHEAD IS NOT EQUAL TO ITAIL CODE-SUB RCV? ( -- flag ) CC C, FFFF , ( LDD #-1 ;START WITH TRUE FE C, IHEAD , ( LDX IHEAD ;GET HEAD BC C, ITAIL , ( CPX ITAIL ;COMPARE TO TAIL 26 C, 03 C, ( BNE X ;IF NOT EQUAL, IS TRUE, GO RTS C3 C, 0001 , ( ADDD #1 ;EQUAL, FALSE, -1 + 1 = 0 18 C, 09 C, ( DEY ;MAKE ROOM ON THE STACK 18 C, 09 C, ( DEY ; 18 C, ED C, 00 C, ( STD 0,Y ;WRITE 16 BIT CHAR TO STACK 39 C, ( X: RTS ;RETURN END-CODE ( WAIT FOR A CHAR, READ IT, THEN INCREMENT ITAIL, WRAP IF NEEDED CODE-SUB RCV ( -- flag ) 4F C, ( CLRA ;ZERO FOR 16 BIT VALUE LATER 18 C, 09 C, ( DEY ;MAKE ROOM ON THE STACK 18 C, 09 C, ( DEY ; FE C, ITAIL , ( LDX ITAIL ;GET TAIL BC C, IHEAD , ( X: CPX IHEAD ;SPIN TIL HEAD <> TAIL 27 C, FB C, ( BEQ X ; E6 C, 00 C, ( LDAB 0,X ;GET CHAR INTO B 18 C, ED C, 00 C, ( STD 0,Y ;WRITE 16 BIT CHAR TO STACK 08 C, ( INX ;INCREMENT BUFFER POINTER 8C C, IEND , ( CPX #IEND ;CHECK FOR END OF BUFFER 26 C, 03 C, ( BNE Y: ; CE C, IBUF , ( LDX #IBUF ;RESET POINTER FF C, ITAIL , ( Y: STX ITAIL ;SAVE NEW POINTER VALUE 39 C, ( RTS END-CODE ( PUT A CHARACTER INTO THE OBUF FOR TRANSMISSION. THE TRANSMITTER IDLES ( WITH AN INTERRUPT PENDING, SO THE FIRST CHAR IS SENT BY JUST PUTTING ( IT IN THE BUFFER AND CALLING THE IXMT ROUTINE. CODE-SUB XMT ( char -- ) 18 C, A6 C, 01 C, ( LDAA 1,Y ;GET CHAR 18 C, 08 C, ( INY ;DISCARD CHARACTER 18 C, 08 C, ( INY FE C, OHEAD , ( LDX OHEAD ;GET WHERE TO PUT CHARS A7 C, 00 C, ( STAA 0,X ;WRITE INTO BUFFER AT X 08 C, ( INX ;INCREMENT BUFFER POINTER 8C C, OEND , ( CPX #OEND ;END OF BUFFER 26 C, 03 C, ( BNE Y: ;NO, SKIP RELOAD CE C, OBUF , ( LDX #OBUF ;RELOAD WITH START BC C, OTAIL , ( Y: CPX OTAIL ;COMPARE WHERE WE ARE TO TAIL 27 C, FB C, ( BEQ Y ;WAIT UNTIL BUFFER NOT FULL 0F C, ( SEI FF C, OHEAD , ( STX OHEAD ;AND SAVE IN POINTER B6 C, OSTAT , ( LDAA OSTAT ;CHECK TO SEE IF IXMT ACTIVE 27 C, 08 C, ( BEQ Z ;ZERO IS ACTIVE 86 C, 00 C, ( LDAA #00 ;FALSE B7 C, OSTAT , ( STAA OSTAT BD C, ' IXMT1 @ , ( JSR IXMT1 ;OUTPUT THE FIRST CHAR 0E C, ( X: CLI 39 C, ( RTS END-CODE ( SETUP TO USE INTERRUPT DRIVEN CONSOLE I/O : INIT SEI IBUF DUP IHEAD ! ITAIL ! OBUF DUP OHEAD ! OTAIL ! 7E B7E9 EEC! [ ' ISERV @ ] LITERAL DUP >< FF AND B7EA EEC! FF AND B7EB EEC! C1 IER1 C! FF OSTAT C! F0 STAT1 C! 0C STAT1 C! ; : NEW INIT TIB 6 - [ ' RCV @ ] LITERAL OVER ! 2+ [ ' XMT @ ] LITERAL OVER ! 2+ [ ' RCV? @ ] LITERAL SWAP ! CLI ; ( RESTORE POLLED CONSOLE I/O : OLD SEI 0FF8 TIB 6 - 6 CMOVE ;