;! FILE 'DVDUP'
;.TIME40
;**************************************
;*         DVDUP                      *
;*  INTERFACE BETWEEN HARDWARE AND IMP*
;*  DATE:  27.MAR.81                  *
;**************************************
 
PS=177776; PROCESSOR STATUS WORD
 
IDLEST=-1; SUPERVISOR IDLE FLAG
 
INTVAL=40; DEDICATED LOCATION FOR INTERRUPT NUMBER
ALARMF=44; DITTO - FOR CLOCK
PSECT=46; DITTO - CURRENT PSECT
LASTPS = 54
INTINF=56
 
UPAR=177640
UPDR=177600
 
UPAR0=40; INDEC INTO PSECT
UPDR0=UPAR0+2; DITTO
UR0=14
UR4=UR0+10; ALL DITTO
UPC=UR0+14
UPS=UR0+16
USP=UR0+20
UTRP=UR0+22
 
 
.=0
0,0
ADDERR, 340
ADDERR,340; ILLEGAL INSTRUCTION TRAP TO SAME PLACE FOR NOW
BPTINT,340
.+2,0; 20,22
.+2,0; 24,26; POWER
SVC,340; EMT HANDLER
.+2,0
.+2,0
.+2,0
.+2,0; 50,52
.+2,0; 54,56
 
.=40
INT6BA; FOR USE IN SBLD ONLY

.=60
KBINT,340,TTINT,340
.=70; PR AND PP INT
PRINT,340
LPINT,340

.=100
TIMINT,340
TIMINT,340; ALLOW FOR BOTH CLOCKS
 

.=120;   GRAPH PLOTTER INT
GPINT, 340

;   .=140;  DUMP ADDRESS
;   JMP DUMP

.=160; RL01 INTERRUPT
DKINT, 340; SAME AS RK05

.=200; LP (REAL) INT
LPINT,340

.=220; DISC INT
DKINT, 340

.=224; TU16 INT
TU16IT,340
.=230; CR INT
CRINT,340

.=250; SEGMENTATION TRAP
SEGTRP, 340

.=264; FLOPPY INT  (RX02)
DKINT, 340

.=270; BIG DISC INT
RP4INT, 340

.=300; PL11 #1 (TELETYPE), VEC=175610
KB2INT,340
TT2INT,340
UBRIS, 340; DUP11 ON 11/34 DEV MACHINE
UBTIS, 340

;  NB:  THIS IS PART OF THE DUP CODE ***************
.=360
UBRIS, 340
UBTIS, 340
; ********* END

.=60100;    CODE TO TRAP TOP OF REAL STORE
CLR @#60110
RTI
;
.PAGE
.=1300; LEAVING ROOM FOR SUP STACK
RUN:
MOV PSECT, R3;  GET CURRENT PSECT
BEQ IDLE;   GO INTO IDLE LOOP
MOV R3, R0; PSECT POINTER TO R0
ADD #USP, R0; POINT R0 AT USER SP
CMP LASTPS,R3; SAME AS LAST TIME?
BEQ NOSER; YES, SO DONT RESTORE SEG REGS
MOV R3,LASTPS; MAKE IT TRUE NOW
MOV #UPAR,R1; POINT R1 AT USER SEG REGISTER PAR 0
MOV #UPDR,R2; R2 AT PDR 0
MOV #8.,R5; 8 REGISTERS
ADD #UPAR0,R3; POINT R3 AT REGS IN PSECT
LOOP: MOV (R3)+,(R1)+; SHIFT PAR(N)
MOV (R3),(R2)+; PDR(N)
ADD #10-2,R3; POINT AT NEXT BLOCK
077505;   SOB R5,LOOP; BRACH BACK TILL FINISHED
 
 MOV #030340,PS; SET PREVIOUS MODE=USER
MOV (R0),-(SP); PLANT ON STACK
.WORD 6606;  MTPI R6 - SET R16
NOSER: MOV -(R0), -(SP); PLANT PS ON STACK
MOV -(R0), -(SP); AND PC
MOV -(R0), R5
MOV -(R0),R4
MOV -(R0),R3
MOV -(R0), R2
MOV -(R0), R1
MOV -(R0),R0; RESTORE ALL HIS REGISTERS
.WORD  6;  RTT; AND EXIT TO HIM

