1
0
mirror of https://github.com/PDP-10/its.git synced 2026-03-22 09:03:20 +00:00

Files for CHAT.

This commit is contained in:
Lars Brinkhoff
2018-02-23 09:43:51 +01:00
parent 3c2f52304a
commit 1814765cb5
4 changed files with 803 additions and 0 deletions

581
src/alan/chat.112 Normal file
View File

@@ -0,0 +1,581 @@
;;;-*-Midas-*-
title Chat -- User.
.insrt chat format
if2, ffpage==:com"page+com"npages ;First free page.
a=:1
b=:2
c=:3
d=:4
e=:5
t=:6 ? intacs==:t_6+3 ;T, TT & X saved by interrupts.
tt=:7
x=:10
pi=:15 ;PI=I-1 So JFFO will load I
i=:16 ;Bit numbers kept here.
u=:17 ;Keep our UIND here at all times!
dsk==:1
usr==:2
ttyo==:3
ttyi==:4
stop=:.break 16,100000
quit=:.logout 1,
tyo=:.iot ttyo,
tyi=:.iot ttyi,
;;;Flags in 0
%f==:0,,525252
%fsail==:1_17. ;User's terminal has SAIL characters.
%ffull==:1_16. ;User's keyboard can generate the full character set.
%fmeta==:1_15. ;User's keyboard has a Meta key.
%faty==:1_14. ;The TTY has been returned to us, but the user hasn't typed
;any characters since then.
;;;Pre-allocated bits in our UHANG word.
%b==:525252,,525252
%bcmd==:1_0 ;Wakeup from CMDBUF.
%brip==:1_1 ;Demon job vanished.
%baty==:1_2 ;The TTY has been returned to us and the user has typed a
;character, so the screen needs to be repainted.
nbits==:33. ;Free
define syscall name,args
.call [setz ? sixbit /name/ ? args(400000)]
termin
define lose code,pc
jrst [ syscall lose,[movei code ? movei pc]
.lose %lssys]
termin
define princ &string&
move t,[440700,,[ascii string]]
movei tt,.length string
.call sout
.lose %lssys
termin
.scalar height ;Height of the screen.
.scalar width ;Width of the screen.
define def name,size=1
name==:.val.
.val.==.val.+<size>
termin
.scalar aline ;First line on the screen.
.scalar zline ;Last line on the screen.
.scalar ptline ;Cursor is positioned at the end of this line.
.val.==0
;;;The line structure describes a single line of the user's display.
def l.next ;The logical next line.
def l.prev ;The logical previous line.
def l.down ;The next line on the user's screen. 0 => last line.
def l.up ;The previous line. 0 => first line.
def l.vpos ;The argument to V to position to the start of this line.
def l.bp.a ;Byte pointer to the beginning of the image of this line.
def l.bp.z ;Byte pointer to the end of the image of this line.
def l.room ;Count of columns of free space to the right of this line.
lline==:.val. ;Length of the line structure.
.vector window(1+nbits) ;One possible window for each bit, plus one
;more for the mode line.
.scalar uname
.scalar xuname
.scalar sname
.scalar hsname
go: setzi 0, ;Clear flags.
move tt,[-lintpdl,,intpdl-1] ;Set up interrupt pdl.
movem tt,intsp
movei tt,ffpage ;Free all memory.
movem tt,free
.suset [.roption,,a]
tlo a,%opint+%opopc+%oplok+%oplkf
move tt,[-9,,[ .ruind,,u
.soption,,a
.s40addr,,[twenty,,forty]
.smask,,[%pipdl+%piaty]
.smsk2,,[1_usr]
.runame,,uname
.rxuname,,xuname
.rsname,,sname
.rhsname,,hsname
]]
.suset tt
;;Initialize the TTY:
.open ttyo,[.uao+%tjdis+%tjmor+%tjctn,,'tty ? setz ? setz]
.lose %lsfil
.open ttyi,[.uai+%tiful+%tinwt+%tiint,,'tty ? setz ? setz]
.lose %lsfil
move tt,[-6,,[ sixbit /ttyopt/ ? movem a
sixbit /height/ ? movem height
sixbit /width/ ? movem width
]]
syscall ttyvar,[movei ttyi ? tt]
.lose %lssys
aos width ;Because we set %TJCTN.
trne a,%tpmta ;User has a meta bit?
tro %fmeta
tlne a,%tofci ;User has full keyboard?
tro %ffull+%fmeta
tlne a,%tomvu ;User has a display?
tlnn a,%toers
jrst [princ "AError: Terminal must be a display!"
quit]
movsi tt,%tscle+%tsmor+%tssai+%tsfco
tlne a,%tosai ;User has SAIL characters?
troa %fsail ;Yes.
tlz tt,%tssai+%tsfco ;No.
syscall ttyset,[movei ttyi
[<%tgint+%tgact>*<010101,,010101>]
[<%tgint+%tgact>*<010101,,010101>]
tt]
.lose %lssys
lcmdbuf==:200. ;Length in bytes.
.vector cmdbuf(com"buffer+<<lcmdbuf+4>/5>)
;;Initialize CMDBUF:
movei tt,lcmdbuf
movem tt,cmdbuf+com"bsize
movem tt,cmdbuf+com"iwrap
movem tt,cmdbuf+com"owrap
subi tt,1
movem tt,cmdbuf+com"icount
setzm tt,cmdbuf+com"ocount
movei tt,%bcmd
movem tt,cmdbuf+com"wkmask
movei tt,com"uhang(u)
movem tt,cmdbuf+com"wkaddr
setzm cmdbuf+com"inext
move tt,[440700,,cmdbuf+com"buffer]
movem tt,cmdbuf+com"iptr
movem tt,cmdbuf+com"optr
movei tt,cmdbuf
movem tt,input
;;Initialize the screen image:
move e,width
addi e,4
idivi e,5
addi e,lline ;E: number of words to allocate per line.
move a,e
imul a,height
addi a,1777
lsh a,-12 ;A: number of pages needed.
jsp t,alloc
syscall corblk,[movei %cbndr+%cbndw ? movei %jself ? tt ? movei %jsnew]
.lose %lssys
movem a,aline ;A: current line
setzi b, ;B: up line
movei c,8 ;C: vpos arg to V.
movsi d,440700 ;D: byte pointer.
move t,height ;T: loop counter.
move tt,width ;TT: width.
ilinlp: movem b,l.up(a)
movem c,l.vpos(a)
hrri d,lline(a)
movem d,l.bp.a(a)
movem d,l.bp.z(a)
movem tt,l.room(a)
sojle t,ilinex
move b,a
add a,e
movem a,l.down(b)
aoja c,ilinlp
ilinex: movem a,zline
setzm l.down(a)
move e,height
subi e,1 ;1 line for mode line.
idivi e,2 ;Separating 2 windows.
move a,aline
movem a,window+1
movei tt,[asciz "> "]
jsp t,prinz
jrst inp1go
inp1lp: move b,l.down(a)
movem b,l.next(a)
movem a,l.prev(b)
move a,b
inp1go: sojg e,inp1lp
move b,aline
movem a,l.prev(b)
movem b,l.next(a)
move a,l.down(a)
movem a,window+0
movem a,l.prev(a)
movem a,l.next(a)
movei tt,[asciz "------- Command: "]
jsp t,prinz
movem a,ptline
move a,l.down(a)
movem a,window+2
movei tt,[asciz "> "]
jsp t,prinz
jrst inp2go
inp2lp: movem a,l.prev(b)
movem b,l.next(a)
move a,b
inp2go: move b,l.down(a)
jumpn b,inp2lp
move b,window+2
movem a,l.prev(b)
movem b,l.next(a)
;;Contact the demon:
contac: syscall open,[moves e ? [.uii+10,,usr]
[sixbit /usr/]
move duname
move djname]
jrst [ cain e,%ensfl
jrst launch
lose %lsfil(e),.-1
]
move t,[-com"npages,,com"page]
move tt,[-com"npages,,com"dpage]
syscall corblk,[movei %cbndr+%cbndw
movei %jself ? move t
movei usr ? tt]
.lose %lssys
;;AOS the area use counter.
pioff
aos com"count
cntsw1: movei tt,cntswt
movem tt,forty+3
cntsw2: pion
;;Initialize process table:
movei tt,p.err
movem tt,proc
move tt,[proc,,proc+1]
blt tt,proc+nbits-1
movei tt,p.cmd
movem tt,proc+.lz %bcmd
movei tt,p.rip
movem tt,proc+.lz %brip
movei tt,p.aty
movem tt,proc+.lz %baty
;;Probably safe to handle TTY interrupts now...
.suset [.simsk2,,[1_ttyi]]
hrrzi pi,%baty ;Simulate ATY interrupt first thing.
wait: jffo pi,wait2
wait1: skipn com"uhang(u)
.hang
exch pi,com"uhang(u) ;PI must contain 0 here.
jffo pi,wait2
.lose
wait2: andcm pi,unjffo(i)
jrst @proc(i)
.vector proc(36.)
unjffo: repeat 36., 1_<35.-.rpcnt>
p.err: princ "AError: Bad process bit set."
lose 0,wait
p.rip: princ "AError: Demon went away."
lose 0,wait
p.cmd: movei x,cmdbuf
tyo ["_]
jrst wait
p.aty: tyo [^P]
tyo ["C]
move a,aline
patylp: move tt,width
sub tt,l.room(a)
jumpe tt,patynx
tyo [^P]
tyo ["V]
tyo l.vpos(a)
move t,l.bp.a(a)
.call sout
.lose %lssys
tyo [^P]
tyo ["H]
tyo [10]
patynx: move a,l.down(a)
jumpn a,patylp
move a,ptline
tyo [^P]
tyo ["V]
tyo l.vpos(a)
tyo [^P]
tyo ["H]
move tt,width
sub tt,l.room(a)
addi tt,8
tyo tt
jrst wait
duname: sixbit /.chat./
djname: sixbit /demon/
ddir: sixbit /bawden/
dfn1: sixbit /chat/
dfn2: sixbit /demon/
launch: .gensym a,
syscall open,[moves e ? [.uio,,usr]
[sixbit /usr/]
movei 0
move a]
jrst [ cain e,%ensmd
jrst launch
lose %lssys(e),.-1
]
syscall open,[[.uii,,dsk]
[sixbit /dsk/]
move dfn1
move dfn2
move ddir]
.lose %lsfil
syscall load,[movei usr ? movei dsk]
.lose %lssys
.iot dsk,a
.close dsk,
hrrz a,a
move tt,[-5,,[ .supc,,a
.sxuname,,duname ;XUNAME & XJNAME tell demon
.sxjname,,djname ; what it should call itself.
.shsname,,ddir ;HSNAME is where demon was
; loaded from.
.ssname,,uname ;SNAME is name of launcher.
]]
.uset usr,tt
syscall disown,[movsi 5 ? movei usr]
.lose %lssys
movei a,30. ;Wait one second...
.sleep a,
jrst contac
;;;JSP T,GETMSG to lock a msg bit. Skips if it gets one. Msg bit number
;;;returned in A.
getmsg: movei a,com"lock
movei tt,bitswt
pioff
aose (a)
aoja a,[
caige a,com"lock+com"nmsgs
jrst .-1
pion
jrst (t)]
bitsw1: movem a,bitswt
movem tt,forty+3
bitsw2: pion
subi a,com"lock
movem u,com"user(a)
jrst 1(t)
;;;JSP T,RELMSG to unlock a msg bit.
relmsg: movei tt,bitswx
pioff
movem tt,forty+3
bitsw3: setom @bitswt
bitsw4: pion
jrst (t)
;;;JSP T,SNDMSG to send off a message to the demon.
sndmsg: movei tt,bitswx
pioff
movem tt,forty+3
bitsw5: move tt,bitswt
subi tt,com"lock
move tt,unjffo(tt)
iorm tt,com"dhang
bitsw6: pion
jrst (t)
.scalar free ;Number of first free page in memory.
;;;JSP T,ALLOC to allocate pages.
;;;A: (arg) number of pages desired.
;;;A: (val) address of first allocated word.
;;;TT: (val) -<number allocated>,,<first page allocated>
;;; (Suitable for CORBLK)
alloc: hrr tt,a
hrl tt,a
addb a,free
caile a,400
.lose
subb a,tt
hrrz a,a
lsh a,12
jrst (t)
;;;JSP T,PRINZ to print an ASCIZ string in TT into the line in A.
;;;A kludge for the moment.
prinz: hrli tt,440700
ildb x,tt
jumpe x,(t)
prinzl: idpb x,l.bp.z(a)
sosge l.room(a)
lose 0,.
ildb x,tt
jumpn x,prinzl
jrst (t)
kill=:jrst .
$kill: pioff
movei tt,com"%kdie
movem tt,com"dhang
.logout 1,
tsint: intacs,,intsp
%piaty ? 0 ? %piaty ? 0 ? atyint
0 ? 1_usr ? 0 ? 1_usr ? usrint
0 ? 1_ttyi ? 0 ? 1_ttyi ? ttyint
ltsint==:.-tsint
lintpdl==:50. ;Maximum depth: 3 interrupts.
.vector intpdl(lintpdl)
.scalar intsp
pion=:.suset .
$pion: .spiclr,,[-1]
pioff=:.suset .
$pioff: .spiclr,,[0]
dismis: setz
sixbit /dismis/
movsi intacs
setz intsp
atyint: tro %faty
disint: .call dismis
.lose %lssys
usrint: movei tt,%brip
iorm tt,com"uhang(u)
.call dismis
.lose %lssys
.scalar input
ttyint: tyi t
jumpl t,disint
trze %faty
jrst [ movei tt,%baty
iorm tt,com"uhang(u)
jrst .+1]
cail t,40 ;Ordinary printing characters are the most
cail t,177 ; common case.
jrst ttycvt
ttyin: skipn x,input
.lose ;Our input is being thrown away!
ttyilp: idpb t,com"iptr(x)
sosge com"iwrap(x)
jrst [ movei tt,com"buffer(x)
hrli tt,440700
movem tt,com"iptr(x)
move tt,com"bsize(x)
movem tt,com"iwrap(x)
jrst .+1]
sosge com"icount(x)
jrst broken
aos com"ocount(x)
move tt,com"wkmask(x)
iorm tt,@com"wkaddr(x)
skipe x,com"inext(x)
jrst ttyilp
jrst ttyint
;;;Clip a broken buffer out of our input queue:
broken: movei tt,input ;TT: location of previous pointer.
brokn1: camn x,(tt) ;Is this where it came from?
jrst brokn2 ; Yes.
skipn tt,(tt) ;No. Get next.
lose 0,broken ;Oops! Didn't find it!
movei tt,com"inext(tt) ;Location of its INEXT cell.
jrst brokn1
brokn2: move x,com"inext(x) ;Next buffer in queue after broken one.
movem x,(tt) ;Store it in previous buffer.
jumpe x,ttyint
jrst ttyilp
%TXSUP==:%TXSFT
;;;Odd characters of potential interest:
;;;Top-1 Square
;;;Top-2 Circle
;;;Top-3 Triangle
;;;Top-B Break/Suspend
;;;Top-H Help
;;;Control- End
ttycvt: trne t,%txtop ;Top?
jrst ttytop
ldb tt,[.bp %txasc,t]
cain tt,177
jrst cvtrub
cain tt,33
jrst ttytop
caile tt,40
tro %txctl+100
ttytop: andi t,%txsup+%txmta+%txctl+%txasc
jrst ttyin
critic: cntsw1,,cntsw2
sos com"count
bitsw1,,bitsw2
setom @a
bitsw3,,bitsw4
setom @bitswt
bitsw5,,bitsw6
setom @bitswt
lcritic==:.-critic
cntswt: com"count
sos @0 ;Always last.
sout: setz
sixbit /siot/
movei ttyo
move t
setz tt
cnstnts:
constants
variables
twenty: block 20
forty: 0
0
-ltsint,,tsint
0
-lcritic,,critic
pat: block 100.
patch==:pat
bitswx==:cntswt ;Always 2nd to last.
bitswt: 0
setom @bitswx
com"page==:<.+1777>_-12 ;Communications area.
end go


1
src/alan/chat.format Symbolic link
View File

@@ -0,0 +1 @@
alan/chatfm.>

150
src/alan/chatdm.34 Normal file
View File

@@ -0,0 +1,150 @@
;;;-*-Midas-*-
title Chat -- Demon.
.insrt chat format
com"page==:com"dpage
a=:1
b=:2
c=:3
d=:4
e=:5
t=:6
tt=:7 ? intacs==:t_6+2 ;T & TT saved by interrupts.
pi=:15 ;PI=I-1 So JFFO will load I
i=:16 ;Bit numbers kept here.
u=:17 ;UINDs kept here.
dsk==:1
usr==:2
define syscall name,args
.call [setz ? sixbit /name/ ? args(400000)]
termin
define lose code,pc
jrst [ syscall lose,[movei code ? movei pc]
.lose %lssys]
termin
.scalar duname
.scalar djname
.scalar ddir
go: move tt,[-lintpdl,,intpdl-1]
movem tt,intsp
.suset [.roption,,a]
tlo a,%opint+%opopc
move tt,[-6,,[ .soption,,a
.s40addr,,[twenty,,forty]
.smask,,[%pirlt+%pipdl]
.smsk2,,[0]
.rxuname,,duname
.rxjname,,djname
.rhsname,,ddir
]]
.suset tt
;;Create area:
move tt,[-com"npages,,com"page]
syscall corblk,[movei %cbndr+%cbndw+%cbpub
movei %jself ? move tt
movei %jsnew]
.lose %lssys
;;Initialize area:
setzm com"count
setzm com"tick
setzm com"dhang
setom com"lock
move tt,[com"lock,,com"lock+1]
blt tt,com"lock+com"nmsgs-1
;;Install ourselves:
move tt,[-4,,[ sixbit /uname/ ? move duname
sixbit /jname/ ? move djname
]]
syscall usrvar,[moves e ? movei %jself ? tt]
jrst [ cain e,%etop ;Allow debugging.
jrst .+1
cain e,%eexfl ;Someone else is it.
.logout 1,
lose %lssys(e),.-1
]
;;Wake up every minute:
move tt,[%rlset,,[60.*60. ? 0 ? 0 ? 0]]
.realt tt,
;;Initialize process table:
movei tt,p.msg
movem tt,proc
move tt,[proc,,proc+1]
blt tt,proc+com"nmsgs-1
movei tt,p.die
movem tt,proc+.lz com"%kdie
movei tt,p.rlt
movem tt,proc+.lz com"%krlt
setzi pi,
jrst wait1
wait: jffo pi,wait2
wait1: skipn com"dhang
.hang
exch pi,com"dhang ;PI must contain 0 here.
jffo pi,wait2
.lose
wait2: andcm pi,unjffo(i)
jrst @proc(i)
.vector proc(36.)
unjffo: repeat 36., 1_<35.-.rpcnt>
p.msg: move tt,com"msg(i)
movem tt,lstmsg'
move tt,com"user(i)
movem tt,lstuser'
setom com"lock(i)
jrst wait
p.die: .logout 1,
p.rlt: aos com"tick
jrst wait
tsint: intacs,,intsp
%pirlt ? 0 ? %pirlt ? 0 ? rltint
ltsint==:.-tsint
lintpdl==:50. ;Maximum depth: one interrupt.
.vector intpdl(lintpdl)
.scalar intsp
dismis: setz
sixbit /dismis/
movsi intacs
setz intsp
rltint: movei tt,com"%krlt
iorm tt,com"dhang
.call dismis
.lose %lssys
cnstnts:
constants
variables
twenty: block 20
forty: 0
0
-ltsint,,tsint
pat: block 100.
patch==:pat
ifg .-<com"page_12>, .err DPAGE too low.
end go


71
src/alan/chatfm.12 Normal file
View File

@@ -0,0 +1,71 @@
;;;-*-Midas-*-
;;; Chat communications area format.
.begin com
define defloc name,size=1
name=:.loc.
.loc.==.loc.+<size>
termin
define def name,size=1
name==:.val.
.val.==.val.+<size>
termin
dpage==:10 ;Starting on page 10 in the demon.
maxj==:150. ;MC currently has 120. jobs.
;;;Pre-allocated bits in DHANG
%k==:525252,,525252
%krlt==:1_0 ;Realtime interrupt.
%kdie==:1_1 ;Request to terminate.
nmsgs==:34. ;The rest are msg bits.
;;;Buffer format. All sizes are in bytes. Entries marked with a star are
;;;initialized by the demon from information supplied in the initial messages.
.val.==0
def iuser ;* UIND of input side.
def ouser ;* UIND of output side.
def bsize ;* Total space in buffer.
def icount ;* Count of free space minus one. If the input side
;deposits a byte and decrements this count to be -1, then
;it must consider the connection to be broken. If the
;output side increments this count and it becomes 0, then
;it knows that the connection has been broken.
def ocount ;* Count of occupied space. Incremented by the output side
;AFTER depositing a byte but BEFORE delivering the wakeup.
;If the input side decrements this to 0, then it knows it
;will recieve a wakeup when the next byte in input.
def wkmask ;* A mask of bits to use to wake up the output side.
def wkaddr ;A pointer to the output side's UHANG word. For use by the
;input side.
def inext ;The input side uses this to build a linked list of
;buffers.
def iwrap ;Count of empty space before wraparound for input side.
def owrap ;Count of empty space before wraparound for output side.
def iptr ;Byte pointer for input side.
def optr ;Byte pointer for output side.
def buffer ;First location of buffer.
ifdef page,[
.loc.==page_12
defloc count ;Count of jobs using the area.
defloc tick ;Demon increments this every minute.
defloc uhang,maxj ;Users hang on bits in these words.
dhang==:uhang+0 ;Demon hangs on bits in this word.
; (SYS job can't be a user!)
defloc lock,nmsgs ;Locks for msg bits in DHANG.
defloc user,nmsgs ;UIND of owners of locks.
defloc msg,nmsgs ;Messages.
npages==:<<.loc.+1777>_-12>-page
] ;end ifndef page,
.end com