;-- DK:DIAL.MAC DATE: 4-MAY-87 TIME: 21:04 .REPT 0 Maarten van Swaay maarten@ksuvax1.BITNET Dept. of Computer Science Nichols Hall Kansas State University Manhattan, Kansas 66506 DIAL is a front end for terminal emulators that handle communication with a remote host over dial lines. It runs under RT11V4. For details see DIAL.TXT. Version 3.2 modifications: default separator char = '< Version 3.1 exit paths: Failure to acquire or control specified LUN: discard command file and exit Failure to reset Hayes modem: discard command file and exit Unexpected modem response: reset modem, replace command file with SY:DIAL.ABT Successful connection to remote host: continue command file Commands to DIAL: .R (.Reset) Can only come from a command file, not recognized if entered from the keyboard. Ignore remainder of this command line, and issue a reset sequence (Hayes protocol: <+++> ); then print message: ?DIAL-I-modem reset to command mode .M (.Manual) Can only come from a command file, not recognized if entered from the keyboard. Ignore remainder of this command line, and enter keyboard mode after transmission of the next command line. Ignore any expected-response character that may be supplied on that command line. Before echoing any response text, print a message: ?DIAL-I-entering keyboard mode, exit with .C (Comment) Can only come from a command file, not recognized if entered from the keyboard. Accepted as a no-op by DIAL's command decoder; triggers no error message. A command line beginning with .C can therefore be used to display descriptive text imbedded in a command file. Can only come from keyboard and must be explicitly typed in. Retrieve further local input from current command file. .ENDR ; MULTITERMINAL SUPPORT IS REQUIRED ; TIME-OUT SUPPORT IS REQUIRED VERS = '3 REV = '2 .GLOBL KMNCMD ; to patch abort filename .ENABL LC .IIF NDF HAYES HAYES = 1 ; default includes Hayes reset .IIF NDF LUNREM LUNREM = 2 ; remote (modem) LUN .IIF NDF LONG LONG = 30 ; default wait time for response .IIF NDF SHORT SHORT = 2 ; default wait time between chars .IIF NDF CSEP CSEP = '< ; command/response separator CHAIN = 004000 ; chain bit in JSW CHBIT = 010000 ; char. mode LCBIT = 040000 ; lower-case bit NOWAIT = 000100 ; no-wait bit AST.IN = 040000 ; set if input available KMNBUF = 510 ; chain command area starts at 510 octal ERRBYT = 52 JSW = 44 CBEL = 7 CCR = 15 CLF = 12 CCTLZ = 32 .MCALL .MTATCH,.MTGET,.MTSET,.MTIN,.MTOUT,.MTPRNT .MCALL .TTYIN,.TTINR,.TTYOUT,.PRINT .MCALL .GTLIN,.MRKT,.CMKT,.TWAIT,.EXIT ;****************************** ; START OF CODE, ENTRY POINT ;****************************** ;****************************** ; claim a terminal port, quit on failure ;****************************** DIAL: .PRINT #WELCOM .MTATCH #ATTEMT ; grab modem port BCC 1$ MOV #101$,R0 JMP QUIT 1$: .MTGET #SETEMT BCC 2$ MOV #102$,R0 JMP QUIT 2$: BIS #CHBIT+LCBIT,MTSTS ; modem in char mode .MTSET #SETEMT BCC 3$ MOV #103$,R0 JMP QUIT 3$: BIS #CHBIT+NOWAIT+LCBIT,@#JSW ; keyboard in char. mode, no wait CLRB WAIT ; enter without wait BR DOIT 101$: .ASCIZ /?DIAL-F-cannot attach modem port/ 102$: .ASCIZ /?DIAL-F-cannot get modem port configuration/ 103$: .ASCIZ /?DIAL-F-cannot set up modem port/ .EVEN ;****************************** ; read and process command lines ;****************************** DOIT: CLRB CMDBUF .GTLIN #CMDBUF CMPB CMDBUF,#'. BNE 1$ CALL DECODE BR DOIT 1$: CALL CUT ; break line into cmd + response DRAIN: BIT #AST.IN,REMAST ; any old modem chars? BEQ 1$ ; no .MTIN #INEMT ; yes, throw them away BR DRAIN 1$: .MTPRNT #OUTEMT ; send new command TSTB MANUAL ; enter manual mode? BEQ AUTO CALL KB ; yes, return after typed-in BR DOIT AUTO: CLRB EXPIRE MOV #60.*LONG,TIME+2 ; allow slow response on first char .MRKT #MRKEMT ; limited patience for response 1$: BIT #AST.IN,REMAST BNE 2$ ; response arrived TSTB EXPIRE BEQ 1$ ; wait some more .PRINT #NOCHAR JMP ABORT 2$: .CMKT #CMKT ; cancel outstanding mark-time request .MTIN #INEMT MOVB REMCH,R0 MOVB R0,RSPONS ; retain first char (for Hayes response tests) .TTYOUT MOV #60.*SHORT,TIME+2 ECHO: .MRKT #MRKEMT CLRB EXPIRE 1$: BIT #AST.IN,REMAST BNE 2$ TSTB EXPIRE BEQ 1$ BR 90$ ; no more response expected 2$: .CMKT #CMKT .MTIN #INEMT MOVB REMCH,R0 .TTYOUT BR ECHO 90$: TSTB EXPECT ; predictable response expected? BEQ DOIT ; no CMPB EXPECT,RSPONS ; yes, response as expected? BEQ DOIT 99$: .PRINT #UNEXP ; no, give up ABORT: CALL BREAK ; reset modem on any hard error MOV #DERAIL,R1 MOV #KMNBUF,R0 MOV #DIAL,SP 1$: MOVB (R1)+,(R0)+ CMP R1,#KMNEND BLO 1$ JMP EXIT QWKt: .PRINT ; local problems .PRINT #QUITMS MOV #1,@#KMNBUF BEQ 1$ BR 90$ ; no more response expected 2$: .CMKT #CMKT .MTIN #INEMT MOVB REMCH,R0 .TTYOUT BR ECHO 90$: TSTB E: .ASCIZ /@SY:DIAL.ABT/ ; catch abort in a command file KMNEND: .EVEN ;****************************** ; DECODE: recognizes .M, .R, .C commands in command files ; Changes R0 ;****************************** DECODE: MOVB CMDBUF+1,R0 BICB #40,R0 ; brute-force upper-case CMPB R0,#'C BEQ DECODX ; comment line CMPB R0,#'M BNE 1$ BISB #1,MANUAL ; .M sets manual flag BR DECODX 1$: CMPB R0,#'R BNE 2$ CALL BREAK ; .R resets (Hayes) modem BR DECODX 2$: .PRINT #INVAL DECODX: RETURN ;****************************** ; KB: char-by-char unsynchronized two-way loop between local and ; remote ports. Local keystrokes not echoed under the assumption that ; they will come back from the remote host. ; Discard character after local without inspection. ; Return to command file on keystroke. ; R0 changed on exit. ;****************************** KB: .TTINR BCC KB ; drain old KB input, if any CLRB MANUAL .PRINT #KBMODE ; entering keyboard mode, exit with MOVB #200,CMDBUF+1 ; send single chars one at a time 1$: BIT #AST.IN,REMAST ; any remote response? BEQ 2$ .MTIN #INEMT ; yes, display it MOVB REMCH,R0 .TTYOUT 2$: .TTINR ; any keystroke? BCS 1$ CMPB R0,#CLF ; yes, ? BEQ KBX ; yes, back to command file MOVB R0,CMDBUF .MTPRNT #OUTEMT ; no, send it off without synchronization CMPB CMDBUF,#CCR ; was it ? BNE 1$ .TTYIN ; yes, discard the after it BR 1$ KBX: RETURN ;****************************** ; BREAK: modem reset sequence: wait, then +++, wait some more ;****************************** .IF NE HAYES .IFT BREAK: .TWAIT #WTEMT MOV #PLUS,OUTSTR .MTPRNT #OUTEMT MOV #CMDBUF,OUTSTR .TWAIT #WTEMT .PRINT #RESET RETURN WTEMT: .WORD 24*400,TWOSEC TWOSEC: .WORD 0,2*60. ; 2 seconds RESET: .ASCIZ /?DIAL-I-modem reset to command mode/ PLUS: .ASCII /+++/<200> .EVEN .IFF BREAK: RETURN .ENDC ;****************************** ; CUT: replaces separator by null, copies next char to EXPECT. ; If no separator is found, EXPECT = 0 ; Also terminates command string with <15><200> ; Changes R0 ;****************************** CUT: MOV #CMDBUF,R0 CLRB EXPECT ; default, expect no separator 1$: TSTB @R0 BEQ CUTX ; no separator mark found CMPB (R0)+,#CSEP BNE 1$ MOVB @R0,EXPECT ; expected response DEC R0 CUTX: MOVB #CCR,(R0)+ MOVB #200,@R0 RETURN ;****************************** ; TIMUP: mark-time completion routine sets EXPIRE ;****************************** TIMUP: BISB #1,EXPIRE RETURN ATTEMT: .WORD 37*400+5,REMAST,LUNREM ; for .MTATCH SETEMT: .WORD 37*400+1,MTSTS,LUNREM ; for .MTGET, .MTSET INEMT: .WORD 37*400+2,REMCH,1*400+LUNREM OUTEMT: .WORD 37*400+7,CMDBUF,LUNREM ; word 2 changed at runtime OUTSTR = OUTEMT+2 MRKEMT: .WORD 22*400,TIME,TIMUP,1 TIME: .WORD 0,60*LONG ; limit of dial-up patience CMKT: .WORD 23*400,0,0 ; cancel mark-time requests MTSTS: .BLKW 2 ; port status block REMAST: .BLKW 1 ; AST word CRLF: .BYTE 0 ; newline via .PRINT WELCOM: .ASCIZ /-DIAL- Version //./ QUITMS: .ASCIZ / Command file, if any, aborted/ INVAL: .ASCIZ /?DIAL-W-Invalid local command ignored/ NOCHAR: .ASCIZ /?DIAL-F-no response from modem/ UNEXP: .ASCIZ /?DIAL-F-unexpected response from modem/ KBMODE: .ASCIZ /?DIAL-I-entering manual mode, exit with / CMDBUF: .BLKB 82. ; command text buffer MANUAL: .BLKB 1 ; keyboard-input flag EXPECT: .BLKB 1 ; expected response char (from input line) EXPIRE: .BLKB 1 ; expired patience flag REMCH: .BLKB 1 ; modem response char RSPONS: .BLKB 1 ; expected response char .END DIAL