IDLE:; IDLE LOOP
   CLR PS
WAIT
BR IDLE

 
DPTAB: DPR1TB;  NORMAL BRUN = 0
SAVER4: 0
SAVER5: 0;      MAIN SUPERVISOR PLANTS VALUES HERE

SVC:
JSR R5,SAVE; SAVE THE REGS
MOV UPC-UTRP(R4), R4; PUT HIS PC ON THE STACK
.WORD 6544; MFPI -(R4); GET THE WORD BEFORE THE PC (EMT CODE)
MOVB (SP)+,R1; GET THE CODE (BYTE) INTO R1
EXIT: MOV SAVER4, R4
MOV SAVER5, R5; AND RESTORE R5
EXIT2: RTS PC
 
SAVE:
MOV R4,-(SP)
MOV LASTPS,R4; PSECT ADDR
ADD #UR0,R4; POINT AT USER REGS
MOV R0,(R4)+
MOV R1,(R4)+
MOV R2,(R4)+
MOV R3,(R4)+
MOV (SP)+,(R4)+; R4
MOV (SP)+,(R4)+; R5
MOV (SP)+,(R4)+; PC
MOV (SP)+,(R4)+; PS
.WORD 6506; MFPI R6 - GET USER R6
MOV (SP)+,(R4)+; AND SAVE
MOV R5,PC; AND RETURN
 
INT:  TST PSECT;   IS THERE AN ACTIVE TASK?
     BNE NORMAL; YES, SO SAVE ITS REGISTERS
ADD #4, SP; DUMP PC&PS
MOV #-1,R1; SET INT CODE=-1
BR EXIT2; AND EXIT
 
NORMAL: JSR R5,SAVE; SAVE THE CONTEXT
MOV #-1,R1; SET SERVICE=INTERRUPT
BR EXIT; AND RETURN
 
; *********************************************************
; DEVICE INTERRUPTS
 
KBINT: MOV #-2,INTVAL
BR INT
 
TTINT: MOV #-1,INTVAL
BR INT
 
TIMINT:
CLR INTVAL; INT VALUE=0
BR INT
 
DKINT: MOV #-3, INTVAL
BR INT

SEGTRP: MOV #1, @#52
ERR2: BIT #030000,PS;  PREVIOUS = USER?
BNE ERR3; YES, SO LET THE ERROR THROUGH
HALT; NO, SO WERE IN SUPER STATE (KERNEL HAD IT)
ERR3: MOV #-4,INTVAL
BR INT

ADDERR: MOV #2, @#52
BR ERR2
TU16IT: MOV #-5, INTVAL
BR INT

INT2: BR INT;  IN CASE ITS NEEDED LATER
INT6BA:
; NB: ALL INTS BENEATH MAY BE OVERWRITTEN BY SBLD *************

TXINT: MOV #-6, INTVAL
BR INT

RXINT: MOV #-7, INTVAL
BR INT

RP4INT: MOV #-10, INTVAL
BR INT

LPINT: MOV #-11, INTVAL
BR INT
 
BPTINT: MOV #-12,INTVAL
MOV @SP, INTINF; PASS PC THROUGH
BR INT
KB2INT: MOV #-13,INTVAL
BR INT

TT2INT: MOV #-14, INTVAL
BR INT

KB3INT: MOV #-15, INTVAL
BR INT

TT3INT: MOV #-16, INTVAL
BR INT
MOV #-17, INTVAL
BR INT
CRINT: MOV #-20,INTVAL
BR INT
PRINT: MOV #-21,INTVAL
BR INT
GPINT:   MOV   #-22, INTVAL;      GRAPH PLOTTER
        BR   INT

DTINT:   MOV   #-23, INTVAL
        BR INT
X1INT:   MOV   #-24, INTVAL
        BR INT

X2INT:   MOV   #-25, INTVAL
        BR INT
