;-*-Midas-*- Title :ARGUS - The Dog (ticktick) of One Hundred Eyes ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; ;;; Format: ;;; ;;; :ARGUS ,, . . . , ;;; ;;; Output: ;;; ;;; [Here is FOOMAN] or, if two logins, ;;; [Here are FOO and AHEM] or, for polylogins, ;;; [Here are JOE, ED and LOUISE] ;;; ;;; For departures: Change "Here are/is" to "There go/goes" ;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; A=1 ;General porpoise B=2 C=3 D=4 T=5 ;Temp TT=6 T3=7 Q=10 ;Counter for various loops J=11 ;Pointer to JCL NA=12 U=13 ;Accumulated username in GetJCL BP=14 TL=15 P=17 ;Pointer to basic you-know-what PDL PDLen==20 ;Length of PDL MaxUsr==100. ;Max # users allowed to look for JCLen==/5+10 ;This had BETTER be enough. Right, Devon? TTYo==1 CLIo==2 ;CLI chnl to be used to send you messages USRi==3 ;For checking if an Argus job already exists CLAi==4 ;For receiving updates/hoodunnit list USRc==5 ;To tell when the creating diety goes away. DEFINE SYSCAL OP,ARGS .CALL [SETZ ? SIXBIT /OP/ ? ARGS ((SETZ))] TERMIN Define EVAL *string*,ac=0 Move A,[Squoze 0,string] .Eval A, .Lose %LsSys IFN ac, Add A,[(ac)] Movem A,string Termin DEFINE OUTCHR LOCS IRP FOO,,[LOCS] Movei T,FOO Idpb T,BP Addi TL,1 TERMIN TERMIN Define OUTSTR &string Move T,[440700,,[Asciz string]] Pushj P,SavStr Termin PDLIST: -PDLEN,,. ;The usual. Make room for PDL BLOCK PDLEN Tsint: Loc 42 -TsintL,,Tsint Loc Tsint P %PiCLI ? 0 ? %PiCLI ? 0 ? GotCLI 0 ? 1_USRc ? 0 ? 0 ? Die TsintL==.-Tsint JCLBUF: BLOCK JCLEN ;Again, the usual stuff. Room for JCL -1 UUNAME: 0 ;Your uname/jname will go here UJNAME: 0 YUNAME: 0 ;Who sent us an update request YJNAME: 0 HooTo: 0 FUNAME: 0 Argusp: 0 ;Are we the real & original Argus? nUsers: 0 ;Number of current users (last value of SUSRS) UAOBJN: 0 ;Static AOBJN-pointer to SEARCH list TAOBJN: 0 ;Likewise, but for TTYSTS table EOJCL: 0 ;Flag for while reading JCL. Found end? nMods: 0 ;Number of modifications specified in JCL line nTarge: 0 ;# of targets SEARCH: BLOCK MAXUSR ;List of unames supplied from JCL OSEEN: BLOCK MAXUSR ;Initially +/- flags for original unames NSEEN: Block MaxUsr LUBLK: 0 ;Values of monitor symbols. NCT: 0 TTYSTS: 0 MAXJ: 0 XUNAME: 0 JNAME: 0 SUSRS: 0 BEGIN: MOVE P,PDLIST .Suset [-5,,[.rUNAME,,UUNAME .rJNAME,,UJNAME .sOPTION,,[(OptInt)] ;New-style interrupts .sMASK,,[%PiCLI] ;Allow trapping of CLI interrupts .sMSK2,,[1_USRc]]] .BREAK 12,[..RJCL,,JCLBUF] ;Load JCL into JCLBUF Setzb Q,EOJCL Setzm nMods MOVE J,[440700,,JCLBUF] MAKEC: MOVE C,[440600,,U] ;Where username accumulates. SETZ U, GETJCL: ILDB A,J ;Get a char from JCL into A JUMPE A,EOL ;A null is final terminator CAIL A,"a ;Is this a lowercase character? Trz A,40 ; Yup, so make it caps CAIE A,^C ;This a ^C? CAIN A,^M ;What about ^M? Both are semi-final delimiters. JRST EOL ; Yup! Caie A,40 ;Space or CAIN A,", ; comma delimits JRST STORE ; a username. CAIGE A,40 ;Is this some other random control char? ADDI A,100 ; Sho nuf. Normalify it. Tlnn C,770000 ;Already written 6 characters for this one? Jrst GetJCL ; Yes, so don't store it. Jumpn U,6ate ;If not the first character of uname, just store it. Cain A,"+ ;1st character a + (add to list)? Jrst [Aos OSeen(Q) Aos nMods Jrst GetJCL] Cain A,"- ;Or a - (delete from list)? Jrst [Setom OSeen(Q) Aos nMods Jrst GetJCL] Cain A,"* Jrst [Setom HooTo Aos nMods Jrst GetJCL] 6ate: SUBI A,40 ;Yep. Change to 6bit, IDPB A,C ;poke it into the appropriate place in SEARCH, JRST GETJCL ;and keep reading chars EOL: Setom EOJCL STORE: JUMPE U,Nextp ;If no letters in uname, keep reading (,,) Skipe HooTo Jrst [Movem U,FUNAME Jrst Nextp] AOS Q ;Add 1 to # unames fully read CAIL Q,MAXUSR ;This less than the last allowed? .Value [Asciz ": Too many usernames! KILL "] Movem U,Search-1(Q) Nextp: Setzm HooTo Skipn EOJCL ;End of the line? JRST MAKEC ; Naw, so keep grinding away Movem Q,nTarget ;# of targets Movss Q ;#users,,0 Movnm Q,UAOBJN ;Static AOBJN pointer Change: Skipe FUNAME Jrst Chang0 Move T,UJNAME Camn T,[Sixbit "ARGUS"] Jrst Newp Setzm Argusp Move T,UUNAME Movem T,FUNAME Chang0: Syscal OPEN,[%Clbit,,.uii\10 %Climm,,USRi [Sixbit "USR"] FUNAME [Sixbit "ARGUS"]] .Value [Asciz ": Can't modify what don't exist - No Argus! KILL "] .Close USRi, ;Just wanted to make sure it was there. Syscal OPEN,[%Clbit,,.uio %Climm,,CLIo [Sixbit "CLI"] FUNAME [Sixbit "ARGUS"]] .Lose %LsFil Skipn T,UAOBJN Jrst Modif1 Modify: Skipn OSeen(T) ;Want to modify this one? Jrst Modif0 ; Naw, not specified with + or - .IOT CLIo,OSeen(T) ;Send type-of-modification flag word .IOT CLIo,Search(T) ;and then the username to be changed. Modif0: Aobjn T,Modify Modif1: .IOT CLIo,[Sixbit "*DONE*"] .Close CLIo, Movei T,30.*60. .Sleep T, .Value [Asciz ": No answer from Argus in one minute! KILL "] Jrst Die ;Just to be sure. Newp: Skipn UAOBJN .VALUE [ASCIZ /: Do :ARGUS ,,..., KILL /] Setom Argusp Eval "LUBLK" Eval "NCT" Eval "TTYSTS" Movs T,NCT Movns T Hrr T,TTYSTS Movem T,TAOBJN Eval "MAXJ" Eval "XUNAME",TT Eval "SUSRS" Hrrz T,XUNAME Lsh T,-10. ;Get starting system page# Move TT,MAXJ IMul TT,LUBLK Add TT,XUNAME Tlz TT,-1 ;Flush the ac field from XUNAME Lsh TT,-10. ;Ending page# Subi TT,-1(T) ;# pages in range Movss TT ;#pages,,0 Movns TT ;-#pages,,0 Hrr TT,T ;-#pages,,parallel page# Syscal CORBLK,[%Climm,,%CBNDR %Climm,,%JSELF %Clin,,TT %Climm,,400000] .Lose %LsSys Move T,SUSRS Lsh T,-10. Syscal CORBLK,[%Climm,,%CBNDR %Climm,,%JSELF %Clin,,T %Climm,,400000] .Lose %LsSys Move T,TTYSTS Lsh T,-10. Hrli T,-2 ;Get 2 pages in case table wraps. Move TT,T Syscal CORBLK,[%Climm,,%CBNDR %Climm,,%JSELF %Clin,,T %Climm,,400000] .Lose %LsSys Syscal OPEN,[%Clbit,,.uii %Climm,,USRc [Sixbit "USR"] UUNAME [Sixbit "HACTRN"]] .Lose %LsSys .VALUE [ASCIZ / :VKî/] ;:PROCEED - :DISOWN Setzm OSeen Move T,[OSeen,,OSeen+1] Move TT,nTarget BLT T,OSeen-1(TT) ;Make sure this is cleared to begin with Jrst Set Wait: Move T,nUsers ;Wait until the # of users changes Camn T,@SUSRS .HANG Set: Move T,@SUSRS Movem T,nUsers GETLST: Setzm NSeen Move T,[NSeen,,NSeen+1] Move TT,nTarget BLT T,NSeen-1(TT) Move T,TAOBJN GetL0: Hrre TT,(T) ;Get TTYSTS word Jumpl TT,GetL2 ;If <0, nothing on this TTY Move A,@XUNAME ;Indexed through TT Move B,UAOBJN GetL1: Camn A,Search(B) Aosa NSeen(B) ;Bump found-count Aobjn B,GetL1 GetL2: Aobjn T,GetL0 SENDP: Move BP,[440700,,Buffer] Setzb C,TL OUTCHR [177] Move T,UAOBJN Arrivp: Skipe TT,NSeen(T) ;Someone here now? Camg TT,OSeen(T) ; That wasn't here before? Jrst Arriv0 ; Whatever, ignore this one. Push P,T ;Save index Addi C,1 ;Bump arrival count Arriv0: Aobjn T,Arrivp ;Loop over all users. Jumpe C,Deparp ;No new arrivals. CAIG C,1 ;Only one arrival? JRST [OUTSTR "[Here is " ;Singular, Pop P,A ;then print one-&-only uname. PUSHJ P,6TYPEc JRST ENDLNA] ;Finally, do the close bracket. OUTSTR "[Here are " SAYIT: Pop P,A ;Pop the uname off and put index in ac A PUSHJ P,6TYPEc ;Print it. Soje C,EndLNA ;If no more, tie off line. CAIG C,1 ;If one more, JRST [OutStr " and " ; say "and", else Jrst Sayit] OUTSTR ", " ;say "," to separate unames. JRST SAYIT ENDLNA: OutStr "] " Deparp: Move T,UAOBJN Setz C, Depar0: Move TT,NSeen(T) Caml TT,OSeen(T) Jrst Depar1 Push P,T Addi C,1 Depar1: Aobjn T,Depar0 Jumpe C,Yawner CAIG C,1 JRST [OutStr "[There goes " Pop P,A Pushj P,6Typeg Jrst ENDLNB] OUTSTR "[There go " SENDIT: POP P,A ;Get a departure uname into ac A PUSHJ P,6TYPEg ;Print it, SOJE C,ENDLNB ;Number-left in C CAIG C,1 ;As before. Greater than 1, do "," JRST [OutStr " and " Jrst SendIt] OUTSTR ", " JRST SENDIT ENDLNB: OutStr "] " YAWNER: Caig TL,1 ;Any message accumulated? Jrst Wait ; Nah, so nothing happened. SYSCAL OPEN,[%CLBIT,,.UAO %CLIMM,,CLIo ;Open your CLI so we can report [SIXBIT /CLI/] ;what has heppened. UUNAME [SIXBIT /HACTRN/]] Jrst Wait Move A,[440700,,Buffer] Syscal SIOT,[%Climm,,CLIo %Clin,,A %Clin,,TL] Jfcl .CLOSE CLIo, ;Would be fatal to leave this open Move T,[NSeen,,OSeen] Move TT,nTarget BLT T,OSeen-1(TT) Jrst Wait GotCLI: Syscal OPEN,[%Clbit,,.uii ;Get our end of the pipe open. %Climm,,CLAi [Sixbit "CLA"]] .Lose %LsFil .Iot CLAi,YUNAME .Iot CLAi,YJNAME Skipe Argusp Jrst DoMods Syscal OPEN,[%Clbit,,.uao %Climm,,TTYo [Sixbit "TTY"]] .Lose %LsFil Setz A, ShoHoo: .IOT CLAi,T Camn T,[Sixbit "*DONE*"] Jrst Die Aos A ;This is the (A)th to go on this line. Caile A,8. Jrst [.Iot TTYo,[^M] Movei A,1 Jrst .+1] Pushj P,T6Type .Iot TTYo,[^I] Jrst ShoHoo DoMods: Hlre B,UAOBJN Movns B ;Current # targets. Move NA,UAOBJN DoMod0: .Iot CLAi,T ;Get flag word Camn T,[Sixbit "*DONE*"] Jrst Report ;No more reports, report our status. .IOT CLAi,TT ;Get uname. Move A,NA DoMod1: Camn TT,Search(A) Jrst Found Aobjn A,DoMod1 Jumpl T,DoMod0 ;Can't get rid of what ain't here. Cail B,MaxUsr ;Can handle another? Jrst DoMod0 ; Nope, ignore it. Movem TT,Search(B) ;Save the new uname. Setzm OSeen(B) ;Say we've never seen them. Sub NA,[1,,0] Soja B,DoMod1 ;and go for more. Found: Jumpg T,DoMod0 ;Adding someone who's already here? IRP table,,[Search,OSeen,NSeen] ;Nope, so remove them. Movsi C,table+1(A) ;Move down all the arrays. Hrri C,table(A) Movei D,table-1(B) BLT C,(D) Termin Add NA,[1,,0] Aoja B,DoMod0 ;and keep on truckin. Report: Movem NA,UAOBJN .Close CLAi, Syscal OPEN,[%Clbit,,.uio %Climm,,CLIo [Sixbit "CLI"] YUNAME YJNAME] Jrst Repor1 ;Oh well. Jumpe NA,[.Iot CLIo,[Sixbit "!! BYE"] .Iot CLIo,[Sixbit "NOW !!"] Jrst Repor0] Move B,UAOBJN .Iot CLIo,Search(B) Aobjn B,.-1 Repor0: .Iot CLIo,[Sixbit "*DONE*"] .Close CLIo, Jumpe NA,Die Repor1: Syscal DISMIS,[P ? %Climm,,GetLst] .Lose .Lose T6Type: Setz TT, Rotc T,6 Addi TT,40 .Iot TTYo,TT Jumpn T,T6Type Popj P, DIE: .LOGOUT 1, ;Suicide noisily SavStr: Ildb T3,T Jumpe T3,CPopj Idpb T3,BP Aoja TL,SavStr 6typeg: move b,oseen(a) sub b,nseen(a) caie b,1 jrst 6types move b,oseen(a) caig b,1 jrst 6tc0 ldb b,[360600,,search(a)] caie b,'a cain b,'e jrst 6tg0 caie b,'i cain b,'o jrst 6tg0 caie b,'u skipa t,[440700,,[asciz "a "]] 6tg0: move t,[440700,,[asciz "an "]] pushj p,savstr jrst 6tc0 6types: outstr "poly" jrst 6tc0 6typec: move b,nseen(a) sub b,oseen(a) caie b,1 jrst 6types move b,nseen(a) caile b,1 jrst [outstr "another " jrst .+1] 6tc0: move a,search(a) ;get the uname ;fall into 6TYPE: SETZ B, ;6TYPE contents of ac A. Zero B in preparation ROTC A,6 ;Rotate a char from A into B ADDI B,40 ;Make it full ASCII Idpb B,BP Addi TL,1 Jumpn A,6Type CPopj: POPJ P, ;Return Buffer: Block 2*MaxUsr END BEGIN