;***********************************
;
;   TALK - inter-job chat program
;
;***********************************
;2.0 10-Aug-84 DFP written by D. Pallmann.

       VMAJOR=2

       SEARCH  SYS
       SEARCH  SYSSYM
       SEARCH  TRM

       .OFINI
       .OFDEF  PREFIX,12.              ;prefix (job name + text)
       .OFDEF  MESSAG,512.             ;message to send
       .OFSIZ  MEMSIZ

DEFINE  DEPACK  ADDR
       SAVE    A1-A2
       IF      NB,ADDR,LEA A1,ADDR
       SUB     #4,SP
       MOV     SP,A2
       UNPACK
       CLRB    @A2
       TTYL    @SP
       ADD     #4,SP
       REST    A1-A2
       ENDM

START:  PHDR    -2,0,PH$REE!PH$REU      ;program header
       GETIMP  MEMSIZ,A5               ;allocate impure area
       TYPESP  TALK                    ;print program name
       VCVT    START+2,OT$TRM          ; and version
       CRLF                            ;newline

SETTRM: JOBIDX  A0                      ;A0 := JCB
       MOV     JOBTRM(A0),A1           ;A1 := TRMDEF
       ORW     #T$IMI!T$ECS,T.STS(A1)  ;image mode, no-echo

SETPFX: LEA     A2,PREFIX(A5)
       MOVB    #176,(A2)+              ;store message character
       LEA     A1,JOBNAM(A0)
       UNPACK
       UNPACK
10$:    CMMB    -(A2),#40
       BEQ     10$
       INC     A2
       MOVB    #':,(A2)+
       MOVB    #40,(A2)+
       CLRB    @A2

GETMSG: CRLF                            ;newline
       LEA     A2,MESSAG(A5)           ;A2 := message line index
       CLR     D2                      ;D0 := char count
       TYPE    :                       ;prompt for message

GETCHR: KBD     EXIT                    ;get char, abort on ^C
       AND     #177,D1                 ;mask to 7-bit ASCII
       CMPB    D1,#40                  ;control character?
       BLO     CTLCHR                  ; yes
       CMPB    D1,#'~                  ;control character?
       BHIS    CTLCHR                  ; yes

TXTCHR: TTY                             ;echo char
       MOVB    D1,(A2)+                ;store char
       INC     D2                      ;inc char count
       BR      GETCHR                  ;get next char

CTLCHR: LEA     A0,CHRTBL               ;A0 := ctl char table index
       MOV     #-2,D0                  ;D0 := jump index
10$:    TSTB    @A0                     ;end of table?
       BEQ     GETCHR                  ; yes - ignore char
       ADD     #2,D0                   ;update jump index
       CMPB    D1,(A0)+                ;char match?
       BNE     10$                     ; no

BRANCH: MOVW    JMPTBL[~D0],D0          ;calculate offset position
       JMP     JMPTBL[~D0]             ;jump to appropriate routine

CHRTBL: BYTE    'H-'@                   ;BS
       BYTE    'M-'@                   ;CR
       BYTE    '[-'@                   ;ESC
       BYTE    176                     ;<MESSAGE>
       BYTE    177                     ;DEL
       BYTE    0                       ;end of table
       EVEN

JMPTBL: WORD    DELCHR-JMPTBL           ;delete character
       WORD    SEND-JMPTBL             ;send message
       WORD    QUIT-JMPTBL             ;exit
       WORD    RECEIV-JMPTBL           ;receive message from another job
       WORD    DELCHR-JMPTBL           ;delete character

DELCHR: TSTW    D2                      ;anything in buffer to delete?
       JEQ     GETCHR                  ; no
       TTYI                            ;echo deletion:
       BYTE    10,40,10,0              ; BS-SPACE-BS
       DEC     A2                      ;correct buffer index
       DEC     D2                      ;correct char count
       JMP     GETCHR                  ;done

SEND:   CRLF                            ;echo CR
       TYPESP
       TYPESP
       CLRB    @A2                     ;terminate message
       MOV     JOBTBL,A0               ;A0 := current JCB addr
       JOBIDX  A2                      ;A2 := own JCB addr
10$:    MOV     (A0)+,D0                ;D0 := current JCB
       BEQ     10$                     ;ignore deallocated jobs
       JMI     GETMSG                  ;branch on end-of-table
       MOV     D0,A1                   ;A1 := current JCB
       CMM     JOBPRG(A1),#[TAL]_16.+[K  ];is job running TALK?
       BNE     10$                     ; no
       MOVW    JOBSTS(A1),D0           ;D0 := jobs status flags
       ANDW    #J.MON,D0               ;strip all bits but J.MON
       BNE     10$                     ;branch if at AMOS/L cmd level
       CMM     A1,A2                   ;own job?
       BEQ     10$                     ; yes - no need to send msg
       TYPE    ->                      ;text
       DEPACK  JOBNAM(A1)              ;print job
       DEPACK  JOBNAM+2(A1)            ; name
       TYPESP                          ;spacing
       TYPESP                          ; prettyprinting
       LEA     A4,PREFIX(A5)           ;send prefix char & job name
       CALL    XMIT                    ; to selected job
       LEA     A4,MESSAG(A5)           ;send message
       CALL    XMIT                    ; to selected job
       LEA     A4,SUFFIX               ;send suffix char
       CALL    XMIT                    ; to selected job
       BR      10$                     ;process next job

RECEIV: MOV     #15,D1                  ;D1 := <CR>
       TTY                             ;echo <CR>
       MOV     #177400+9.,D1           ;D1 := clear-to-end-of-line code
       TCRT                            ;clear to EOL
10$:    KBD     EXIT                    ;get char
       AND     #177,D1                 ;mask to 7-bit ASCII
       CMPB    D1,#176                 ;end of message?
       BEQ     RETYPE                  ; yes - branch
       TTY                             ; no - echo
       BR      10$                     ;go back for more

RETYPE: CRLF                            ;newline
       MOV     D2,D0                   ;D0 := msg buffer size
       JEQ     GETMSG                  ;branch on zero
       TYPE    :                       ;re-print prompt
       LEA     A2,MESSAG(A5)           ;A2 := message line index
10$:    MOVB    (A2)+,D1                ;D1 := char
       TTY                             ;echo char
       SOB     D0,10$                  ;loop till done
       JMP     GETCHR                  ;continue message entry

QUIT:   TYPECR  EXIT

EXIT:   CRLF
       EXIT

XMIT:   SAVE    A5
       MOV     JOBTRM(A1),A5
10$:    MOVB    (A4)+,D1
       BEQ     20$
       TRMICP
       BR      10$
20$:    REST    A5
       RTN

SUFFIX: BYTE    176
       BYTE    0
       EVEN

       END