MOV #-26,INTVAL
BR INT
MOV #-27,INTVAL
BR INT
MOV #-30,INTVAL
BR INT
MOV #-31,INTVAL
BR INT2
MOV #-32,INTVAL
BR INT2
MOV #-33,INTVAL
BR INT2
MOV #-34,INTVAL
BR INT2
MOV #-35,INTVAL
BR INT2
MOV #-36,INTVAL
INTX:BR INT2
JMP UBRIS;  -31  - SPECIALLY LINKED TO DUP HANDLER
.WORD 0, 0
JMP UBTIS;  -32   DITTO
.WORD 0, 0
JMP UBR2IS; -33 - DUP #2 INPUT HANDLER
.WORD 0,0
JMP UBT2IS; -34 -        OUTPUT
.WORD 0,0
JMP UBR3IS; -35. - DUP #3 INPUT HANDLER
.WORD 0,0
JMP UBT3IS; -36. -        OUTPUT
.WORD 0,0
MOV #-45,INTVAL
BR INTX
MOV #-46,INTVAL
BR INTX
MOV #-47,INTVAL
BR INTX
MOV #-50,INTVAL
BR INTX
MOV #-51,INTVAL
BR INTX

;  DUMP: MOV #177412, R1;  DUMPER FOR AN RK05
;  MOV #14124, (R1); DISC ADDRESS
;  CLR -(R1); CORE ADDRESS=0
;  MOV #1000002, -(R1); WC = MAX
;  MOV #3, -(R1); WRITE+GO
;  DLOOP: TSTB (R1)
;  BPL DLOOP
;  MOV #3,(R1); WRITE+GO AGAIN
;  DLOOP2: TSTB (R1)
;  BPL DLOOP2
;  BIT #20000,@#777402
;  BNE DUMP; NO, SO GO AGAIN
;  MOV #7, @#777566; BELL ON TT
;  HALT
;  
.PAGE
;
; BLOCK SPEC
        ;  PT = 0
        STATE =2
        S1 = 3
        MAXLN = 4
        P1 = 6
        MODE = 10
        SEG = 12
        COU= 14
        VEC  =  16
      INTNO = 20

; USEFUL ADDRESSES
        INTENB = 100
        KPAR6 = 772354
        KPDR6 = 772314

;****************** DUP 11 HANDLER *********************
;  ELEMENT DVRUP IN NSILIB (WAS DUP113)
;
; THIS VERSION PUTS THE FIRST 2 BYTES OF THE FRAME IN THE BUFFER'S
;PARAMETER BLOCK.  THESE ARE NOT INCLUDED IN THE MESSAGE LENGTH.
;THE LENGTH COUNT MAY BE ZERO IF EITHER THE LENGTH REALY IS ZERO OR
;IF IT IS 256 BYTES.  IN THE LATTER CASE THE POINTERS WILL BE NON-ZERO.
;
;** REGISTER DEFINITIONS **
      DUPRCS=0
      DUPRDB=2
      DUPPSR=2
      DUPTCS=4
      DUPTDB=6
;** BIT DEFINITIONS **
         TSOM=400
         TEOM=1000
         RSOM=400
         REOM=1000
         TXDONE=200
         RXDONE=200
         DUPSND=20
         RCVEN=20
         DUPDSR=1000
         DUPDTR=2
         DUPDRS=400
         DUPRTS=4
         DUPCTS=20000
         DUPDCD=10000
         COUNT=5000
;
;** INTERFRAME FLAG COUNT **
      IFLAGS=0                          ;OK WITH DQS11E'S SILO
;

