perm filename SUPSER.MID[S,NET]4 blob
sn#796095 filedate 1985-06-06 generic text, type C, neo UTF8
COMMENT ⊗ VALID 00016 PAGES
C REC PAGE DESCRIPTION
C00001 00001
C00005 00002 X INTFOP INTPTO INTCLK INTQUIT FCS FULTWX XON TLKRNG
C00007 00003 %TOALT %TOCLC %TOERS %TOHDX %TOMVB %TOSAI %TOSA1 %TOOVR %TOMVU %TOMOR %TOROL %TORAW %TOLWR %TOFCI %TOIML %TOLID %TOCID %TPPLF %TPPCR %TPPTB %TPPRN %TPTEL %TPCBS %TP11T %TPORS %TQMCH %TQIM1 %TQIM4 %TQP11 %TQHGT %TQWID %TQVIR %TQBNK %TQXOR %TQREC %TQSET %TQGRF %TRGIN %TRGHC %TNPRT %TNDP %TNODP %TNIML %TNTEK %TNTV %TNMEM %TNSFW %TNTRM %TNESC %TNDTM %TNMAX %TXASC %TXCTL %TXMTA %TXSFT %TXSFL %TXTOP
C00012 00004 %GOMVR %GOXOR %GOSET %GOMSR %GOINV %GOBNK %GOCLR %GOPSH %GOVIR %GOHRD %GOGIN %GOLMT %GOMVA %GOIOR %GOMSA %GOVIS %GOCLS %GOPHY %GODLR %GODPR %GODRR %GODCH %GODLA %GODPA %GODRA %GOELR %GOEPR %GOERR %GOECH %GOELA %GOEPA %GOERA %TDMOV %TDMV1 %TDEOF %TDEOL %TDDLF %TDMTF %TDMTN %TDCRL %TDNOP %TDBS %TDLF %TDRCR %TDORS %TDQOT %TDFS %TDMV0 %TDCLR %TDBEL %TDINI %TDILP %TDDLP %TDICP %TDDCP %TDBOW %TDRST %TDMAX
C00017 00005 TYSBLK IMPSET LINCHR XONOFF DPYSET GAGOFF MODSET NTYSTS DPYBLK SETVSZ SETHSZ PADCHR PDBAUD TABFLG EDITKY DPYDES CNSBLK TCTYP TTYOPT TCMXV TCMXH TTYROL SMARTS ISPEED OSPEED CNSBLL TERMID CORBEG TERSTR HPOS VPOS SCRMST GETCXP GETCYP INDLMP ROLLP LFFLSP QUOTEP 128CHP OVRPRP PTINTP NTINTP DOQUIT PRESCP SDCMDP EATERP NODETP BKYBTS FLSCNT TERMBP TTYLIN TPCSAV IDLTIM PTIBUF PDL COREND
C00022 00006 INTSER CLKSER INTDIE CLKSR1
C00025 00007 SUPSER CPYHST 1DIGTP NOTTIP
C00028 00008 NOFLAK GETSIZ GETCNS CHKTRM NOTSAI
C00031 00009 GETPTY MAINL MAINL0
C00034 00010 NTISER
C00037 00011 PTYSN0 FNYQOT PTYSN1 PTYSN2 PTYSND
C00040 00012 PTISER PTISR1 CHKCYP CHKDMC DMSND DMSND0 MRKNBL ISPCH NOTPCH
C00043 00013 SCLEAR CANCEL CLEOL SETCPS SNDPOS INSLIN IDCMND SPACE FORSPC
C00046 00014 DMCTAB
C00050 00015 DMCTAB...
C00053 00016 GETSMD BITTAB SNDMSG MSGLUP ERRDIE SUICID DIEDIE ...LIT SVRRTS ERRTNS ERRHAN ERRINS HSTTAB HSTSIX
C00056 ENDMK
C⊗;
;X INTFOP INTPTO INTCLK INTQUIT FCS FULTWX XON TLKRNG
TITLE SUPSER
SUBTTL Definitions
; Mark Crispin, SU-AI, October 1979
; Assembly switches
IFNDEF SVRSKT,SVRSKT==137 ; default listen socket
IFNDEF LOKTMO,LOKTMO==5 ; # of 15-second frobs of lock timeout
IFNDEF PDLLEN,PDLLEN==50 ; stack length
IFNDEF VSZMAX,VSZMAX==70. ; maximum TCMXV
IFNDEF HSZMAX,HSZMAX==95. ; maximum TCMXH
; AC definitions. 0→3 are used by NETWRK
X=4 ? Y=5 ? Z=6 ? A=7 ? B=10 ? C=11 ? D==12 ? P=17
; SAIL system bit definitions
INTFOP==040000,, ; PTY clear output buffer
INTPTO==001000,, ; PTY interrupt
INTCLK==000200,, ; clock interrupt
INTQUIT==002000 ; (right half) interrupt on QUIT cmd
FCS== 000020,, ; full character set mode
FULTWX==000004,, ; no echo
XON== 000002,, ; paper tape mode
TLKRNG==000001,, ; TALKing
;%TOALT %TOCLC %TOERS %TOHDX %TOMVB %TOSAI %TOSA1 %TOOVR %TOMVU %TOMOR %TOROL %TORAW %TOLWR %TOFCI %TOIML %TOLID %TOCID %TPPLF %TPPCR %TPPTB %TPPRN %TPTEL %TPCBS %TP11T %TPORS %TQMCH %TQIM1 %TQIM4 %TQP11 %TQHGT %TQWID %TQVIR %TQBNK %TQXOR %TQREC %TQSET %TQGRF %TRGIN %TRGHC %TNPRT %TNDP %TNODP %TNIML %TNTEK %TNTV %TNMEM %TNSFW %TNTRM %TNESC %TNDTM %TNMAX %TXASC %TXCTL %TXMTA %TXSFT %TXSFL %TXTOP
SUBTTL ITS TTY definitions
; These definitions are the various bits, words, etc. for the ITS terminal
; service system calls and are here for convenience and clarity. This is
; abridged from [MIT-AI] SYSTEM;BITS >, the monitor bits definition file.
; TTYOPT variable (terminal capabilities)
%TOALT==200000,, ; 1 → standardise altmodes
%TOCLC==100000,, ; 1 → convert cases on input
%TOERS==040000,, ; 1 → this terminal can erase
%TOHDX==020000,, ; 1 → half duplex
%TOMVB==010000,, ; 1 → can backspace
%TOSAI==004000,, ; 1 → has SAIL graphics
%TOSA1==002000,, ; 1 → init %TSSAI in new jobs (use graphics)
%TOOVR==001000,, ; 1 → can overprint
%TOMVU==000400,, ; 1 → can line starve (ie a display)
%TOMOR==000200,, ; 1 → do **More** processing (init %TSMOR)
%TOROL==000100,, ; 1 → scroll (init %TSROL for new jobs)
%TORAW==000040,, ; 1 → no cursor motion optimization
%TOLWR==000020,, ; 1 → lower case keyboard
%TOFCI==000010,, ; 1 → has bucky bit keyboard
%TOIML==000004,, ; 1 → acts like a grIMLAC (funny ↑PF, ↑PB)
%TOLID==000002,, ; 1 → can insert/delete lines
%TOCID==000001,, ; 1 → can insert/delete characters
%TPPLF==700000 ; LF padding
%TPPCR==070000 ; CR padding
%TPPTB==007000 ; TAB padding (0 → no tabs, 1 → tabs)
%TPPRN==000200 ; 1 → swap () with [] on input
%TPTEL==000100 ; 1 → CR → CRLF for ARPAnet protocol
%TPCBS==000040 ; 1 → intelligent terminal protocol (↑\)
%TP11T==000020 ; 1 → PDP-11 TV (reflects %TY11T)
%TPORS==000010 ; 1 → output reset should do something
; SMARTS variable (terminal smarts)
%TQMCH==700000,, ; machine type
%TQIM1==300000,, ; PDS1
%TQIM4==200000,, ; PDS4
%TQP11==100000,, ; PDP-11
%TQHGT==076000,, ; character height in dots
%TQWID==001700,, ; character width in dots
%TQVIR==000040,, ; virtual coordinates
%TQBNK==000020,, ; blinking
%TQXOR==000010,, ; XOR mode
%TQREC==000004,, ; rectangle command
%TQSET==000002,, ; multiple sets
%TQGRF==000001,, ; understands graphics
%TRGIN==400000 ; graphics input
%TRGHC==200000 ; hardcopy device
; TCTYP variable (terminal type)
%TNPRT==0 ; printing console, glass TTY, etc.
%TNDP==1 ; good Datapoint
%TNODP==2 ; inferior losing Datapoint
%TNIML==3 ; grIMLAC
%TNTEK==4 ; Tektronix 4000 series
%TNTV==5 ; PDP-11 TV
%TNMEM==6 ; Memowreck
%TNSFW==7 ; Software
%TNTRM==10 ; Terminet
%TNESC==11 ; ASCII standard display (VT52, etc.)
%TNDTM==12 ; Datamedia 2500
%TNMAX==13 ; 1 + largest terminal type
; Components of an input character in 12-bit mode.
%TXASC==0177 ; ASCII part
%TXCTL==0200 ; control
%TXMTA==0400 ; meta
%TXSFT==1000 ; shift
%TXSFL==2000 ; shift lock
%TXTOP==4000 ; top
;%GOMVR %GOXOR %GOSET %GOMSR %GOINV %GOBNK %GOCLR %GOPSH %GOVIR %GOHRD %GOGIN %GOLMT %GOMVA %GOIOR %GOMSA %GOVIS %GOCLS %GOPHY %GODLR %GODPR %GODRR %GODCH %GODLA %GODPA %GODRA %GOELR %GOEPR %GOERR %GOECH %GOELA %GOEPA %GOERA %TDMOV %TDMV1 %TDEOF %TDEOL %TDDLF %TDMTF %TDMTN %TDCRL %TDNOP %TDBS %TDLF %TDRCR %TDORS %TDQOT %TDFS %TDMV0 %TDCLR %TDBEL %TDINI %TDILP %TDDLP %TDICP %TDDCP %TDBOW %TDRST %TDMAX
; Graphics output buffer codes
%GOMVR==001 ; move cursor to P
%GOXOR==002 ; turn on XOR mode
%GOSET==003 ; select set N
%GOMSR==004 ; move set origin to P
%GOINV==006 ; make current set invisible
%GOBNK==007 ; make current set blink
%GOCLR==010 ; erase whole screen
%GOPSH==011 ; push status information
%GOVIR==012 ; use virtual coordinates
%GOHRD==013 ; divert output to N
%GOGIN==014 ; request input, reply code N
%GOLMT==015 ; limit to subrectangle P1 P2
%GOMVA==021 ; move cursor to P, abs addr
%GOIOR==022 ; turn off XOR mode
%GOMSA==024 ; move set origin to P, abs addr
%GOVIS==026 ; make current set visible
%GOCLS==030 ; erase current set
%GOPHY==032 ; use unit coordinates
%GODLR==101 ; draw line relative, to P
%GODPR==102 ; draw point relative, at P
%GODRR==103 ; draw rectangle relative, at P
%GODCH==104 ; display STRING
%GODLA==121 ; draw line absolute, to P
%GODPA==122 ; draw point absolute, at P
%GODRA==123 ; draw rectangle absolute, at P
%GOELR==141 ; erase line relative, to P
%GOEPR==142 ; erase point relative, at P
%GOERR==143 ; erase rectangle relative, at P
%GOECH==144 ; erase STRING
%GOELA==161 ; erase line absolute, to P
%GOEPA==162 ; erase point absolute, at P
%GOERA==163 ; erase rectangle absolute, at P
; Non-graphics output buffer codes
%TDMOV==200 ; move cursor OV OH NV NH
%TDMV1==201 ; move cursor; NV NH
%TDEOF==202 ; clear to end of screen
%TDEOL==203 ; clear to end of line
%TDDLF==204 ; delete character after cursor
%TDMTF==205 ; motor off
%TDMTN==206 ; motor on
%TDCRL==207 ; terpri
%TDNOP==210 ; no-op
%TDBS==211 ; backspace
%TDLF==212 ; line feed
%TDRCR==213 ; carriage return
%TDORS==214 ; output reset
%TDQOT==215 ; quote next character (mystery command)
%TDFS==216 ; cursor forward
%TDMV0==217 ; move cursor NV NH
%TDCLR==220 ; clear screen
%TDBEL==221 ; feep!
%TDINI==222 ; reset reset reset
%TDILP==223 ; insert line; count
%TDDLP==224 ; delete line; count
%TDICP==225 ; insert character; count
%TDDCP==226 ; delete character; count
%TDBOW==227 ; inverse video
%TDRST==230 ; reset inverse video, etc.
%TDMAX==231 ; 1 + largest display code
;TYSBLK IMPSET LINCHR XONOFF DPYSET GAGOFF MODSET NTYSTS DPYBLK SETVSZ SETHSZ PADCHR PDBAUD TABFLG EDITKY DPYDES CNSBLK TCTYP TTYOPT TCMXV TCMXH TTYROL SMARTS ISPEED OSPEED CNSBLL TERMID CORBEG TERSTR HPOS VPOS SCRMST GETCXP GETCYP INDLMP ROLLP LFFLSP QUOTEP 128CHP OVRPRP PTINTP NTINTP DOQUIT PRESCP SDCMDP EATERP NODETP BKYBTS FLSCNT TERMBP TTYLIN TPCSAV IDLTIM PTIBUF PDL COREND
SUBTTL Data area
; TTYSET command words
TYSBLK==.
IMPSET: 034400,, ; IMP TTY
LINCHR: 001400,,(FCS) ; default line characteristics
XONOFF: 002400,,(XON\FULTWX) ; generate LF after CR
DPYSET: 064400,,DPYBLK ; set display characteristics
GAGOFF: 024400,, ; gag off
MODSET: 014400,, ; set DM mode
NTYSTS==.-TYSBLK
DPYBLK: 'DM2500 ; Datamedia 2500
SETVSZ: BLOCK 1 ; screen height
SETHSZ: BLOCK 1 ; screen width
PADCHR: 400000,, ; padding character
PDBAUD: 400000,, ; pad baud rate (no padding)
TABFLG: 1 ; have tabs
EDITKY: 0 ; EDITKY bits - use default for now
DPYDES: 0 ; DPYDES bits - use default for now
BLOCK 4 ; reserved bits
; Terminal characteristics
CNSBLK: BLOCK 1 ; CNSGET info
TCTYP: %TNSFW ; TCTYP for server
TTYOPT: %TOERS\%TOMVB\%TOMVU\%TOFCI\%TOLID\%TOCID\%TPCBS ; TTYOPT for server
TCMXV: 24. ; TTY page length
TCMXH: 79. ; TTY width
TTYROL: 0 ; TTYROL variable
SMARTS: 0 ; SMARTS variable
ISPEED: 0 ; input speed
OSPEED: 0 ; output speed
CNSBLL==.-CNSBLK
; Terminal location string
TERMID: 'TERMID
CORBEG==. ; start of initialized core storage
TERSTR: BLOCK 20. ; console location string
; Datamedia translator variables
HPOS: BLOCK 1 ; horizontal position
VPOS: BLOCK 1 ; vertical position
SCRMST: BLOCK 3*<VSZMAX+1> ; screen character allocation table
GETCXP: BLOCK 1 ; -1 → get cursor X position
GETCYP: BLOCK 1 ; -1 → get cursor Y position
INDLMP: BLOCK 1 ; -1 → in I/D mode
ROLLP: BLOCK 1 ; -1 → in roll mode
LFFLSP: BLOCK 1 ; -1 → flush a line feed
QUOTEP: BLOCK 1 ; -1 → quote next character
128CHP: BLOCK 1 ; -1 → FCS terminal
OVRPRP: BLOCK 1 ; -1 → TV terminal
; Interrupt flags
PTINTP: BLOCK 1 ; -1 → PTI interrupt
NTINTP: BLOCK 1 ; -1 → NTI interrupt
DOQUIT: BLOCK 1 ; -1 → QUIT interrupt
; Protocol flags
PRESCP: BLOCK 1 ; -1 → protocol escape seen
SDCMDP: BLOCK 1 ; -1 → in SUPDUP protocol command
EATERP: BLOCK 1 ; -1 → getting terminal string
NODETP: BLOCK 1 ; -1 → don't detach this guy
BKYBTS: BLOCK 1 ; -1 → incoming bucky bits
; Other storage
FLSCNT: BLOCK 1 ; flush count for NTISER
TERMBP: BLOCK 1 ; terminal byte pointer
TTYLIN: BLOCK 1 ; line number of PTY
TPCSAV: BLOCK 1 ; save of JOBTPC
IDLTIM: BLOCK 1 ; idle time in 15-second units
PTIBUF: BLOCK 30. ; PTY input buffer
PDL: BLOCK PDLLEN ; stack
COREND==.-1 ; end of initialized storage
;INTSER CLKSER INTDIE CLKSR1
SUBTTL Interrupt server
; Interrupts only set flags which the main program (normally in INTW⊗
; state) looks at.
INTSER: SKIPN X,JOBCNI ; get interrupt status
JRST 4,.-1
TLNE X,(INTPTO) ; PTY int
SETOM PTINTP
TRNE X,INTQUIT ; QUIT int?
SETOM DOQUIT
TLNE X,(INTCLK) ; CLK int
JRST CLKSER
TLNE X,(INTFOP) ; output reset?
JRST [ MOVE JOBTPC
MOVEM TPCSAV
INTMSK [0]
UWAIT
PUSH P,TPCSAV
INTMSK [-1]
DEBREAK
PUSHJ P,NETINS
MOVEI %TDORS
PUSHJ P,NETOCH
JRST NETSND]
TLNE X,(INTINP) ; NTI int
SETOM NTINTP
TLNE X,(INTIMS) ; status change
JRST [ INTMSK [0]
DEBREAK
JRST SUICID]
TLNE X,(INTINR)
OUTSTR [ASCIZ/*INR*
/]
TLNE X,(INTINS) ; IMP INS int
OUTSTR [ASCIZ/*INS*
/]
INTSR1: MOVSI 1,-1 ; requeue into TQ from any queue
DISMIS 1,
; Service clock interrupt
CLKSER: AOSGE IDLTIM ; bump idle time
JRST INTSR1
UNLOCK ; idle timeout; unlock
MOVE TTYLIN
PTGETL
TLNE 1,(TLKRNG) ; TALKing?
JRST INTSR1 ; don't kill him if so!
TTYJOB
JUMPN INTSR1
INTMSK [0] ; no more interrupts
DEBREAK ; out of interrupt level
SETOM NODETP ; forget about detaching
MOVEI X,[ASCIZ/Autologout/]
PUSHJ P,SNDMSG
JRST SUICID
;SUPSER CPYHST 1DIGTP NOTTIP
SUBTTL Start of program
SUPSER: CAI
RESET
MOVE ['SUPSER]
SETNAM
SETZM CORBEG
MOVE [CORBEG,,CORBEG+1]
BLT COREND
MOVE P,[PDL(-PDLLEN)]
MOVEI [DEBREAK ? EXIT]
MOVEM JOBAPR
CLKINT 5.*60.*60. ; must die if around too long
OUTSTR [ASCIZ/SUPSER started
/]
; Listen for a connection on our socket
SETOM NODETP ; don't try to detach
MOVEI SVRSKT
MOVEM LSNSKT
PUSHJ P,LISTEN
; Set up interrupts
MOVEI INTSER
MOVEM JOBAPR ; set up server location
CLKINT 60.*15. ; start slow ticking clock
MOVE [INTPTO\INTFOP\INTCLK\INTINR\INTINS\INTIMS\INTINP\INTQUIT]
INTENB ; turn on interrupts
; Set up terminal id for interested spies
MOVEI TERMID
MOVEM JOBVER
; Log this connection
OUTSTR [ASCIZ/Connected to /]
PUSHJ P,MAPHST ; map in host table
MOVE HOST
PUSHJ P,HSTNUM ; get HDB
CAI ; sorry about errors
MOVEI Y,(1) ; host name
HRLI Y,440700
SKIPA X,[440700,,TERSTR]
CPYHST: IDPB Z,X
ILDB Z,Y
JUMPN Z,CPYHST
HLRZ Y,1 ; pointer to system name
JUMPE Y,NOTTIP ; jump if no HDB was returned (unknown name)
MOVE Z,(Y) ; get system name
MOVE Y,FSOCKT ; and ICP socket
CAME Z,[ASCII/TAC/] ; on a TAC? (with SUPDUP???)
CAMN Z,[ASCII/TIP/] ; on a TIP? (with SUPDUP???)
TRNE Y,177774 ; just paranoia; make sure a TIP port
JRST NOTTIP
MOVEI Z,"#
IDPB Z,X
LSH Y,-16.
IDIVI Y,8. ; ports are octal
JUMPE Y,1DIGTP
ADDI Y,"0 ? IDPB Y,X
1DIGTP: ADDI Z,"0 ? IDPB Z,X
NOTTIP: MOVEM X,TERMBP
PUSHJ P,SETANM ; set our alias name
PUSHJ P,UNMHST ; map out the host table
OUTSTR TERSTR
OUTSTR [ASCIZ/
/]
MOVEI X,[ASCIZ/SU A.I. Lab KL-10
/]
PUSHJ P,SNDMSG
;NOFLAK GETSIZ GETCNS CHKTRM NOTSAI
SUBTTL Paw over user console characteristics
MOVEI X,256 ; LASTDISASTERTIME
PEEK X,
PEEK X,
JUMPE X,NOFLAK
ACCTIM A,
SUB A,X
TLZE A,1 ; forgive one day
ADDI A,24.*60.*60.
CAILE A,15.*60. ; lost within 15 minutes?
JRST NOFLAK
MOVEI X,[ASCIZ/System is flakey--watch out!
/]
PUSHJ P,SNDMSG
; Get terminal characteristics
NOFLAK: MOVE Y,[440600,,CNSBLK] ; pointer to characteristics block
MOVEI Z,6
GETSIZ: PUSHJ P,NETICW
IDPB Y
SOJG Z,GETSIZ
HLRO X,CNSBLK
MOVNS Z,X ; size of block
CAILE Z,CNSBLL-1
MOVEI Z,CNSBLL-1 ; additional args we don't know about
IMULI Z,6
GETCNS: PUSHJ P,NETICW
IDPB Y
SOJG Z,GETCNS
CAIN X,CNSBLL-1
JRST CHKTRM
CAIG X,CNSBLL ; more than we wanted?
JRST CHKTRM ; too few
SUBI X,CNSBLL-1 ; too many
IMULI X,6
PUSHJ P,NETICW ; eat extra bytes
SOJG X,.-1
; Check terminal out
CHKTRM: MOVE TCTYP
CAIE %TNSFW ; software?
JRST [ MOVEI X,[ASCIZ/Sorry, TCTYP must be %TNSFW.
/]
OUTSTR (X)
PUSHJ P,SNDMSG
INTMSK [0]
PUSHJ P,CLOSER
JRST SUICID]
MOVE TTYOPT
TLNE (%TOOVR)
SETOM OVRPRP ; remember overprinting!
TLNN (%TOSAI) ; FCS terminal?
JRST NOTSAI
MOVEI X,1
IORM X,MODSET ; set DM128 bit
SETOM 128CHP
NOTSAI: AND [%TOERS\%TOMVB\%TOMVU\%TOFCI\%TOLID\%TOCID\%TPCBS]
CAMN [%TOERS\%TOMVB\%TOMVU\%TOFCI\%TOLID\%TOCID\%TPCBS]
JRST GETPTY
MOVEI X,[ASCIZ\Sorry, your console has insufficient display capabilities.
\]
OUTSTR (X)
PUSHJ P,SNDMSG
INTMSK [0]
PUSHJ P,CLOSER
JRST SUICID
;GETPTY MAINL MAINL0
SUBTTL Final initialization
; Get a PTY, put its number in A and other places
GETPTY: PTYGET A
JRST [ MOVEI 254 ; MAINTM
PEEK
PEEK
SKIPE
SKIPA X,[[ASCIZ/SU-AI - System being debugged, users not allowed on.
/]]
MOVEI X,[ASCIZ/SU-AI - All network ports in use.
/]
PUSHJ P,SNDMSG
INTMSK [0]
PUSHJ P,CLOSER
JRST SUICID]
HRRZM A,TTYLIN ; dumb interrupts
MOVSI (A)
IRPS FOO,,LINCHR XONOFF GAGOFF DPYSET MODSET IMPSET
IORM FOO
TERMIN
; Initialize the user's display mode
MOVEI %TDNOP
PUSHJ P,NETOCH
MOVEI %TDCLR
PUSHJ P,NETOCH
PUSHJ P,NETSND
; And get the terminal ready
MOVE TCMXV
CAILE VSZMAX
MOVEI VSZMAX
MOVEM TCMXV
MOVEM SETVSZ
MOVE TCMXH
CAILE HSZMAX
MOVEI HSZMAX
MOVEM TCMXH
ADDI 1 ; width is less 1 for the excl
ANDCMI 7 ; round down to a multiple of 8
MOVEM SETHSZ
MOVE [-NTYSTS,,TYSBLK]
TTYSET ; set up TTY parameters
MOVEI B,↑M
PTWR1W A
; Final initialization
MOVNI LOKTMO
MOVEM IDLTIM ; initialize lock timeout
LOCK ; keep response good
SETZM NODETP ; okay to detach jobs now
JRST NTISER ; check network input
; Main program loop
MAINL: IWAIT ; wait for an interrupt
MAINL0: MOVEI 2 ; check connection status
MTAPE NET,
TLNN 1,(CLSS\CLSR) ; send side gronked?
TLNE 2,(CLSS\CLSR) ; receive side?
JRST SUICID
AOSG NTINTP ; net input?
JRST NTISER
AOSG PTINTP ; PTY input?
JRST PTISER
AOSG DOQUIT ; QUIT seen?
JRST SUICID
JRST MAINL ; back to sleep for us
;NTISER
SUBTTL Network input interrupt
NTISER: PUSHJ P,NETICH ; get character from the network
JRST MAINL0 ; network input buffer empty
SKIPL IDLTIM
LOCK
MOVNI 1,LOKTMO
MOVEM 1,IDLTIM ; reset idle time
AOSGE 1,FLSCNT ; flush this character?
JRST NTISER
JUMPE 1,[ PUSHJ P,SNDPOS ; tell user what position really is
JRST NTISER]
SKIPE BKYBTS ; if have bucky bits
JRST PTYSN0 ; forget all this cruft
SKIPE EATERP ; getting terminal name?
JRST [ IDPB TERMBP ; save character
JUMPN NTISER
SETZM EATERP ; got it all
JRST NTISER]
AOSN PRESCP
JRST [ CAIN ↑\ ; quoted?
JRST PTYSN0
CAIN ↑P
JRST [ MOVNI 2 ? MOVEM FLSCNT
JRST NTISER] ; flush two characters
CAIN ↑C ; redisplay screen?
JRST [ PUSH P,["P] ; [BREAK]P command fixifies us
SETZ B,
PTWR1S A ; send first part of [ESCAPE]
CAI ; will lose soon enough
MOVEI B,"- ; convert [ESCAPE] to [BREAK]
JRST PTYSN2]
TRZN 100 ; bucky bits?
JRST NTISER ; losing somehow
LSH 7
MOVEM BKYBTS
JRST NTISER]
AOSN SDCMDP
JRST [ CAIN 301 ; logout?
SETOM NODETP
CAIN 302 ; get terminal name?
JRST [ SETOM EATERP
MOVEI ":
IDPB TERMBP
MOVEI <" >
IDPB TERMBP
JRST NTISER]
JRST NTISER]
CAIN 300 ; start of protocol command?
JRST [ SETOM SDCMDP
JRST NTISER]
CAIN ↑\ ; protocol escape command?
JRST [ SETOM PRESCP
JRST NTISER]
;PTYSN0 FNYQOT PTYSN1 PTYSN2 PTYSND
; Send character to the PTY
PTYSN0: MOVE B,
IOR B,BKYBTS ; add in bucky bits
SETZM BKYBTS
MOVE X,B
TRZ X,%TXMTA\%TXCTL ; get character without CONTROL and META
CAIN X,%TXTOP\"β ; beta?
JRST @FNYQOT
CAIE X,%TXTOP\"≡ ; equivalence?
CAIN X,%TXTOP\"∨ ; or?
FNYQOT: JRST [PUSH P,B
SETZ B, ; quote with escape
PTWR1S A
CAI
POP P,B
JRST PTYSN1]
CAIN X,%TXTOP\"_ ; underscore?
JRST [ MOVEI X,137
DPB X,[000700,,B]
JRST PTYSN1]
CAIN X,%TXTOP\↑K ; uparrow?
JRST [ MOVEI X,"↑
DPB X,[000700,,B]
JRST PTYSN1]
CAIN X,"← ; backarrow?
JRST [ MOVEI X,030
DPB X,[000700,,B]
JRST PTYSN1]
CAIN X,↑Z ; [CALL]?
JRST [ MOVEI X,↑C ; yes, convert to our [CALL]
DPB X,[000700,,B]
JRST PTYSN1]
CAIN X,%TXTOP\"A ; [ESCAPE]?
JRST [ SETZ B,
JRST PTYSND]
CAIN X,%TXTOP\"B ; [BREAK]?
JRST [ PUSH P,["-]
SETZ B,
JRST PTYSN2]
CAIN X,%TXTOP\"C ; [CLEAR]?
JRST [ MOVEI B,↑↑
JRST PTYSND]
PTYSN1: TRZ B,%TXTOP ; flush top now
TRZN B,%TXMTA ; meta set?
JRST PTYSND
PUSH P,B
MOVEI B,200 ; <EDIT>[NULL]
PTYSN2: PTWR1S A ; send prefix meta command
CAI ; will lose soon enough
POP P,B
PTYSND: PTWR1S A ; send character to PTY
JRST [ MOVEI %TDBEL ; bell
PUSHJ 17,NETOCH
PUSHJ 17,NETSND ; output it
JRST NTISER]
JRST NTISER ; try for more user characters
;PTISER PTISR1 CHKCYP CHKDMC DMSND DMSND0 MRKNBL ISPCH NOTPCH
SUBTTL PTY input interrupt
PTISER: MOVE B,[441140,,PTIBUF]
PTRDS A ; read buffer from PTY
ILDB B
JUMPE [ PUSHJ P,NETSND ; buffer empty, force output out
JRST MAINL0]
SKIPA D,
PTISR1: ILDB D,B
JUMPE D,PTISER
MOVNI LOKTMO
MOVEM IDLTIM ; reset idle time
ANDI D,377 ; flush funny 400 bit
AOSN LFFLSP ; flush a line feed?
CAIE D,↑J
CAIA
JRST PTISR1
AOSN QUOTEP ; quote frob?
JRST DMSND
AOSN GETCXP ; set X position?
CAIG D,↑← ; yes, abort?
JRST CHKCYP
XORI D,140
CAMLE D,TCMXH ; beyond screen limit?
SETZ D,
MOVEM D,HPOS
SETOM GETCYP
JRST PTISR1
CHKCYP: AOSN GETCYP ; set Y position?
CAIG D,↑← ; yes, abort?
JRST CHKDMC
XORI D,140
CAML D,TCMXV ; beyond screen limit?
SETZ D,
MOVEM D,VPOS
JRST SETCPS ; finally set position
CHKDMC: CAIG D,<" > ; DM command?
XCT DMCTAB(D)
DMSND: CAIN D,013 ; integral sign?
JRST [ MOVEI D,177
JRST DMSND0]
CAIN D,"_ ; underscore?
JRST [ MOVEI D,137
JRST DMSND0]
SKIPN 128CHP
JRST DMSND0
CAIN D,"↑ ; uparrow?
JRST [ MOVEI D,013
JRST DMSND0]
CAIN D,"← ; backarrow?
JRST [ MOVEI D,030
JRST DMSND0]
CAIN D,177 ; circumflex?
JRST [ MOVEI D,136
JRST DMSND0]
DMSND0: CAIL D,200 ; a %TD code?
JRST NOTPCH
SKIPN OVRPRP
JRST ISPCH
PUSHJ P,GETSMD
TDNN X,(Y)
JRST MRKNBL ; position already blank
MOVEI %TDDLF ; delete character at this position
PUSHJ P,NETOCH
MRKNBL: IORM X,(Y) ; mark position as non-blank
ISPCH: AOS HPOS ; no, account for character
NOTPCH: MOVE D
PUSHJ P,NETOCH
JRST PTISR1
;SCLEAR CANCEL CLEOL SETCPS SNDPOS INSLIN IDCMND SPACE FORSPC
; Datamedia conversion subroutines
SCLEAR: MOVEI %TDCLR ; clear screen
PUSHJ P,NETOCH
SETZM HPOS ; home up
SETZM VPOS
SKIPN OVRPRP
JRST CANCEL
SETZM SCRMST ; clear screen bit mask
MOVE [SCRMST,,SCRMST+1]
BLT SCRMST+3*VSZMAX-1
CAIA ; roll isn't cancelled by this
CANCEL: SETZM ROLLP
SETZM INDLMP
; MOVEI %TDRST
; PUSHJ P,NETOCH
JRST PTISR1
CLEOL: MOVEI %TDEOL
PUSHJ P,NETOCH
SKIPN OVRPRP
JRST PTISR1
PUSHJ P,GETSMD
ANDCAM X,(Y) ; flag current position as blank
SUBI X,1
ANDCAM X,(Y) ; flag rest of word as blank
CAIE Z,2
SETZM 1(Y) ; 0 or 1 → flag next word as blank
JUMPN Z,PTISR1
SETZM 2(Y) ; 0 → flag word after that as blank
JRST PTISR1
SETCPS: PUSHJ P,SNDPOS
JRST PTISR1
SNDPOS: MOVEI %TDMV0 ; set cursor position
PUSHJ P,NETOCH
MOVE VPOS
CAML TCMXV ; beyond screen limit?
SETZB VPOS ; paranoia for dumb ITS SUPDUP
PUSHJ P,NETOCH
MOVE HPOS
CAMLE TCMXH
SETZM HPOS
JRST NETOCH
INSLIN: MOVEI %TDILP
SKIPN OVRPRP
JRST IDCMND
MOVEI X,VSZMAX-1
SUB X,VPOS ; # of lines to move
IMULI X,3
ADDI X,377777 ; # of lines-1 w/ sign bit
HRL X,X
HRRI X,SCRMST+3*<VSZMAX-1>-1 ; source address
POP X,3(X) ; reverse BLT
JUMPL X,.-1
IDCMND: PUSHJ P,NETOCH ; insert/delete mode command
MOVEI 1
PUSHJ P,NETOCH
JRST PTISR1
SPACE: SKIPN OVRPRP
JRST ISPCH
MOVEI %TDDLF
PUSHJ P,NETOCH
PUSHJ P,GETSMD
ANDCAM X,(Y) ; flag position as blank
FORSPC: MOVEI %TDFS ; forespace
PUSHJ P,NETOCH
AOS HPOS
JRST PTISR1
;DMCTAB
SUBTTL Datamedia command table
DMCTAB: JRST PTISR1 ; ↑@ no-op
JRST PTISR1 ; ↑A no-op
JRST [ SETZM HPOS ; ↑B home up
SETZM VPOS
JRST SETCPS]
JRST PTISR1 ; ↑C no-op
JRST PTISR1 ; ↑D no-op
JRST PTISR1 ; ↑E no-op
JRST PTISR1 ; ↑F no-op
MOVEI D,%TDBEL ; ↑G bell
JRST [ SKIPE INDLMP ; ↑H backspace/delete character
JRST [ MOVEI %TDDCP
SKIPN OVRPRP
JRST IDCMND
PUSHJ P,GETSMD
MOVE D,(Y)
LSH X,1
SUBI X,1 ; mask for bits being hacked
ANDCAM X,(Y)
LSH D,1 ; shift characters over
AND D,X
IORM D,(Y)
CAIN Z,2
JRST IDCMND
MOVEI C,1 ; bit to bring in previous words if needed
MOVE D,1(Y)
LSH D,1 ; shift characters over
TLZE D,(1←32.)
IORM C,(Y) ; bring in overflow to next word
MOVEM D,1(Y)
JUMPN Z,IDCMND ; if last word flush
MOVE D,2(Y)
LSH D,1
TLZE D,(1←32.)
IORM C,1(Y)
MOVEM D,2(Y)
JRST IDCMND]
SOSGE HPOS
SETZM HPOS
JRST SETCPS]
JRST [ MOVE HPOS ; ↑I tab
TRZ 7
ADDI 8.
MOVEM HPOS
JRST SETCPS]
JRST [ SKIPE INDLMP ; ↑J line feed/insert line
JRST INSLIN
AOS VPOS
JRST SETCPS]
JRST PTISR1 ; ↑K tab clear (no-op)
JRST [ SETOM GETCXP ; ↑L cursor position
JRST PTISR1]
JRST [ AOS X,VPOS ; ↑M terpri
SETZM HPOS
SETOM LFFLSP
SKIPN ROLLP ; scrolling?
JRST [ CAML X,TCMXV ; not scrolling; gone off bottom?
SETZM VPOS ; yes, wrap around to top of screen
JRST SETCPS] ; use %TDMV0 to move cursor
MOVEI %TDCRL ; scrolling, use %TDCRL instead
PUSHJ P,NETOCH
CAMGE X,TCMXV
JRST PTISR1
MOVE TCMXV ; somehow we scrolled
SOS
MOVEM VPOS
MOVE [SCRMST+3,,SCRMST]
BLT SCRMST+3*VSZMAX-1
JRST PTISR1]
; MOVEI D,%TDBOW ; ↑N blink on (set complement mode)
JRST PTISR1 ; ↑N blink on (no op for now)
JRST PTISR1 ; ↑O bold on (no-op)
JRST [ SETOM INDLMP ; ↑P enter I/D mode
JRST PTISR1]
;DMCTAB...
JRST PTISR1 ; ↑Q transmit page to computer (no-op)
JRST PTISR1 ; ↑R transmit page to printer (no-op)
JRST PTISR1 ; ↑S transmit line to computer (no-op)
JRST PTISR1 ; ↑T no-op
JRST PTISR1 ; ↑U no-op
JRST PTISR1 ; ↑V no-op
JRST CLEOL ; ↑W erase to end of line
JRST CANCEL ; ↑X cancel bold, I/D, roll
JRST PTISR1 ; ↑Y set tab (no-op)
JRST [ SKIPE INDLMP ; ↑Z line starve/delete row
JRST [ MOVEI %TDDLP
SKIPN OVRPRP
JRST IDCMND
MOVE X,VPOS
LSH X,1
ADD X,VPOS
ADDI X,SCRMST
HRLI X,3(X)
BLT X,SCRMST+3*VSZMAX-1
JRST IDCMND]
SOSGE VPOS
SETZM VPOS
JRST SETCPS]
JRST [ SETOM QUOTEP ; ↑[ quote FCS character
JRST PTISR1]
JRST [ SKIPN INDLMP ; ↑\ forespace/insert character
JRST FORSPC
MOVEI %TDICP
SKIPN OVRPRP
JRST IDCMND
PUSHJ P,GETSMD
MOVE D,(Y)
LSH X,1
SUBI X,1 ; fill in mask to the right
ANDCAM X,(Y)
AND D,X
LSHC D,-1
IORM D,(Y)
CAIN Z,2
JRST IDCMND
MOVE D,1(Y)
SKIPGE C
TLO D,(1←31.) ; bring in bit from previous word
LSHC D,-1
MOVEM D,1(Y)
JUMPN Z,IDCMND
MOVE D,2(Y)
SKIPGE C
TLO D,(1←31.)
LSH D,-1
TRZ D,100000 ; flush overflow bit
MOVEM D,2(Y)
JRST IDCMND]
JRST [ SETOM ROLLP ; ↑] roll on
JRST PTISR1]
JRST SCLEAR ; ↑↑ master clear
JRST SCLEAR ; ↑← erase screen
JRST SPACE ; sp delete character and forespace
IFN .-DMCTAB-1-" ,.ERR DMCTAB loses!
;GETSMD BITTAB SNDMSG MSGLUP ERRDIE SUICID DIEDIE ...LIT SVRRTS ERRTNS ERRHAN ERRINS HSTTAB HSTSIX
SUBTTL Subroutines
; Get screen mask data in Y, Z, X
GETSMD: MOVE Y,VPOS
LSH Y,1
ADD Y,VPOS
MOVE Z,HPOS
LSH Z,-5 ; Z ← word index in line (for cleol)
ADDI Y,SCRMST(Z) ; Y ← addr of screen mask word
MOVE X,HPOS
ANDI X,37
MOVE X,BITTAB(X) ; X ← mask for this byte
POPJ P,
; Bit table
BITTAB: REPEAT 32.,1←<31.-.RPCNT> ; bit table
; Send a message, b.p. in X
SNDMSG: TLOA X,440700 ; set up b.p.
MSGLUP: PUSHJ P,NETOCH
ILDB X
JUMPN MSGLUP ; continue until a null hit
JRST NETSND
; Here to suicide on network errors or idle timeout
ERRDIE: INTMSK [0]
SUICID: OUTSTR [ASCIZ/Connection closed.
/]
SKIPE NODETP
JRST DIEDIE ; logout the guy
MOVE TTYLIN
TTYJOB
JUMPE DIEDIE
MOVE A,TTYLIN
MOVEI B,7
PTJOBX A ; clear PTY's input buffer
MOVEI 2
MOVEI B,10 ; DETACH
PTJOBX A
JRST [SLEEP ? JRST .-1]
SLEEP
PTRD1S A ; slurp up stuff in buffer
CAIA
JRST .-2
DIEDIE: RESET ? EXIT
...LIT: CONSTANTS
; Wonderful network routines
SVRRTS==-1 ; include server routines
ERRTNS==-1 ; include error routines
ERRHAN==-1 ; include automagic error handling
ERRINS==<JRST ERRDIE> ; error instruction
HSTTAB==-1 ; include host table magic
HSTSIX==-1 ; and alias name kludge
.INSRT NETWRK
END SUPSER