home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Columbia Kermit
/
kermit.zip
/
pdp11
/
k11rtt.mac
< prev
next >
Wrap
Text File
|
2020-01-01
|
16KB
|
611 lines
.title k11rtt mt terminal service for Kermit-11/RT
.ident /1.0.01/
; 28-May-84 09:06:31 Brian Nelson
;
; Copyright (C) 1984 Change Software, Inc.
.if ndf, K11INC
.ift
.include /IN:K11MAC.MAC/
.endc
.psect
.sbttl definitions for multiple terminal support
.mcall .mtstat ,.mtatch,.mtdtch,.mtget ,.mtin
.mcall .mtout ,.mtprnt,.mtrcto,.mtset
.mcall .mrkt ,.cmkt ,.twait ,.ttinr
.enabl gbl
m.tsts = 0 ; terminal status word
m.tst2 = 2 ; terminal status word number 2
m.tfil = 4 ; character requiring fill
m.fcnt = 5 ; number of fillers
m.twid = 6 ; width
m.tstw = 7 ; terminal status byte
m.nlun = 4 ; number of terminals for .mtstat
.macro $mterr ; map multiple terminal service
movb @#errbyt,r0 ; into a global error code
asl r0 ; simple to do
mov mterr(r0),r0 ; thats all there is to it
.endm $mterr
.save
.psect mtmap ,rw,d,lcl,rel,con
lunmap: .blkw 12 ; map LUNS to RT units
mtsts: .blkw 10 ; from the .mtstat call
ttsts: .blkw 10 ; for ttyini
tmowrk: .blkw 10 ; for mark time while reading
ttsave: .blkw 4
ttctlc: .blkw 1 ; for control C things in connect mode
ttime: .word 0,1 ; a tick sleep for .twait
.restore
.sbttl assign the terminal unit
m.assdev::
save <r1> ; we may want to use these
.mtstat #rtwork ,#mtsts ; get terminal driver status
bcs 90$ ; oops
tst mtsts+m.nlun ; any multi tty support in exec?
beq 80$ ; no, thats fatal
call ttpars ; parse the device unit number
bcs 70$ ; bad device name
mov r0 ,r1 ; save the unit number now
.mtatch #rtwork,#kbiost,r1 ; try to attach the terminal now
bcs 90$ ; fatal error, exit
clr r0 ; ok, exit with success
br 100$ ; bye
70$: mov #er$dev ,r0 ; return bad device name error
br 100$ ; bye
80$: mov #er$sup ,r0 ; return missing support error
br 100$ ; bye
90$: $mterr ; map local error into global error
100$: unsave <r1> ; pop local registers and exit
return
m.deadev::
save <r1> ; save this one, folks
call ttpars ; parse the device name
bcs 70$ ; oops
mov r0 ,r1 ; save the unit number now
.mtdtch #rtwork,r1 ; do it
clr r0 ; success
br 100$ ; bye
70$: mov #er$dev ,r0 ; bad device name error
br 100$ ; bye
100$: unsave <r1> ; exit
return ; dh
.sbttl initialize the terminal
; T T Y I N I
;
; input: @r5 device name
; 2(r5) LUN
; 4(r5) modifiers
;
; output: r0 error code
ttmode = 100 ! 10000 ! 40000
m.ttyini::
save <r1,r2> ; we will need this one
call ttpars ; get the unit number
bcs 70$ ; oops, return ER$DEV error
mov 2(r5) ,r1 ; get the internal LUN to use
asl r1 ; into a word offset
mov r0 ,lunmap(r1) ; so we can map lun into a unit
movb #377 ,lunmap+1(r1) ; say we have done this already
mov r0 ,r1 ; save the unit number please
.mtatch #rtwork,#kbiost,r1 ; ensure it's attached
mov #ttsts ,r2 ; point to the status area
.mtget #rtwork,r2,r1 ; get the current terminal setting
bcs 90$ ; oops
bic #2 ,m.tsts(r2) ; no automatic cr/lf's please
bis #ttmode ,m.tsts(r2) ; no lower case convert, no echo
bis #200!100000,m.tst2(r2) ; read and write pass all please
.mtset #rtwork,r2,r1 ; set these please
bcs 90$ ; oops
mov #1000 ,r2
10$: calls binrea ,<2(r5),#-1> ; eat anything that's pending please
dec r2 ; don't loop forever please
beq 20$ ; exit the loop
tst r0 ; did we get anything at all ?
beq 10$ ; yes, eat some more input
20$: clr r0 ; all done
br 100$ ; bye
70$: mov #er$dev ,r0 ; device name parse failed
br 100$ ; bye
90$: $mterr ; map local error into a global one
100$: unsave <r2,r1> ; pop and exit
return
.sbttl save/restore terminal settings
m.ttysav::
save <r1> ; we will use this one
call ttpars ; parse the unit number please
bcs 80$ ; oops
mov r0 ,r1 ; copy the parsed unit number
.mtget #rtwork,#ttparm,r1 ; get the current settings
bcs 90$ ; error
clr r0 ; success
br 100$ ; bye
80$: mov #er$dev ,r0 ; bad device name
br 100$ ; bye
90$: $mterr ; error, map into global and exit
100$: unsave <r1> ; pop this and exit
return
m.ttyrst::
save <r1,r2> ; we will use this one
clr r2 ; was already attached
call ttpars ; parse the unit number please
bcs 80$ ; oops
mov r0 ,r1 ; copy the parsed unit number
.mtset #rtwork,#ttparm,r1 ; get the current settings
bcc 20$ ; it worked
cmpb @#errbyt,#1 ; not attached?
bne 90$ ; no
.mtatch #rtwork,#0,r1 ; yes, attach it
bcs 90$ ; oops
mov sp ,r2 ; flag we just attached it
.mtset #rtwork,#ttparm,r1 ; get the current settings
bcs 90$ ; error
20$: clr r0 ; success
br 100$ ; bye
80$: mov #er$dev ,r0 ; bad device name
br 100$ ; bye
90$: $mterr ; error, map into global and exit
100$: tst r2 ; need to detach it again
beq 110$ ; no
.mtdtch #rtwork,r1 ; yes, do it please
110$: unsave <r2,r1> ; pop this and exit
return
.sbttl binrea read binary
; B I N R E A
;
; input: @r5 LUN
; 2(r5) timeout
; output: r0 error code
; r1 character just read
m.xbinre::
m.binrea::
save <r2,r3,r4> ; we may want to use these here
clr -(sp) ; allocate a single character buffer
mov sp ,r4 ; and a pointer to it also
clr -(sp) ; allocate a mark time tim buffer
clr -(sp) ; simple
mov sp ,r2 ; and point to it
mov @r5 ,r3 ; get the LUN
asl r3 ; and map it into the unit number
movb lunmap(r3),r3 ; simple
;- .mtget #rtwork,#ttsts,r3 ; get current terminal setting
;- bcs 90$ ; oops
;- bis #ttmode ,ttsts+m.tsts ; set so we don't wait for anything
;- .mtset #rtwork,#ttsts,r3 ; set this please
;- bcs 90$ ; can't set it for some reason
cmp 2(r5) ,#-1 ; read without any wait ?
bne 40$ ; no
.mtin #rtwork,r4,r3,#1 ; read a single character now
bcs 80$ ; it worked
clr r1 ; get the character into r1 now
bisb @r4 ,r1 ; and exit with success
clr r0 ; bye
br 100$ ; exit at last
40$: mov 2(r5) ,r1 ; get the timeout in seconds
mul #60. ,r1 ; into ticks now
50$: .mtin #rtwork,r4,r3,#1 ; do it please
bcc 60$ ; it worked, get the ch into r1
dec r1 ; been here too long ?
beq 80$ ; yes, exit with error
tst clkflg ; /37/ is there a clock on system?
bne 55$ ; /37/ yes
cpuwait #1 ; /37/ no, try loop for one tick
br 56$ ; /37/ very cpu speed dependent.
55$: .twait #rtwork,#ttime ; sleep a moment please
56$: br 50$ ; and try again please
60$: clr r1 ; it worked, get the character and exit
bisb @r4 ,r1 ; simple
clr r0 ; success
br 100$
80$: mov #er$nin ,r0 ; no data today
br 100$ ; bye
90$: $mterr ; map the error code into a global one
100$: add #6 ,sp ; pop local buffers
unsave <r4,r3,r2> ; pop registers and exit
return
200$: mov #1 ,r1 ; flag a timeout
return
.sbttl binary write
; B I N W R I
;
; binwri( %loc buffer, %val buffer_size, %val lun )
;
; output: r0 error code
;
; Assumption: TTYINI has been called to map the Kermit LUN
; into the RT11 unit number for the terminal.
m.binwri::
save <r1,r2,r3,r4,r5> ; save registers we may need
sub #20 ,sp ; a save area for tt settings
clr r0 ; preset no errors as of yet
mov @r5 ,r1 ; get the string address
mov 2(r5) ,r2 ; get the string length
beq 100$ ; nothing to do
mov #ttsts ,r3 ; for getting tt settings
mov 4(r5) ,r4 ; the internal LUN
bne 10$ ; map LUN 0 to console
print r1,r2 ; simple
clr r0 ; no errors
br 100$ ; exit
10$: mov sp ,r5 ; point to the stack work area
asl r4 ; times two
tstb lunmap+1(r4) ; have we mapped the lun into unit?
beq 80$ ; no, fatal error
movb lunmap(r4),r4 ; map into the rt11 unit number
.mtget #rtwork,r3,r4 ; get current settings, set to wait
bcs 90$ ; oops, exit with the error code in r0
mov (r3)+ ,(r5)+ ; copy the four words now
mov (r3)+ ,(r5)+ ; copy the four words now
mov (r3)+ ,(r5)+ ; copy the four words now
mov (r3)+ ,(r5)+ ; copy the four words now
bit #100 ,ttsts+m.tsts ; is the wait bit set already ?
beq 20$ ; no, don't bother to clear it
bic #100 ,ttsts+m.tsts ; set so we will wait for buffer space
.mtset #rtwork,#ttsts,r4 ; simple to set
20$: .mtout #rtwork,r1,r4,r2 ; do the output now
bcs 90$ ; oops, it failed for whatever reason
mov -(r5) ,-(r3) ; restore the terminal settings
mov -(r5) ,-(r3) ; restore the terminal settings
mov -(r5) ,-(r3) ; restore the terminal settings
mov -(r5) ,-(r3) ; restore the terminal settings
.mtset #rtwork,r3,r4 ; simple
clr r0 ; say it worked and exit
br 100$ ; bye
80$: mov #er$map ,r0 ; rt11 unit not mapped to internal LUN
br 100$ ; bye
90$: $mterr ; map mt error into global error code
100$: add #20 ,sp ; pop local work buffer
unsave <r5,r4,r3,r2,r1> ; pop the saved registers
return ; and exit
.sbttl parse terminal unit
; T T P A R S
;
; input: @r5 address of RT11 Multiple terminal service unit string
; output: r0 unit in binary
m.ttpars::
mov r1 ,-(sp) ; save scratch register please
mov @r5 ,r0 ; get the address of the string
call 200$ ; check for legit character
bcs 110$ ; oops
movb (r0)+ ,r1 ; get the first byte please
sub #'0 ,r1 ; convert to binary
call 200$ ; check for legit character
bcs 110$ ; oops
movb @r0 ,r0 ; get the next digit
beq 100$ ; nothing there then we are done
mul #12 ,r1 ; something there, shift over by 10
sub #'0 ,r0 ; and convert low digit to binary
add r0 ,r1 ; add into the accumulator
100$: mov r1 ,r0 ; and return the result
clc ; return success
110$: mov (sp)+ ,r1
return
200$: tstb @r0 ; null ?
beq 210$ ; yes, it's ok
cmpb @r0 ,#'0 ; must only be digits today
blo 220$ ; oops
cmpb @r0 ,#'9 ; 0..9
bhi 220$ ; bad device name
210$: clc ; device name ok so far
return ; bye
220$: sec ; bad, set and exit
return
.sbttl GTTNAM get MT unit of current console (set tt:consol=nn)
; G T T N A M
;
; input: @r5 address of console name to be written
; output: @r5 current console name
; consave same thing
.mcall .mtstat
; data returned by .mtstat
;
; offset 0 offset from RMON base to first TCB
; 2 offset from RMON base to the current console TCB
; 4 numer of luns generated into the exec
; 6 size of the TCB in bytes
;
; Since the TCB does NOT contain a copy of the LUN in it, we have
; to start with TCB number 0 and add in the TCB size until we get
; the value of the offset to the current console's TCB. Counting
; this will give us the LUN for that TCB.
m.gttnam::
save <r1,r2,r3> ; save registers please
.mtstat #rtwork,#mtsts ; get info on mt service
clr r3 ; current lun number, starts with zero
tst mtsts+4 ; see if mt service is present?
beq 30$ ; no, ignore it for now
mov mtsts+0 ,r1 ; offset to tcb for console interface
mov mtsts+4 ,r2 ; number of tcb's generated in exec
10$: cmp r1 ,mtsts+2 ; find our tcb yet?
beq 20$ ; yes, exit
inc r3 ; no, then lun := succ(lun)
add mtsts+6 ,r1 ; add the tcb size in and compage offset
dec r2 ; if more tcbs to do, then try again
bne 10$ ; next please
20$:
30$: asl r3 ; get word indexing please to map the
add #200$ ,r3 ; value into a ascii string.
mov @r5 ,r1 ; where to put it please
movb (r3)+ ,@r1 ; copy a byte
cmpb @r1 ,#40 ; but if it's a blank, then skip it
beq 40$ ; a space
inc r1 ; not a space, bump the dest pointer
40$: movb (r3)+ ,(r1)+ ; copy the next character now
clrb @r1 ; always make it .asciz
mov @r5 ,r1 ; copy to consave:
mov #consave,r2 ;
50$: movb (r1)+ ,(r2)+ ; simple to copy .asciz string
bne 50$ ; next please
100$: clr r0
unsave <r3,r2,r1>
return
; This is a rather dumb way to convert to ascii, but there are only
; a few values, and it is easier to test via downloading to my PDT
; with Kermit since the PDT150 lacks DIV.
200$: .asciz / 0 1 2 3 4 5 6 7 8 9/
.asciz /101112131415161718/
.even
global <consave>
m.ttyfin::
call ttpars ; finish up mt service
mov r0 ,r1 ; parse the device name
.mtdtch #rtwork,r1 ; and detach the device now
clr r0 ; return 'success'
return ; and exit
.sbttl speed read and change
m.setspd::
save <r1,r2,r3> ; save temps that we will use
clr r0 ; find the speed map now
10$: tst spdlst(r0) ; reach the end of the table?
beq 80$ ; yes, return unknown speed
cmp 2(r5) ,spdlst(r0) ; table entry match the passed speed
beq 20$ ; yes
add #2 ,r0 ; no, try the next one please
br 10$ ; next please
20$: mov spdmap(r0),r3 ; and get the speed setting bits
call ttpars ; parse the mt unit number
bcs 70$ ; oops
mov r0 ,r1 ; save the unit number
.mtatch #rtwork,#kbiost,r1 ; insure unit is attached
mov #ttsts ,r2 ; point to the status area
.mtget #rtwork,r2,r1 ; get the current terminal setting
bcs 90$ ; oops
bic #7400 ,m.tsts(r2) ; clear out old speed bits
bis r3 ,m.tsts(r2) ; stuff the dz11 speed bits in
.mtset #rtwork,r2,r1 ; set these please
bcs 90$ ; oops
clr r0 ; all done
br 100$ ; bye
70$: mov #er$dev ,r0 ; device name parse failed
br 100$ ; bye
80$: mov #er$spe ,r0 ; unknown speed ?
br 100$
90$: $mterr ; map local error into a global one
100$: unsave <r3,r2,r1> ; pop and exit
return
m.ttspee::
save <r1,r2,r3> ; save these please
call ttpars ; parse the mt unit number
bcs 70$ ; oops
mov r0 ,r1 ; save the unit number
.mtatch #rtwork,#kbiost,r1 ; insure unit is attached
mov #ttsts ,r2 ; point to the status area
.mtget #rtwork,r2,r1 ; get the current terminal setting
bcs 90$ ; oops
mov m.tsts(r2),r3 ; get the speed mask out now
bic #^C7400 ,r3 ; drop all bits but the speed
clr r0 ; now look for the correct speed map
10$: tst spdmap(r0) ; reach the end of the list ?
bmi 80$ ; yes, return a speed of zero
cmp r3 ,spdmap(r0) ; setting match up now ?
beq 20$ ; yes
add #2 ,r0 ; no, try again please
br 10$ ; next
20$: mov spdlst(r0),r0 ; a match, return the speed setting
br 100$ ; bye
70$: mov #er$dev ,r0 ; device name parse failed
br 100$ ; bye
80$: clr r0 ; failure
br 100$ ; return a speed of zero then
90$: $mterr ; map local error into a global one
100$: unsave <r3,r2,r1> ; pop and exit
return
.save
.psect $pdata
spdlst: .word 50. ,75. ,110. ,134. ,150. ,300. ,600.
.word 1200. ,1800. ,2000. ,2400. ,3600. ,4800. ,7200.
.word 9600. ,0 ,0
spdmap: .word 0 ,400 ,1000 ,1400 ,2000 ,2400 ,3000
.word 3400 ,4000 ,4400 ,5000 ,5400 ,6000 ,6400
.word 7000 ,7400 ,-1
.restore
.sbttl terminal i/o things we don't need, can't do or haven't done yet
m.ttxon::
m.cantyp::
m.ttset::
m.ttydtr::
m.ttrfin::
m.ttrini::
clr r0
return
m.ttyhan::
mov #er$iop ,r0
return
.mcall .ttyin
jsw = 44
m.kbread::
mov r2 ,-(sp)
mov r3 ,-(sp)
bis #40000 ,@#jsw ; enable lower case tt: input
bic #10000 ,@#jsw ; ditch single ch input please
mov @r5 ,r1 ; a buffer to put the chars
mov #80. ,r3 ; size of the buffer here
;10$: .scca #area ,#kmonbf ; so we can catch control Z
10$: .ttyin ; read a character please
tstb r0
beq 15$ ; a null
cmpb r0 ,#'Z&37 ; control Z ?
beq 20$ ; yes
cmpb r0 ,#'C&37 ; control C ?
beq 20$ ; yep
cmpb r0 ,#15 ; carriage return ?
beq 30$ ; yep
movb r0 ,(r1)+ ; return what we just got
cmpb r0 ,#14 ; form feed ?
beq 40$ ; yep
15$: sob r3 ,10$ ; next please
20$: mov #er$eof ,r0 ; say read error and exit
br 100$ ; bye
30$: movb #cr ,(r1)+ ; return all terminators please
movb #lf ,(r1)+ ; simple
.ttyin ; eat the line feed now
40$: clrb @r1
sub @r5 ,r1 ; the length
clr r0
100$: mov (sp)+ ,r3
mov (sp)+ ,r2
return
m.finrt:: ; /37/
clr r0 ; /37/
return ; /37/
m.senbrk::
calls ttspee ,<@r5> ; get the remotes terminal speed
mov r0 ,r2 ; save the old speed
calls setspd ,<@r5,#50.,2(r5)>;try to set it down to 50 baud
tst r0 ; did it work ?
bne 100$ ; no, forget it
calls binwri ,<#200$,#2,2(r5)>;yes, send a null over
calls setspd ,<@r5,r2,2(r5)> ; restore the terminal's speed
100$: clr r0
return
200$: .byte 0,0
.end