; TABLES
DPR1TB: 0,0,0,0,0,0,0, 0,-31.
DPT1TB: 0,0,0,0,0,0,0, 0,-32.
DPR2TB: 0, 0, 0, 0, 0, 0, 0, 0, -33.
DPT2TB: 0, 0, 0, 0, 0, 0, 0, 0, -34.
DPR3TB: 0,0,0,0,0,0,0,0, -35.
DPT3TB: 0,0,0,0,0,0,0,0, -36.
OVERRUN: 0;       OVERRUN FLAG (ALL LINES)
;
;** TX MECHANISM **
;AT INITIALISATION SEND AND TSOM ARE SET.  SO LONG AS DATA IS NOT
;LOADED INTO THE TX BUFFER THE I/F WILL TRANSMIT IDLE FLAGS.
;INTERRUPTS ARE DISABLED TO REDUCE PROCESSOR LOAD.  TO TRANSMIT
;DATA, TSOM IS CLEARED AND INTERRUPTS ENABLED.  AN INTERRUPT WILL
;OCCUR WHEN TRANSMISSION OF THE CURRENT FLAG HAS BEEN COMPLETED.
;THE FIRST DATA BYTE IS LOADED, INTERRUPTS REMAIN ENABLED AND
;THE REST OF THE MESSAGE IS SENT.  ON INTERRUPT AFTER
;THE LAST CHAR THE TEOM BIT IS SET TO TRANSMIT THE CRC.  ON INT
;AFTER TEOM, TEOM IS CLEARED AND TSOM SET.  FLAGS WIIL THEN BE IDLED
;WITH INTERRUPTS UNTIL THE INTER-FRAME REQUIREMENT IS
;SATISFIED WHEN INTERRUPTS ARE DISABLED LEAVING THE UNIT
;IDLING FLAGS.
;
;  TX STATES
;     0 = INTER FRAME IDLE,INTS DISABLED, TSOM SET
;     1 = AWAITING COMPLETION OF CURRENT FLAG,TEOM CLEAR
;     2 = SECOND CHARACTER TRANSMISSION
;     3 = MESSAGE TRANSMISSION, NOT LAST BYTE, TEOM CLEAR
;     4 = CRC BEING TRANSMITTED, TEOM SET
;     5 = INTERFRAME FLAGS, TEOM SET
;     6 = CLEARING AFTER DATA LATE ERROR
;     7 = CLEARING (2)
;
;** TX INTERRUPT SEQUENCE **
;
UBTIS: MOV R0, -(SP)
 MOV #DPT1TB, R0
 BR DUPTIS

UBT2IS: MOV R0, -(SP)
 MOV #DPT2TB, R0
 BR DUPTIS
UBT3IS: MOV R0, -(SP)
 MOV #DPT3TB, R0

DUPTIS:
 MOV R1, -(SP)
 MOV R2, -(SP)
 MOV VEC(R0), R1;  PICK UP VECTOR ADDRESS
         MOVB  STATE(R0),R2             ;GET STATE
         ASL   R2                       ;SWITCH ON IT
         JMP   @DUPTSW(R2)
DUPTSW:  .WORD DUPT00                   ;UNWANTED INT
         .WORD DUPT10                   ;1ST AND 2ND CHARS
         .WORD DUPT10                   ;    -DITTO-
         .WORD DUPT20                   ;SUBS. CHARS
         .WORD DUPT30                   ;CRC DONE
         .WORD DUPT40                   ;INTER-FRAME FLAGS
         .WORD DUPT50                   ;CLEARING
         .WORD DUPT60                   ;CLEARING (2)
;
; IRRELEVANT INTERRUPT,  SET TEOM AGAIN TO GET ANOTHER.
DUPT00:  MOV   #TEOM,DUPTDB(R1)         ;CLEAR TSOM AND SET TEOM
         BR    DUPTEX
;
;1ST AND 2ND CHARS, BOTH MUST BE PRESENT.
DUPT10:  JSR   PC,LDC                   ;GET CHAR
         BLT   DUPT21                   ;** SHOULD BE ERROR **!!
         MOV   R2,DUPTDB(R1)            ;OUTPUT CHAR
         INCB  STATE(R0)                ;NEXT STATE
         BR    DUPTX1
;
;SUBSEQUENT CHARS
DUPT20:  JSR   PC,LDC                   ;GET CHAR
         BLT   DUPT21                   ;NO MORE (TCP, BEQ IS NO MORE)
         MOVB  R2,DUPTDB(R1)            ;SEND CHAR
         BR    DUPTX1
DUPT21:  BIS   #TEOM,DUPTDB(R1)         ;SET TEOM TO TRANSMIT CRC
         INCB  STATE(R0)                ;NEXT STATE
         MOVB  #IFLAGS,P1(R0)           ;SET INTER-FRAME FLAG COUNT
         BR    DUPTX2
