{ File: [Iris]DLion>RS232CMisc.asm Modification History: Dennis DEG : 1-Sep-84 17:13:02 Add copyright notice. Michael MAT : 3-Jan-84 15:04:21 Add Async Flow Control Dennis DEG : 1-Dec-83 18:22:25 More on fix for DTR/RTS glitch. Dennis DEG : 9-Oct-83 11:02:36 Added Siemens 9750 support. Dennis DEG : 12-Jul-83 23:44:37 Do naked notify after simple command (improve performance). Dennis DEG : 1-Jul-83 13:33:14 .Put in fix for DTR/RTS glitch on SetParameters Dennis DEG : 30-Jun-83 11:12:50 meet IBM specs. Dennis DEG : 26-Jun-83 17:03:12 to incorporate changes made by AeF AEF : 10-Jun-83 15:42:21: Add GetTaskStartAddress stuff for fixing CTS naked notify. Also incorporate changes made by Allen TSang and Tommy TXC : 17-May-83 9:11:09 Initialization of SIO for RS232C CrF CRF : 9-Jan-83 19:04:18: Fix send break command. Jim JXF : October 15, 1982 10:36 AM: Test for Voice command. Jim JXF : September 8, 1982 4:56 PM: Change handling of abort. Jim JXF : August 5, 1982 10:36 AM: new IO Page format Created by Jim JXF : March 25, 1982 1:53 PM } { Copyright (C) 1982, 1983, 1984 by Xerox Corporation. All rights reserved.} Get "SysDefs" Get "CommonDefs" Get "RS232CDefs" IMP AsyncRS232CInterrupt ;From Rs232CInterrupts IMP AbortGetFlag ;From RS232CGet IMP AbortPutFlag ;From RS232CPut IMP AsyncGetLoop ;From RS232CGet IMP AsynchronousDivisor ;From SIOSubs IMP BEL1 ;From BisyncInterrupts IMP BEL6 ;From BisyncInput IMP BisyncGetLoop ;From RS232CGet IMP BisyncRS232CInterrupt ;From Rs232CInterrupts IMP BisyncTimerTable ;From SIOSubs IMP Copy ;From CPSubs IMP DisableRST ;From Common IMP DisableRxCRC1 ;From BisyncInput IMP DisableRxCRC2 ;From BisyncInput IMP DisableRxCRC3 ;From BisyncInput IMP DisableTxCRC1 ;From BisyncInterrupts IMP DoNakedNotify ;From Common IMP EnableRST ;From Common IMP EnableRxCRC1 ;From BisyncInput IMP EnableRxCRC2 ;From BisyncInput IMP EnableRxCRC3 ;From BisyncInput IMP EnableRxCRC4 ;From BisyncInput IMP EnableTxCRC1 ;From BisyncInterrupts IMP EndOfBisyncFrame ;From BisyncInput IMP ENQ1 ;From BisyncInterrupts IMP ENQ2 ;From BisyncInterrupts IMP ENQ4 ;From BisyncInterrupts IMP ENQ6 ;From BisyncInput IMP ENQ9 ;From BisyncInput IMP ENQ10 ;From BisyncInput IMP ENQ11 ;From BisyncInput IMP ENQ12 ;From BisyncInterrupts IMP EnterHuntMode1 ;From BisyncInput IMP EnterHuntMode2 ;From BisyncInput IMP EOT1 ;From BisyncInterrupts IMP EOT6 ;From BisyncInput IMP EOTEndFrameSwitch ;From BisyncInput IMP EOT3270 ;From BisyncInput IMP ETB2 ;From BisyncInterrupts IMP ETB4 ;From BisyncInterrupts IMP ETB5 ;From BisyncInterrupts IMP ETB6 ;From BisyncInterrupts IMP ETB7 ;From BisyncInput IMP ETB8 ;From BisyncInput IMP ETB9 ;From BisyncInput IMP ETB10 ;From BisyncInput IMP ETB11 ;From BisyncInput IMP ETB12 ;From BisyncInterrupts IMP FCState ;From RS232CInterrupts IMP FlowControlFlag ;From RS232CInterrupts IMP GetModeSwitch ;From RS232CGet IMP GetTaskResumeAddress ;From RS232CGet IMP GetTaskStartAddress ;From RS232CGet CTS fix. IMP GetTaskQuiet ;From RS232CGet IMP HLPlus2A ;From SIOSubs IMP LastBufferFlag ;From RS232CInterrupts IMP NAK1 ;From BisyncInterrupts IMP NAK6 ;From BisyncInput IMP OverflowFlag ;From RS232CInterrupts IMP OneSecondTimerLow ;From BisyncInterrupts IMP OneSecondTimerHigh ;From BisyncInterrupts IMP PortBusyFlag ;From CPSubs IMP PrevAsyncDCD ;From RS232CInterrupts IMP PrevCTS ;From RS232CInterrupts IMP PrevBisyncDCD ;From RS232CInterrupts IMP PrevSdlcDCD ;From BisyncInterrupts IMP PutAsyncMode ;From RS232CPut IMP PutBisyncMode ;From RS232CPut IMP PutSdlcMode ;From RS232CPut IMP PutModeSwitch ;From RS232CPut IMP PutTaskResumeAddress ;From RS232CPut IMP PutTaskQuiet ;From RS232CPut IMP ReadCPBuffer ;From CPSubs IMP ResetChannels ;From SIOSubs IMP RS232CGetFlag ;From BookKeepingTask IMP RS232CInterruptSwitch ;From Common IMP RS232CPutFlag ;From BookKeepingTask IMP RS232CMiscFlag ;From BookKeepingTask IMP RS232CMiscCommand ;From BookKeepingTask IMP RxFIFO IMP RxFifoEnd IMP RxInitBiSyncInput ;From BisyncInput IMP SdlcGetLoop ;From RS232CGet IMP SdlcRS232CInterrupt ;From Rs232CInterrupts IMP SetAsyncTimer ;From RS232CSubs IMP SetBaudRate ;From SIOSubs IMP SetRS366 ;From SIOSubs IMP StartGetTask ;From RS232CGet IMP StartPutTask ;From RS232CPut IMP SYN1 ;From BisyncInterrupts IMP SYN2 ;From BisyncInterrupts IMP SYN3 ;From BisyncInterrupts IMP SYN4 ;From BisyncInterrupts IMP SYN5 ;From BisyncInterrupts IMP SYN6 ;From BisyncInterrupts IMP SYN7 ;From BisyncInput IMP SYN8 ;From BisyncInput IMP SYN9 ;From BisyncInput IMP SYN10 ;From BisyncInput IMP SYN11 ;From BisyncInput IMP SYN12 ;From BisyncInterrupts IMP SYN13 ;From BisyncInput 6/30/83 IMP SYN14 ;From BisyncInput 6/30/83 IMP SynchronousDivisor ;From SIOSubs IMP TestStatusChange ;From RS232CGet CTS fix. IMP TxInitBiSyncInterrupts {IMP VoiceCommandTask} ;From VoiceTask IMP WriteCPBuffer ;From CPSubs IMP XoffChar IMP XoffReceivedFlag IMP XonChar IMP ZeroCommand ;From Common EXP CurrentCharLengthMask ;Parameter EXP CurrentCorrespondent EXP CurrentRS366Status ;Parameter EXP CurrentSyncCharacter ;Parameter EXP CurrentSyncCount ;Parameter EXP RS232CMiscTask ;Parameter EXP RS232CMode ;Parameter EXP RS232CTaskWakeMask EXP RxWR1 ;Parameter EXP RxWR3 ;Parameter EXP RxWR4 ;Parameter EXP TxWR1 ;Parameter EXP TxWR4 ;Parameter EXP TxWR5 ;Parameter {EXP VoiceSwitch} ; { Commented out until we can get Voice to work with the rest of Domino. DB opJMP VoiceSwitch: DW RS232CMiscTask ;Set by StopVoiceBox ; DW VoiceCommandTask Set by first voice command } RS232CMiscTask: LDA PortBusyFlag ORA A JNZ MiscYield DB opJMP MiscTaskResumeAddress: DW CheckMiscFlag ; JMP WaitForGetAbort ; JMP WaitForPutAbort CheckMiscFlag: {RS232CMiscFlag is the same word as VoiceCommand. For RS232C commands, the high order bit is set. For voice commands, the high order bit is zero.} LDA RS232CMiscFlag ORA A JZ MiscYield JM MiscCommand {Continue if this is the first voice command. From now until we get a StopVoiceBox, we will skip RS232CMiscTask, RS232CGet, and RS232CPut.} { LXI H,VoiceCommandTask SHLD VoiceSwitch PCHL ;Jump to VoiceCommandTask } JMP MiscYield ;Temporarily Yield until voice works. MiscCommand: LXI H,ReadMiscCSB CALL ReadCPBuffer {The Misc Task implements the following commands. The command numbers are defined in IOPInterfaceDefs.mesa.} LDA RS232CMiscCommand ORA A JZ DoOn ;Zero is On command CPI 1 JZ DoOff CPI 2 JZ DoBreakOn CPI 3 JZ DoBreakOff CPI 4 JZ DoAbortInput CPI 5 JZ DoAbortOutput CPI 6 JZ DoSetRS366Status CPI 7 JZ DoGetStatus CPI 8 JZ DoMajorSetParameters CPI 14 JZ DoMinorSetParameters CPI 15 JZ DoSetChannelResetFlag {1 Jul 83} {BREAK} ;treat all other commands as a Nop or break for debugging {Continue if IOP Command is invalid.} JMP ResetMiscTaskFlag ; CurrentCorrespondent: DB 0 RS232CMiscCSB: RS232CParameter4: DS 2 ;1402C RS232CParameter3: DS 1 ;1402D low RS232CParameter3Hi: DS 1 ;1402D high RS232CParameter2: DS 1 ;1402E RS232CParameter2Hi: DS 1 ;1402E high RS232CParameter1: DS 1 ;1402F low RS232CParameter1Hi: DS 1 ;1402F high RS232CTaskWakeMask: DS 2 ;14030 RS232CParameterFlowControl: DS 2 RS232CParameterXOn: DS 2 RS232CParameterXoff: DS 2 RS232CParameter: DS 1 ;14036 low RS232CParameterHi: DS 1 ;14036 high RS232CDeviceStatus: DS 1 ;14035 low RS232CDeviceStatusHi: DS 1 ;14035 high CurrentParameters: ; Channel A is the Rx Channel on the Z80 SIO chip RxWR1: DB 0 RxWR3: DB 0 RxWR4: DB 0 RxWR5: DB 0 ; Channel B is the Rx Channel on the Z80 SIO chip TxWR1: DB 0 TxWR4: DB 0 TxWR5: DB 0 CurrentCode: DB 0 ;0 = Ascii, 1 = Ebcdic {The following characters will be replaced by the Ebcdic or Ascii values, depending on the code used.} BEL: DB 0 ENQ: DB 0 EOT: DB 0 ETB: DB 0 NAK: DB 0 SYN: DB 0 CurrentRS366Status: DB 0 ; RS366 Test Status Storage (LocalTim+SIOLpEn) CurrentParametersSize EQU CurrentRS366Status-RxWR1+1 SdlcDefaultParameters: { Default Values for Sdlc mode. These will be moved into CurrentParameters above.} {RxWR1:} DB IntOnAllRxCharacters+ExternalIntEnable {RxWR3:} DB RxCRCEnable {RxWR4:} DB X1ClockMode+SdlcMode {RxWR5:} DB 0 {TxWR1:} DB StatusAffectsVector+ExternalIntEnable+TxIntEnable {TxWR4:} DB X1ClockMode+SdlcMode {TxWR5:} DB TxCRCEnable+TxEnable {Code:} DB 0 {BEL:} DB 0 {ENQ:} DB 0 {EOT:} DB 0 {ETB:} DB 0 {NAK:} DB 0 {SYN:} DB 0 {Rs366Status:} DB 0 AsyncDefaultParameters: { Default Values for Async mode. These will be moved into CurrentParameters above.} {RxWR1:} DB IntOnAllRxCharacters+ExternalIntEnable {RxWR3:} DB 0 {RxWR4:} DB X16ClockMode {RxWR5:} DB 0 {TxWR1:} DB StatusAffectsVector+ExternalIntEnable+TxIntEnable {TxWR4:} DB X16ClockMode {TxWR5:} DB TxEnable {Code:} DB 0 {BEL:} DB 0 {ENQ:} DB 0 {EOT:} DB 0 {ETB:} DB 0 {NAK:} DB 0 {SYN:} DB 0 {RS366Status:} DB LocalTim BisyncDefaultParameters: {Default values for Bisync mode. These will be moved into CurrentParameters above.} {RxWR1:} DB IntOnAllRxCharacters+ExternalIntEnable {RxWR3:} DB 0 {RxWR4:} DB X1ClockMode+SyncCharacter16Bits {RxWR5:} DB BisyncCRC {TxWR1:} DB StatusAffectsVector+ExternalIntEnable+TxIntEnable {TxWR4:} DB X1ClockMode+SyncCharacter16Bits {TxWR5:} DB TxEnable+BisyncCRC {Code:} DB Ebicdic {BEL:} DB EbcdicBELL {ENQ:} DB EbcdicENQ {EOT:} DB EbcdicEOT {ETB:} DB EbcdicETB {NAK:} DB EbcdicNAK {SYN:} DB EbcdicSYN {RS366Status:} DB 0 ; { Other Parameters} RS232CMode: DB 0 ; current mode (0=Sdlc, 1=Bisync, 2=Async) CurrentCorrespondents: DB 0 {0 = xerox800 1 = xerox850 2 = system6 3 = cmcII 4 = ttyHost 5 = oisSystemElement 6 = ibm3270Host 7 = ibm2770Host 8 = ibm6670Host 9 = ibm6670 10 = xerox860 11 = oisSystemElementBSC 12 = siemens9750} CurrentSyncCount: DB 0 ;Set from RS232CParameter2 CurrentSyncCharacter: DB 0 ;Set from RS232CParameter3 CurrentBaudRate: DB 0 ;Set from RS232CParameter1 {0 = 50 Baud 1 = 75 Baud 2 = 110 Baud 3 = 134.5 Baud 4 = 150 Baud 5 = 300 Baud 6 = 600 Baud 7 = 1200 Baud 8 = 2400 Baud 9 = 3600 Baud 10 = 4800 Baud 11 = 7200 Baud 12 = 9600 Baud 13 = 19200 Baud 14 = 48000 Baud 15 = 56000 Baud} {CurrentCharLengthMask will be replaced by one of the entries from the table below.} CurrentCharLengthMask: DB 0FFH ; character length mask CurrentCharLengthMaskTable: DB 01FH ; 5 bits DB 03FH ; 6 bits DB 07FH ; 7 bits DB 0FFH ; 8 bits {This character length table is set up for WR3.} CharLengthTable: DB 0 ; 0=Character Length 5 of SIO Command DB 80H ; 80H=Character Length 6 of SIO Command DB 40H ; 40H=Character Length 7 of SIO Command DB 0C0H ; 0C0H=Character Length 8 of SIO Command AsciiCodeTable: {Code:} DB Ascii {BEL:} DB AsciiBELL {ENQ:} DB AsciiENQ {EOT:} DB AsciiEOT {ETB:} DB AsciiETB {NAK:} DB AsciiNAK {SYN:} DB AsciiSYN AsciiCodeTableSize EQU 7 ReadMiscCSB: DW RS232CMiscCSBLoc ; CP Buffer Pointer Low DW CPIOPageHi ; CP Buffer Pointer Hi DW RS232CMiscCSBSize ; CP Buffer Count in bytes DW RS232CMiscCSB ; Pointer to IOP Buffer ZeroMiscFlag: DW RS232CMiscFlagLoc ; CP Buffer Pointer Low DW CPIOPageHi ; CP Buffer Pointer Hi DW 2 ; CP Buffer Count in bytes DW ZeroCommand ; Pointer to IOP Buffer SendDeviceStatus: ; to transfer RS232C Device Status to CP IOPage DW RS232CDeviceStatusLoc ; CP Buffer Pointer Low DW CPIOPageHi ; CP Buffer Pointer Hi DW RS232CDeviceStatusSize ; CP Buffer Count in bytes DW RS232CDeviceStatus ; Pointer to IOP Buffer SendParameter: ; to transfer RS232C Parameter Outcome to IOPage DW RS232CParameterLoc ; CP Buffer Pointer Low DW CPIOPageHi ; CP Buffer Pointer Hi DW RS232CParameterSize ; CP Buffer Count in bytes DW RS232CParameter ; Pointer to IOP Buffer ; { Local subroutines} CopyParameters: {Copy default parameters into CurrentParameters. On entry, DE points to default parameters, and HL points to the address to be used for RS232C interrupts. Set up the interrupt table address first.} SHLD RS232CInterruptSwitch XCHG ;HL ¬ address of parameters LXI D,CurrentParameters MVI A,CurrentParametersSize JMP Copy ;Copy and RET CheckResetRingHeard: {If ResetRingHeard bit is set, reset the RingHeardLatch.} LDA RS232CParameter2Hi ; Reset Ring Hard, if required ANI CPRRHMask RZ XRA A STA RingHeardLatch RET UpdateTxWR5: {This procedure is called whenever WR5 changes. We update the value of WR5 with and without CRCEnable for the Bisync interrupt routine.} STA TxWR5 ;Update WR5 STA DisableTxCRC1 ORI TxCRCEnable STA EnableTxCRC1 RET ; DoOn: MVI A,Rst65DisableMsk CALL EnableRST {Initialize state of Clear To Send and Data Carrier Detect so we will know if they change.} XRA A STA PrevAsyncDCD STA PrevCTS STA PrevBisyncDCD STA PrevSdlcDCD {Calculate End of Buffer Address and store it for future use} LXI D,RxFIFO ;calculate end of RxFifo LXI H,RxFifoSize DAD D SHLD RxFifoEnd DoSetChannelResetFlag: {1 Jul 83} JMP ResetMiscTaskFlag DoAbortInput: STA AbortGetFlag CALL SetChannelResetFlag LXI H,WaitForGetAbort JMP SaveMiscResumeAddressAndYield WaitForGetAbort: LDA AbortGetFlag ; the last thing it does is reset the abort flag ORA A JNZ MiscYield ; if not stopped, keep waiting STA OverflowFlag ;Reset the overflow flag. JMP RestoreMiscResumeAddress ; if so, quit now. {Break key handling -- a break is defined to be holding the serial data transmit line low for 190 milliseconds or more. To send a break, you have to tell the SIO chip to hold the transmit line low, wait for 190 milliseconds or more, and then tell the SIO chip to stop holding the line low. The SIO chip will hold the transmit line low if you turn on the "Send Break" bit in write register 5. It stops holding it low when you turn off the bit. The waiting is done in the Dandelion RS232C head.} DoBreakOff: LXI H,TxCont+8000H ;HL points to TxCont register LDA TxWR5 DI MVI M,PointToWR5 ;Send address of WR5 MOV M,A ;Send turn break off command EI JMP ResetMiscTaskFlag DoBreakOn: LXI H,TxCont+8000H ;HL points to TxCont register LDA TxWR5 ORI SendBreak DI MVI M,PointToWR5 ;Send address of WR5 MOV M,A ;Send turn break on command EI {Now abort any puts in progress -- fall through to DoAbortOutput} DoAbortOutput: STA AbortPutFlag LXI H,WaitForPutAbort JMP SaveMiscResumeAddressAndYield WaitForPutAbort: LDA AbortPutFlag ORA A ; the last thing it does is reset the abort flag JNZ MiscYield ; if not stopped, keep waiting RestoreMiscResumeAddress: LXI H,CheckMiscFlag SHLD MiscTaskResumeAddress JMP ResetMiscTaskFlag ; if so, quit now. DoOff: MVI A,Rst65DisableMsk CALL DisableRST ; Disable Rst 6.5 interrupt CALL ResetChannels LXI H,GetTaskQuiet SHLD GetTaskStartAddress ; Fix for CTS LXI H,PutTaskQuiet SHLD GetTaskResumeAddress JMP ResetMiscTaskFlag ; DoMajorSetParameters: {Set CurrentParameters depending on RS232CParameter2Hi: (mask 3): 0 => Sdlc 1 => Bisync 2 => Async } {Set the mode.} LDA RS232CParameter2Hi ANI CPLineTypeMask STA RS232CMode JZ SetSdlcParameters ;Zero is Sdlc mode CPI CPBisyncMode JZ SetBisyncParameters SetAsyncParameters: {Set up the Async timer.} LHLD RS232CParameter4 ; get user-supplied timeout value MVI A,1 ; Set timer not running CALL SetAsyncTimer LXI H, PutAsyncMode SHLD PutModeSwitch ; Set JMP instruction LXI H,AsyncGetLoop SHLD GetModeSwitch LXI H,AsyncRS232CInterrupt LXI D,AsyncDefaultParameters CALL CopyParameters {GEt Flow control flag and characters} LDA RS232CParameterFlowControl STA FlowControlFlag LDA RS232CParameterXOn STA XonChar LDA RS232CParameterXoff STA XoffChar XRA A ;Initialize Flags to False STA XoffReceivedFlag STA LastBufferFlag STA FCState {In Async mode, check for one or two Stop bits and set up WR4 depending on RS232CParameter2Hi: (mask 4): 0 => 1 Stop bit 1 => 2 Stop bits} MVI D,StopBits1 LDA RS232CParameter2Hi ANI CPStopBitsMask JZ SetStopBits MVI D,StopBits2 SetStopBits: LDA TxWR4 ORA D STA TxWR4 LDA RxWR4 ORA D STA RxWR4 LXI H,AsynchronousDivisor JMP SetBaud SetBisyncParameters: LXI H, PutBisyncMode SHLD PutModeSwitch ; Set JMP instruction LXI H,BisyncGetLoop SHLD GetModeSwitch LXI H,BisyncRS232CInterrupt LXI D,BisyncDefaultParameters JMP CommonSynchParamaters SetSdlcParameters: LXI H,PutSdlcMode SHLD PutModeSwitch ; Set JMP instruction LXI H,SdlcGetLoop SHLD GetModeSwitch LXI H,SdlcRS232CInterrupt LXI D,SdlcDefaultParameters CommonSynchParamaters: CALL CopyParameters LXI H,SynchronousDivisor SetBaud: {Set the baud rate. HL points to Divisor table.} LDA RS232CParameter1Hi ; Set Baud Rate ANI CPLineSpeedMask ; Async:x16, Sync or Sdlc:x1 STA CurrentBaudRate CALL SetBaudRate SetSyncCharacter: LDA RS232CParameter3 STA CurrentSyncCharacter {If ResetRingHeard bit is set, reset the RingHeardLatch.} CALL CheckResetRingHeard {Set up the parity parameters in WR4 depending on RS232CParameter2 (mask 0E0): 0 => no parity 20H (1) => odd parity 40H (2) => even parity 60H (3) => one parity (no parity specified, but add "1" bit) 80H (4) => zero parity (no parity specified, but add "0" bit) Set up B to contain the bits to OR into WR4.} MVI D,0 ; Assume no parity LDA RS232CParameter2 ANI CPParityMask JZ SetParity ;zero => no parity CPI CPOneParity JZ SetParity CPI CPZeroParity JZ SetParity MVI D,ParityOdd ;if parity is specified CPI CPOddParity JZ SetParity MVI D,ParityEven SetParity: LDA RxWR4 ORA D STA RxWR4 LDA TxWR4 ORA D STA TxWR4 {Set the character length depending on the character length (mask 18): 0 => char length = 5 0 8H (1) => char length = 6 80 10H (2) => char length = 7 40 18H (3) => char length = 8 C0} LDA RS232CParameter2 ; Charcter Length Check ANI CPCharLMask ;A ¬ LLxxx RRC ;A ¬ LLxx RRC ;A ¬ LLx RRC ;A ¬ LL {Pick up the character length code that we will use to set WR3, and set up WR3.} MOV E,A ;DE ¬ character length code * 2 MVI D,0 LXI H,CharLengthTable DAD D ;HL ¬ CharLengthTable + length code LDA RxWR3 ; Set Character Length ORA M STA RxWR3 {The character length code for WR5 is the character length code for WR3 shifted right one position. Set up WR5.} ANI Rx8BitsPerCharacter ;A ¬ character length for WR3 RRC ;A ¬ character length for WR5 MOV H,A LDA TxWR5 ORA H STA TxWR5 {Set up the character length mask.} LXI H,CurrentCharLengthMaskTable DAD D ;HL ¬ CurrentCharLengthMaskTable + length code MOV A,M STA CurrentCharLengthMask {Set Data Terminal Ready (DTR) in WR5 if this bit is set in the parameter.} LDA RS232CParameter2Hi ; Check Command ANI CPDTRMask ;Mask = 8 JZ CheckRTS LDA TxWR5 ; Set DTR bit if command bit is 1 ORI DTR STA TxWR5 CheckRTS: {Set Clear To Send (CTS) in WR5 if this bit is set in the parameter.} LDA RS232CParameter2Hi ; Check Command ANI CPRTSMask ;Mask = 10H JZ CheckRingHeard LDA TxWR5 ; Set DTR bit if command bit is 1 ORI RTS CALL UpdateTxWR5 CheckRingHeard: {Turn off RingHeardLatch if ResetRingHeard is set in the parameter.} LDA RS232CParameter2Hi ; Reset Ring Hard, if required ANI CPRRHMask JZ CheckCorrespondent XRA A STA RingHeardLatch CheckCorrespondent: {Check the Correspondent specified in RS232CParameter3Hi: 0 = xerox800 1 = xerox850 2 = system6 3 = cmcII 4 = ttyHost 5 = oisSystemElement 6 = ibm3270Host 7 = ibm2770Host 8 = ibm6670Host 9 = ibm6670 10 = xerox860 11 = oisSystemElementBSC 12 = siemens9750 If we are running in BiSync mode, we assume the code is EBCDIC. Check to see if we have a correspondent that requires an ASCII code.} LDA RS232CParameter3Hi ; Set Correspondents STA CurrentCorrespondents CALL RxInitBiSyncInput CALL TxInitBiSyncInterrupts CPI IBM3270Host JZ IBM3270OrSiemens9750 CPI siemens9750 LXI H,EndOfBisyncFrame ;Assume not 3270 host JNZ SetEOTEndFrameSwitch {If the host is a 3270 or 9750, it requires special treatment for EOT EndOfFrame.} IBM3270OrSiemens9750: LXI H,EOT3270 SetEOTEndFrameSwitch: SHLD EOTEndFrameSwitch CPI Xerox850 JZ SetAsciiCode CPI siemens9750 JZ SetAsciiCode CPI xerox860 JNZ SaveSynCount SetAsciiCode: LXI H,AsciiCodeTable LXI D,CurrentCode MVI A,AsciiCodeTableSize CALL Copy SaveSynCount: {Save the number of SYN characters to send.} LDA RS232CParameter2 ; Save Sync Count value ANI CPSyncCntMask STA CurrentSyncCount {Perform common initialization for Get and Put tasks.} XRA A STA AbortGetFlag STA AbortPutFlag LXI H,TestStatusChange ; Fix for CTS SHLD GetTaskStartAddress ; Fix for CTS LXI H,StartGetTask SHLD GetTaskResumeAddress LXI H,StartPutTask SHLD PutTaskResumeAddress ; {Initialize depending on the current Mode.} LDA RS232CMode ORA A JZ InitializeSdlcMode CPI CPAsyncMode JZ InitializeAsyncMode InitializeBisyncMode: {Continue if mode is Bisync. Initialize character values for parsing depending on the character set.} LDA BEL STA BEL1 STA BEL6 LDA ENQ STA ENQ1 STA ENQ2 STA ENQ4 STA ENQ6 STA ENQ9 STA ENQ10 STA ENQ11 STA ENQ12 LDA EOT STA EOT1 STA EOT6 LDA ETB STA ETB2 STA ETB4 STA ETB5 STA ETB6 STA ETB7 STA ETB8 STA ETB9 STA ETB10 STA ETB11 STA ETB12 LDA NAK STA NAK1 STA NAK6 LDA SYN STA SYN1 STA SYN2 STA SYN3 STA SYN4 STA SYN5 STA SYN6 STA SYN7 STA SYN8 STA SYN9 STA SYN10 STA SYN11 STA SYN12 STA SYN13 {6/30/83} STA SYN14 {6/30/83} {WR3 has been set up for the number of bits per character. Store this value wherever we want to disable CRC.} LDA RxWR3 ORI RxEnable STA DisableRxCRC1 STA DisableRxCRC2 STA DisableRxCRC3 {OR in RxCRCEnable and store this value wherever we want to enable the CRC generator.} ORI RxCRCEnable STA EnableRxCRC1 STA EnableRxCRC2 STA EnableRxCRC3 STA EnableRxCRC4 {OR in the SyncCharacterLoadInhibit bit and the EnterHuntMode bit. This is the initial state of the receiver.} LDA RxWR3 ORI RxEnable+SyncCharacterLoadInhibit+EnterHuntPhase STA EnterHuntMode1 STA EnterHuntMode2 {Initialize the values for the one second timer.} LXI H,BisyncTimerTable LDA CurrentBaudRate CALL HLPlus2A MOV A,M STA OneSecondTimerLow INX H MOV A,M STA OneSecondTimerHigh {Set up the SIO chip. The order is important. Any deviation from this may cause the chip to do weird things.} DI LXI H,8000H+RxCont CALL CheckChannelReset MVI M,PointToWR4+ResetExternalStatusInterrupts LDA RxWR4 MOV M,A MVI M,PointToWR5+ResetExternalStatusInterrupts LDA RxWR5 MOV M,A MVI M,PointToWR3 LDA RxWR3 ORI EnterHuntPhase+SyncCharacterLoadInhibit MOV M,A MVI M,PointToWR6 LDA CurrentSyncCharacter MOV M,A MVI M,PointToWR7 LDA CurrentSyncCharacter MOV M,A MVI M,PointToWR1+ResetExternalStatusInterrupts LDA RxWR1 MOV M,A {5/17/83 add reset of Interrupt Vector in channel B} LXI H,8000H+TxCont CALL CheckAndResetChannelReset MVI M,PointToWR2 MVI M,0 MVI M,PointToWR4+ResetExternalStatusInterrupts LDA TxWR4 MOV M,A MVI M,PointToWR6 MVI A,Filler MOV M,A MVI M,PointToWR7+ResetExternalStatusInterrupts MVI A,Filler MOV M,A MVI M,PointToWR1+ResetExternalStatusInterrupts LDA TxWR1 MOV M,A MVI M,PointToWR5+ResetExternalStatusInterrupts LDA TxWR5 MOV M,A JMP ReturnSuccess { 1 Jul 83 Check to see if we are to do a Channel Reset. The routines are re-entrant. It is assumed that the HL register pair points to the memory mapped port of either the receiver or the transmitter. If so do it if not then don't. This subroutine has two entry points: CheckAndResetChannelReset: this entry indicates that the channel reset has been done and resets ChannelNeedsReset flag. CheckChannelReset: this entry checks to see if a channel reset is required.} CheckAndResetChannelReset: PUSH PSW LDA ChannelNeedsReset ORA A JZ ExitCheckChannelReset XRA A STA ChannelNeedsReset JMP DoChannelReset ChannelNeedsReset: DB 1 CheckChannelReset: PUSH PSW LDA ChannelNeedsReset ORA A JZ ExitCheckChannelReset DoChannelReset: MVI M,ChannelReset ExitCheckChannelReset: POP PSW RET SetChannelResetFlag: PUSH PSW MVI A,1 STA ChannelNeedsReset POP PSW RET InitializeSdlcMode: LXI H,8000H+RxCont ;HL points to Rx Control register DI {MVI M,ChannelReset} CALL CheckChannelReset {Set WR6 for the Sdlc sync character} MVI M,ResetExternalStatusInterrupts+PointToWR6 LDA RS232CParameter3 MOV M,A {Set WR7 to the Sdlc flag character.} MVI M,ResetExternalStatusInterrupts+PointToWR7 MVI M,7EH {WR4 has been set up for X1 ClockMode and Sdlc mode.} MVI M,ResetExternalStatusInterrupts+PointToWR4 LDA RxWR4 MOV M,A {WR3 has been set up for the number of bits per character and CRC Enable.} MVI M,ResetExternalStatusInterrupts+PointToWR3 LDA RxWR3 MOV M,A {WR1 has been set up for ExternalIntEnable, IntOnAllRxCharacters (status affects parity)} MVI M,ResetExternalStatusInterrupts+PointToWR1 LDA RxWR1 MOV M,A {Now initialize Channel B, the Tx channel} LXI H,8000H+TxCont ;HL points to TxControl register {MVI M,ChannelReset} CALL CheckAndResetChannelReset {5/17/83 add reset of Interrupt Vector in channel B} {MVI A,PointToWR2 OUT TxCont XRA A ;Clear the accumulator OUT TxCont} MVI M,PointToWR2 MVI M,0 {Set WR7 to the Sdlc flag character.} MVI M,ResetExternalStatusInterrupts+PointToWR7 MVI M,7EH JMP SetTxWR4 InitializeAsyncMode: LXI H,8000H+RxCont ;HL points to Rx Control register DI {MVI M,ChannelReset} CALL CheckChannelReset {WR4 has been set up for X16 ClockMode, the number of stop bits/character, and the parity specified by the client's parameter record.} MVI M,ResetExternalStatusInterrupts+PointToWR4 LDA RxWR4 MOV M,A {WR3 has been set up for the number of bits per character} MVI M,ResetExternalStatusInterrupts+PointToWR3 LDA RxWR3 MOV M,A {WR1 has been set up for ExternalIntEnable, IntOnAllRxCharacters (status affects parity)} MVI M,ResetExternalStatusInterrupts+PointToWR1 LDA RxWR1 MOV M,A {Now initialize Channel B, the Tx channel} LXI H,8000H+TxCont ;HL points to TxControl register {MVI M,ChannelReset} CALL CheckAndResetChannelReset {5/17/83 add reset of Interrupt Vector in channel B} {MVI A,PointToWR2 OUT TxCont XRA A ;Clear the accumulator OUT TxCont} MVI M,PointToWR2 MVI M,0 SetTxWR4: {WR4 has been set up for X16 ClockMode, the number of stop bits/character, and the parity specified by the client's parameter record.} MVI M,ResetExternalStatusInterrupts+PointToWR4 LDA TxWR4 MOV M,A {WR5 has been set up for the number of bits/character, DataTerminalReady (if specified in the client's parameter record), RequestToSend (if specified in the client's parameter record).} MVI M,ResetExternalStatusInterrupts+PointToWR5 LDA TxWR5 MOV M,A {WR1 has been set up for StatusAffectsVector, ExternalIntEnable, TxIntEnable} MVI M,ResetExternalStatusInterrupts+PointToWR1 LDA TxWR1 MOV M,A ReturnSuccess: {Return Success in the CSB.} EI LXI H,XferSuccess SHLD RS232CParameter LXI H,SendParameter JMP ReturnResult ; DoSetRS366Status: LDA RS232CParameter2 ; Read New RS366 Status ANI RS366StatusMask CALL SetRS366 JMP ResetMiscTaskFlag ; DoGetStatus: IN RS366Reg ; Read RS366 Reg Condition STA RS366Buffer ANI DLO+PND+COS+ACR+PWI STA RS232CDeviceStatusHi ;Save RS366 Reg Condition in Device Status {Get Data Carrier Detect bit from RR0.} IN RxCont ANI BreakAbort+DCD ; Bk ABT is only on Async Mode MOV D,A ;Save DCD in D {Get Clear To Send Detect bit from RR0.} IN TxCont ANI CTS ORA D MOV D,A ;Save DCD and CTS in D {Get DataSetReady bit from RS366Buffer.} DB opMVIA ;A ¬ RS366Buffer RS366Buffer: DB 0 ANI DSRdy ; Data Set Ready? JZ CheckRingIndicator MVI A,DataSetReady ; IF Yes, DataSetReady bit Set ORA D MOV D,A ;Save DataSetReady, DCD and CTS in D CheckRingIndicator: {Get RingIndicator from RS366Buffer.} LDA RS366Buffer ANI Ring ; Ring Heard? JZ CheckRingHeardLatch MVI A,RingIndicator ; If Yes, Ring Indicator bit Set ORA D MOV D,A STA RingHeardLatch ; Set RingHeard Latch CheckRingHeardLatch: DB opMVIA ;A ¬ RingHeardLatch RingHeardLatch: DB 0 ORA A JZ WriteDeviceStatus MVI A,RingHeard ; IF Yes, Ring Heard bit set ORA D MOV D,A WriteDeviceStatus: MOV A,D STA RS232CDeviceStatus LXI H,SendDeviceStatus ReturnResult: CALL WriteCPBuffer JMP ResetMiscTaskFlag ; DoMinorSetParameters: LDA TxWR5 ANI 0FFH-DTR-RTS ;Turn off DTR and RTS MOV D,A ;Save TxWR5 in D LDA RS232CParameter2Hi ANI CPDTRMask JZ RTSControl MOV A,D ; Set DTR bit if command bit is 1 ORI DTR MOV D,A ;Save TxWR5 in D RTSControl: LDA RS232CParameter2Hi ; Check Command ANI CPRTSMask MOV A,D ; Set RTS bit if command bit is 1 JZ ControlSigSet ORI RTS ControlSigSet: CALL UpdateTxWR5 LDA TxWR5 LXI H,TxCont+8000H ;HL points to TxCont register DI MVI M,PointToWR5+ResetExternalStatusInterrupts MOV M,A ;Send new WR5 command EI {If ResetRingHeard bit is set, reset the RingHeardLatch.} CALL CheckResetRingHeard ResetMiscTaskFlag: LXI H,ZeroMiscFlag CALL WriteCPBuffer { 7/12/83 issue wakeup to the head after simple command as well as after puts and gets } LHLD RS232CTaskWakeMask CALL DoNakedNotify JMP MiscYield SaveMiscResumeAddressAndYield: SHLD MiscTaskResumeAddress MiscYield: DS 0 {Pass control to the next task specified in Domino.cfg} END