;
;CRC DONE
DUPT30:  BIS   #TEOM,DUPTDB(R1)         ;SET TEOM TO GET NEXT INT.
         INCB  STATE(R0)                ;NEXT STATE
         BR    DUPTEX
;
;FIRST FLAG SENT WITH CRC.  IDLE FLAGS WITH TEOM.
DUPT40:  BIS   #TEOM,DUPTDB(R1)         ;TO GET INT.
         DECB  P1(R0)                   ;COUNT FLAG
         BLT   DUPT41                   ;LAST ONE
         BR    DUPTEX
DUPT41:  CLRB  STATE(R0)                ;RESET STATE
         MOV   (R1),P1(R0)              ;SAVE STATUS
 CLR MODE(R0)
 MOV INTNO(R0), INTVAL
 JMP DOINT
;
; THIS CODE DEALS WITH HANDLING DATA LATE ERRORS
;
DUPER1:  .WORD 0                        ;COUNT OF DATA LATE FAULTS
DUPER2:  .WORD 0                        ;COUNT OF DATA LATE FAULTS AT EOM
;
DUPTX2:  TST   DUPTCS(R1)
         BPL   DUPTEX                   ;OK
         INC   DUPER2                   ;COUNT FAULTS
DUPTX4:                                 ;DATA LATE
         MOV   #0,DUPTDB(R1)            ;CLEAR DONE
         BIC   #DUPSND,DUPTCS(R1)       ;CLEAR SEND REQ.
         MOVB  #6,STATE(R0)             ;CLEARING FLAG
         BR    DUPTEX
;
DUPT50:
         BIS   #DUPSND,DUPTCS(R1)       ;ASSERT SEND
         MOV   #TSOM,DUPTDB(R1)         ;SET TSOM
         MOVB  #7,STATE(R0)             ;CLEARING 2
         BR    DUPTEX
;
DUPT60:
         MOV   #TEOM,DUPTDB(R1)         ;CLEAR TSOM, SET TEOM
         BR    DUPT41
;
DUPTX1:
         TST   DUPTCS(R1)
         BPL   DUPTEX                   ;OK
         INC   DUPER1                   ;COUNT FAULTS
         BR    DUPTX4                   ;DEAL WITH DATA LATE ERROR
;
;
;NORMAL EXIT
DUPTEX:  JMP   DSPNXT
;
;
;
;
;** RECEIVER INTERRUPT SEQUENCE **********************
;
UBRIS: MOV R0, -(SP)
 MOV #DPR1TB, R0
 BR DUPRIS

UBR2IS: MOV R0, -(SP)
 MOV #DPR2TB, R0
 BR DUPRIS
UBR3IS: MOV R0, -(SP)
 MOV #DPR3TB, R0

DUPRIS:
 MOV R1, -(SP)
 MOV R2, -(SP)
 MOV VEC(R0), R1;    PICKUP DEVICE ADDRESS
         MOV   DUPRDB(R1),-(SP)         ;SAVE THE CHAR
         MOVB  STATE(R0),R2             ;SWITCH ON STATE
         ASL   R2
         MOV   DUPRSW(R2),R2
         RTS   R2
DUPRSW:  .WORD DUPR10                   ;1ST CHAR
         .WORD DUPR20                   ;2ND CHAR
         .WORD DUPR30                   ;3RD CHAR
         .WORD DUPR40                   ;4TH CHAR
         .WORD DUPR50                   ;5TH AND SUBSEQUENT CHARS
;
;1ST CHAR
DUPR10:  TST SEG(R0);  BUFFER PRESENT?
         BNE   DUPR11                   ;GOT ONE
         INC OVERRUN;           FAULT COUNT
         BIC   #RCVEN,(R1)              ;RESET RECEIVER TO ABORT FRAME
         BIS   #RCVEN,(R1)
         JMP   DSPNXT
;
DUPR20:                                 ;2ND CHAR
DUPR11:  JSR   PC,DUPCHK                ;CHECK FOR EOM & ERROR (EXIT IF EITHER)
         JSR   PC,STC                ;SAVE GOOD CHAR IN PARAM BLOCK
         BR    DUPRXX                   ;TAKE NEW STATE AND EXIT
;
;3RD CHAR
DUPR30:  CLR   P1(R0)                   ;CLEAR 2-BYTE SHIFT REG
         JSR   PC,DUPCHK
         MOVB  R2,P1+1(R0)              ;SAVE CHAR
         BR    DUPRXX
;
;4TH CHAR
DUPR40:  JSR   PC,DUPCHK
         MOVB  R2,P1(R0)
;NEXT STATE EXIT
DUPRXX:  INCB  STATE(R0)                ;NEXT STATE
         JMP   DSPNXT
;
;5TH AND SUBSEQUENT CHARS
DUPR50:  MOV   R2,-(SP)                 ;SAVE THE CHAR
         BMI   DUPRER                   ;ERROR FLAG SET
         BIT   #REOM,R2                 ;EOM?
         BNE   DUPR51                   ;YES
         MOVB  P1+1(R0),R2              ;GET CHAR FROM SHIFT REG
         JSR   PC,STC                   ;SAVE IN NIBBLE BUFFER
         BLE DUPR54                     ;OVER MAX LENGTH OF BLOCK
         SWAB  P1(R0)                   ;SAVE THE LATEST CHAR
         MOVB  (SP)+,P1(R0)             
         JMP   DSPNXT
;
DUPR54:  ; EXCEEDED MAX LEN OF BLOCK, ERROR = -2
MOV #-2,(SP); CODE ABOVE HAS ITEM ON STACK, SO OVERWRITE
BR UBRW53; AND TAKE EXIT
;
;END OF MESSAGE
DUPR51:  CLR   (SP)                     ;FLAG NO ERROR
DUPR52:  MOV   (R1),P1(R0)              ;SAVE MODEM STATUS
 MOV (SP)+,MODE(R0);  SEND BACK FLAG
         CLRB  STATE(R0)                ;RESET STATE
   CLR  SEG(R0);       NO I/P BLOCK NOW
         MOV INTNO(R0), INTVAL
DOINT:MOV (SP)+,R2
 MOV (SP)+, R1
 MOV (SP)+, R0
 JMP INT
;
;ERROR HANDLER
DUPRER:  MOV   #-1,(SP)                  ;FLAG ERROR
UBRW53:         BIC   #INTENB+RCVEN,(R1)       ;DISABLE RX
         BR    DUPR52                   ;AND EXIT NORMALLY
;
;
;ROUTINE TO CHECK FOR ERROR OR SHORT FRAME. EXITS DIRECT TO ERROR
;SEQUENCE IF EITHER FOUND.
DUPCHK:  BIT   #100000+REOM,R2          ;ERROR OR EOM?
         BEQ   DUPCH1                   ;NO
         BR    DUPRER                   ;EXIT LEAVING WORD ON STACK
DUPCH1:  RTS   PC                       ;NO ERROR, EXIT NORMALLY
;
;
STC:   
         MOV SEG(R0), KPAR6;           SET UP KERNEL SEG 6
         MOV #77406, KPDR6;            ?????????????????????
         MOVB R2, @0(R0);               PLANT CHAR
         INC (R0);     BUMP POINTER
        DEC MAXLN(R0);   OVER LENGTH?
         RTS   PC; WITH MAXLN CONDITION CODE SET
;
;   LOAD CHAR ROUTINE
LDC:       MOV SEG(R0), KPAR6
           MOV #77406, KPDR6;           FULL SEG FOR NOW
           MOV (R0), R2;              GET CHAR AND BUMP POINTER
           MOVB (R2), R2
           BIC #177400, R2
           INC (R0); BUMP POINTERT
           DEC COU(R0);           SENDS '=' ON EXIT WHEN FINISHED
           RTS  PC;                   LAST CHAR??
;
; COMMON RETURN SEQUENCE  -  NO INTERRUPT NOTIFIED
DSPNXT: MOV (SP)+, R2
 MOV (SP)+, R1
 MOV (SP)+, R0
 .WORD 6 ; RTT - RETURN TO LAST ACTIVITY
;
;END OF DUP11 HANDLER
.END
         BNE   DUPR51                   ;YES
 MOV (SP)+, R0
