.TITLE QNJB50 Datacommunication JOB for Qnector(DMA) hardware ; Multiprocessor V5 ;*********************************************************************** ; SYSTEM-JOB for communication with Datacomm. handler using modified RSP, ; ; Handler on OTHER side of line: QN50.MAC (Qnector DMA, Westvries Systems) ; Terminate job: 2 * ^C ; -------------- ; h.h. feb-85 ;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++; ; COPYRIGHT (c) 1985 by ; ; H.H. Klin. Neuro. AZG ; ; ; ; This software is furnished under a LICENSE and may be USED ONLY IN ; ; ACCORDANCE WITH THE TERMS OF SUCH LICENSE. This software or ; ; any other copies thereof may not be provided or otherwise made ; ; available to any other person. NO TITLE TO AND OWNERSHIP OF THE ; ; SOFTWARE IS HEREBY TRANSFERRED. ; ; ; ; The information in this software is subject to change without notice. ; ; ; ;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++; ;************************ User Edits this part **************************** SPF = 0 ;SPFUN/SPDIR support enabled for SPF=1 BSTRP = 1 ;1=generate code for simple(i.e. Toggle-in) boot. CKS = 1 ;0=minimal error checking, 1=enable checksum checking(safer!) TEST = 0 ;TEST conditional, 1=printout of packet markers JBNUM = 0 ;Number of this JOB. ; INITIAL READ/WRITE PROTECTION PATTERN(Example): ; !<------------READ------------->! PROTECTION ; !7 6 5 4 3 2 1 0!7 6 5 4 3 2 1 0! Dev. Unit nr. 0-17(15.) ; 1!1 1 1!0 1 1!1 1 1!1 1 1!1 1 1! prot. bits. ; 1! 7 ! 3 ! 7 ! 7 ! 7 ! ; !<------------WRITE------------>! PROTECTION ; !7 6 5 4 3 2 1 0!7 6 5 4 3 2 1 0! Dev. Unit nr. 0-17(15.) ; 0!1 1 0!1 0 0!0 1 0!0 0 0!0 0 1! prot. bits. ; 0! 6 ! 4 ! 2 ! 0 ! 1 ! ; INITIAL READ/WRITE PROTECTION PATTERN(Actual setting): ;------------------------------------------------------- READQN=175777 ;Read protection bits WRITQN=103541 ;Write protection bits ;Attn. 1=enable access, 0=no access ;*************************** End User Edit ******************************* ; CONTROLS: ; --------- ; FLAG: = 0 Listen ; = 1 receive DATA-packet, after recept of header must ; must be set to -1. ; = 2 receive packet checksum. ; =-1 " COMMAND-packet or DATA-packet when the ; header of the last one is received. ; ; IERR: = 0 No error ; = 1 packet send/received: INIT, give CONTINUE. ; = 2 command received, while processing a previous one. ; = 3 time-out error ; =-1 after receiving: CHECKSUM ERROR, send ENDPACKET. ; =-2 DATA-packet header error. ; =-3 Hard IO error ; ; WCNTX: = >0 nr. of words to be send ; = 0 return from send, goto listening ; = -1 send checksum ; = -2 checksum is send, resume main. ; MAILBOX: Operator message structure in file JBINFO.SYS: ; -------- ; ! Block 0 ! Block 1 ! Block 2 ! Block 3 ! Block 4 ! ; !-------------!------------!------------!-----------!------------!---- ; ! common info ! message TO ! mess. FROM ! mess. TO ! mess. FROM ! ; ! for ALL jobs! JOB 0 ! JOB 0 ! JOB 1 ! JOB 1 ! etc. ; Att. received message restricted to 480. bytes!! (16 words for SYS-info) ; *** Qnector interface defenitions *** BAR = 172410 ;QNECTOR SWITCH SETTING! QNVEC= 170 ;QNECTOR SWITCH SETTING! WCR = BAR+2 ;Word Count Register. CSR = BAR+4 ;Command and Status Register. PRIO = 7 ;Interr. priority COL=20000 ;Collision indicator bit STP= 400 ;Cancel IO bit IE = 100 ;Interrupt enable bit CE = 4 ;Enable collision interrupt SND= 2 ;Transmit data GO = 1 ;Start transfer XOFF = 23 ;19. RSP-serial INIT = 4 ;4. protocol CONTIN = 20 ;16. chars CNDATA = 40 ;32. =continue with data BOOT = 10 ;8. COMMND = 2402 ;2.=command flag, high byte: 5.=wordcount PKMSIZ = 5 ;Command packet word size PKDSIZ = 256. ;Data " " " PKASIZ = 2*PKDSIZ ;Data " corresp. adres offset. CHECK = 125252 ;Bit pattern send and checked when NO checksum FILDEV = 16. ;Total nr. of devices. .MCALL .SPND,.RSUM,.SYNCH,.EXIT,.PROTECT,.UNPROTECT .MCALL .INTEN,.PRINT,.GTJB,.DEVICE,.QSET,.SERR,.SPFUN .MCALL .MTPS,.ENTER,.LOOKUP,.READW,.WRITW,.CLOSE .MCALL .SETTOP,.GVAL,.SAVEST,.REOPEN,.DATE,.GTIM .ENABL LC .PSECT RUNJB START:: CALL BUFFER ;Execute initialisation code in BUFFER! AGAIN:: CALL ONEINP ;Interr. enabl., wait for input 1 word. LISTEN: MOV #1,SPCNT ;Reset suspension count. .SPND ;Wait for next command. ADD #1,IONRLO ;Count the IO's. ADC IONRHI MOVB #'C,COND .IIF NE,TEST .PRINT #COND ;***TEST*** ;-----------------------IO: command received----------------------------; NORMAL: .IF NE,BSTRP ; ; See if we have to BOOT ; CMP #BOOT,OPCODE BNE CMGO ;No boot. .SAVEST #AREA,#MESSAG,#CHINFO .REOPEN #AREA,#MESSAG,#CHBOOT BCS AGAIN MOV #256.,R4 ;1 Block = 512. BYTES! MOV #BUFFER,BUFDAT ;BUF-POINTER .READW #AREA,#MESSAG,#BUFFER,R4,#1 ;Block nr.= QNBOOT.SYS! BCS AGAIN CLR WCNTX ;Send buffer only CALL BUFOUT ;Short/Prom boot stores this in low mem. .SAVEST #AREA,#MESSAG,#CHBOOT .REOPEN #AREA,#MESSAG,#CHINFO MOVB #'B,COND ;Information .IIF NE,TEST .PRINT #COND ;***TEST*** BR LISTEN CHBOOT: .BLKW 5 ;Channel status boot file CHINFO: .BLKW 5 ;channel status info file CMGO: .ENDC ;BSTRP ; ; Command received: Analyse and setup IO ; CALL ERRTST CMPB #FILDEV,UNIT BHI GOON ;Permitt. Nr. 0 to FILDEV-1(norm. 15.) OPCERR: ;OPCODE ERROR UNIERR: JMP HRDERR ;UNIT ERROR GOON: MOV WRDCNT,R5 MOV R5,R1 CLRB R1 ;MULTIPLE OF 256. SUB R1,R5 ;WORD REST SWAB R1 ;NR. OF BLOCKS TST R5 ;REMAINING WORDS? BEQ NOWRDR ;NO INC R1 ;YES, 1 BLOCK MORE TO DO NOWRDR: MOV BLCKNR,R3 ;R3=Block start nr.! MOV #1,R0 ;Construct ASH UNIT,R0 ; prot. bit mask ; R1 => Nr. of IO blocks ; R3 => Block address ; R5 => Remaining words .IF NE,SPF CMPB #5,OPCODE ;SPF request with zero BNE 1$ ; wordcount? JMP SPFREQ .IFF TSTB SPFCOD ;SPFREQ? BNE OPCERR ;Reject SPF req., as SPF not selected. .ENDC 1$: CMPB #2,OPCODE ;Read ? BEQ READST CMPB #3,OPCODE ;Write? BNE OPCERR JMP WRITE ;Write to device. ;-----------------------IO: read from device---------------------------; READST: .IF NE,SPF TSTB SPFCOD ;If SPF with DATA READ, execute BEQ 1$ ; SPF first. Then branch to SEND JMP SPFREQ ; entry after setting up BUFDAT, 1$: ; R1,R4,R5. .ENDC BIT R0,RDSTAT ;Check read prot. BNE 2$ JMP PRTERR 2$: MOVB #'S,COND READ: MOV #BUFFER,BUFDAT MOV BUFBLK,R4 ;R4=Nr. blocks to read CMP R4,R1 ;All? BLOS 1$ MOV R1,R4 ;No, less. 1$: MOV R4,R2 SWAB R2 ;R2=Nr. words to read. .READW #AREA,UNIT,#BUFFER,R2,R3 BCC SEND JMP IOERR SEND: MOV #1,ONEWRD ;Set up header of datapacket, 1=data flag MOV #PKDSIZ,WCNTX ;Words/packet CMP #1,R1 ;Last block? BNE 1$ TST R5 ;Remaining words? BEQ 1$ MOV R5,WCNTX ;Remaining words! MOVB R5,ONEWRD+1 ;Init upper byte checksum. 1$: .IF NE,CKS MOV ONEWRD,CHKSUM ;Set up checksum .IFF MOV #CHECK,CHKSUM ;Fixed checksum .ENDC CMPB UNIT,#MESSAG ;Mailbox data? BNE NOMAIL MOV #CHSTAT,R0 ;ADD MOV #BUFFER+480.,R2 ; JOB MOV (R0)+,(R2)+ ; INFO MOV (R0)+,(R2)+ ; RDSTAT MOV (R0)+,(R2)+ ; WTSTAT MOV (R0)+,(R2)+ ; JBSTAT .DATE MOV R0,(R2)+ ;System date .GTIM #AREA,R2 ;System time, 2 words! NOMAIL: ;-------------------------Send DATA packet(s)---------------------------; .IIF NE,TEST .PRINT #COND ;***TEST*** CALL ONEOUT ;Send the header ; ; Send data within packet through interr. routine ; SDATA: INC SPCNT .SPND ;Wait for contents send. ADD #PKASIZ,BUFDAT ;POINT TO NEXT DATA INC R3 ;NEXT BLOCK DEC R1 BEQ RDSUC ;Done with succes! DEC R4 ;Buffer exhausted? BNE SEND JMP READ RDSUC: .IF NE,SPF TSTB SPFCOD BPL 20$ TSTB ENDMOD ;Set by SPFUN Request! BPL 20$ JMP SNDEND .ENDC; SPF 20$: JMP SUCCES ;BR: too short range ;-----------------------IO: write to device---------------------------; WRITE: BIT R0,WTSTAT ;Check write prot. BNE 1$ JMP PRTERR ;Write protect error. 1$: MOVB #'R,COND WRIT: MOV BUFBLK,R4 ;R4=Nr. blocks to write CMP R4,R1 ;All? BLOS 1$ MOV R1,R4 ;No, less. 1$: MOV R4,R2 SWAB R2 ;R2=Nr. words to write. MOV #BUFFER,BUFDAT ;-----------------------Receive DATA packet(s)---------------------------; RCVDAT: .IIF NE,TEST .PRINT #COND ;***TEST*** MOVB #1,FLAG ;Set input flag MOV #CNDATA,ONEWRD ;CoNtinue with DATA flag. CLR WCNTX ;Go listening after send CNDATA CALL ONEOUT ;Send it INC SPCNT .SPND CALL ERRTST ;Error test. 2$: DEC R1 ;One block less to receive DEC R4 ;Buffer full? BNE RCVDAT .IF NE,SPF TSTB SPFCOD ;If this is SPF with DATA WRITE, data BNE SPFREQ ; are now in buffer. Execute SPF .ENDC CMPB #MESSAG,UNIT ;Outp. for MAILBOX? BNE 3$ .PRINT #BUFFER ;Yes, print it also. ; ; Clear remaining bytes in last block. ; 3$: TST R1 ;Last block received? BNE 4$ TST R5 ;Word rest? BEQ 4$ MOV #256.,R4 SUB R5,R4 ;Calculate remaining w. in block. MOV BUFDAT,R0 5$: CLR (R0)+ ;Clean them up. SOB R4,5$ ; 4$: .WRITW #AREA,UNIT,#BUFFER,R2,R3 BCS IOERR 6$: SWAB R2 ;Make nr. blocks ADD R2,R3 ;Next blockaddres for write. TST R1 ;All blocks done? BEQ SUCCES ;Done with succes JMP WRIT ;-------------------------I/O succes+errors---------------------------; ERRBYT=52 IOERR: TSTB @#ERRBYT ;EOF or HARD error? BNE HRDERR MOVB #-2,ENDMOD ;EOF error! JMP SNDEND SUCCES: CLRB ENDMOD JMP SNDEND PRTERR: ;Protected device violated. HRDERR: MOVB #-1,ENDMOD ;Hard error ;---------SPFUN requests + SPECIAL DIRECTORY device support-----------; .IF NE,SPF JMP SNDEND CONFIG=300 ;RT-11 CONFIGURATION word. USR$=1000 ;USR bit in CONFIG. word. ; R3 => Block address ; R5 => Remaining words ; Read/Spfun with zero wordcount: ; R1 => Nr. of IO blocks ; Write: ; R1 => R1=R4=0 (On return from receive data part=write processing) SPFREQ: MOVB #'F,COND MOV R3,R2 MOV #ENDINF,R4 ;Error return block 4 words. CLR (R4)+ CLR (R4)+ CLR (R4)+ CLR (R4)+ TSTB SPFCOD ;Positive means Special Directory req. BGT SPDIR CMPB UNIT,#MTCHAN BNE 1$ MOV #ENDINF,R2 ;Return MT errors here. 1$: MOV #BUFFER,BUFDAT MOV R1,R4 ;Setup R4 also for EXBUF code in SEND code. CMP R4,BUFBLK ;Data buffer for SPFUN must be contiguous! BHI SPFMEM ;Not enough memory to execute this SPF. .SPFUN #AREA,UNIT,SPFCOD,#BUFFER,SPDATA,R2 BCC 20$ ; ; SPFUN ERROR! Still send the data in case of SPFUN read request! MOVB #-1,ENDMOD ;Init with HARD error! TSTB @#ERRBYT ;EOF or HARD error? BNE 10$ MOVB #-2,ENDMOD ;EOF error! 10$: CMPB #2,OPCODE ;also DATA READ? BEQ 30$ ;No -> all done. Yes -> SPFUN REQ. with DATA- BR IOERR ;read; R1=Nr. IO blks, R5=wordrest, R4=R1 20$: CLRB ENDMOD ;Succes code! CMPB #2,OPCODE ;also DATA READ? BNE SUCCES ;No -> all done. Yes -> SPFUN REQ. with DATA- 30$: JMP SEND ;read; R1=Nr. IO blks, R5=wordrest, R4=R1 SPFMEM: MOV #"NB,TEXT ;Inform that there is No Buffer room! CALL PSTAT BR HRDERR ; ; SPECIAL DIRECTORY Device Requests: ; ================================== ; ASYREQ=-20. LOOKUP =3 ENTER =4 CLOSE =1 FNF =1 ; SPDIR: MOV #1,R4 ASH UNIT,R4 .GVAL #AREA,#CONFIG ;The USR must be available! BIT #USR$,R0 BNE USROK MOV #"NU,TEXT ;Inform that there is No Usr! CALL PSTAT JMP HRDERR USROK: CMPB SPFCOD,#CLOSE BNE SPDIRO SPCLOS: BIT R4,CHSTAT ;Channel open? BEQ HRDR ;No -> hard error .CLOSE UNIT BIC R4,CHSTAT ;Set channel no open. SUCC: JMP SUCCES SPDIRO: CMPB #MTCHAN,UNIT BNE OTHERS ; ; MT: perform ASYNCHRONOUS DIRECTORY OPERATION! ; BIT R4,CHSTAT BNE 1$ .LOOKUP #AREA,UNIT,#NFSMT,R3 BCS HRDR 1$: BIS R4,CHSTAT MOV #BUFFER+6,R2 ;BUFF word 1,2,3 ; contains RAD50 filename TST BUFFER ;Hardware LOOKUP?. BEQ SUCC ;Yes, then we are ready. CMPB #LOOKUP,SPFCOD BNE 2$ MOV #LOOKUP,(R2)+ BR 3$ 2$: CMPB #ENTER,SPFCOD BNE HRDR MOV #ENTER,(R2)+ 3$: MOV R3,(R2)+ ;Enter sequence number(BLCKNR). CLR (R2)+ ;DEC reserved CLR (R2)+ ;DEC reserved ; .SPFUN #AREA,UNIT,#ASYREQ,#BUFFER,,#ENDINF BCC SUCC ;CC =file found! CMP #FNF,ENDINF ;File not found? BEQ SUCC ;Yes! OK! .CLOSE UNIT BIC R4,CHSTAT ;Set channel no open. HRDR: JMP HRDERR OTHERS: BIT R4,CHSTAT BNE HRDR CLR R2 BISB UNIT,R2 SUB #SPCHAN,R2 ;Make offset for device block BMI HRDR ASL R2 ;Make bytes. ADD #NFSBLK,R2 MOV #BUFFER+6.,R5 ;Shift filename MOV #BUFFER+8.,R1 ; 1 word MOV -(R5),-(R1) ; upwards MOV -(R5),-(R1) ; in BUFFER. MOV -(R5),-(R1) MOV @R2,@R5 ;Copy device name. CMPB SPFCOD,#LOOKUP ;Lookup support. BNE 3$ .LOOKUP #AREA,UNIT,R5,R3 BCS HRDR BR 4$ 3$: CMPB SPFCOD,#ENTER ;Enter support. BNE HRDR .ENTER #AREA,UNIT,R5,,R3 BCS HRDR 4$: BIS R4,CHSTAT JMP SUCCES ;************************ User Edits this part **************************** NFSBLK: .RAD50 /PP0/ ;SPDIR 1 ,Non file struc. SPDIR block .RAD50 /PP1/ ;SPDIR 2 NFSMT: .RAD50 /MT / .WORD 0,0,0 ;*************************** End User Edit ******************************* .ENDC ;-------------------------Send END packet-----------------------------; SNDEND: MOVB #'E,COND MOV ENDPKT,ONEWRD ;Header flag to send 1st. MOV #PKMSIZ,WCNTX ;Checksum and header separ. send. MOV #ENDOPC,BUFDAT .IF NE,CKS MOV ONEWRD,CHKSUM ;Init checksum. .IFF MOV #CHECK,CHKSUM ;Fixed checksum. .ENDC CALL ONEOUT INC SPCNT .SPND .IF NE,TEST .PRINT #COND ;***TEST*** .PRINT #CRLF ;***TEST*** .ENDC JMP AGAIN ;Go listening. ;------------------------Error processing-----------------------------; CHKERR: TST (SP)+ ;Pop off ERRTST caller. CMPB #-1,IERR ;Real checksum error? BEQ 1$ MOV #"HD,TEXT ;Indicate. BR 2$ 1$: MOV #"CK,TEXT ;Indicate. 2$: MOVB #-1.,ENDMOD INC HERROR ;Checksum error ! Count it. CALL EQUASP ;Report status, clear err. flag, equalize. BR SNDEND ERRTST: TSTB IERR ;Error? BEQ RETRN BMI CHKERR CMPB #1,IERR ;INIT? BNE COMERR MOV #"IN,TEXT ;Init! COMERR: TST (SP)+ ;Pop off ERRTST caller. CFATAL: INC CERROR ;Count communications errors CALL EQUASP ;Report status, clear err. flag, equalize. JMP AGAIN EQUASP: ;Equalize the .spnd's CALL PSTAT ;Report status. CLRB IERR ;Clear error flag. TST SPCNT ;Equalize nr. .RSUM/.SPND's done. BEQ RETRN BMI 1$ 2$: .RSUM DEC SPCNT BEQ RETRN BR 2$ 1$: .SPND INC SPCNT BNE 1$ RETRN: RETURN ;-------------------------------------------------------------------------; ; Table for accounting information: IONRHI: .WORD 0 ;Nr IO's High word. IONRLO: .WORD 0 ;Nr IO's Low word. HERROR: .WORD 0 ;CHECKSUM ERROR COUNT. CERROR: .WORD 0 ;COMMUNIC. ERROR COUNT. SYNCNT: .WORD 0 ;.SYNCH ERR. BFSIZE: .WORD 0 ;Available data buffer size BITERR: .WORD 0 ;Nr. int. enabl. down. BUFBLK: .WORD 0 ;Nr. of available 256. word buffers ;-------------------------Utilities service-----------------------------; MASK: .WORD 0 JBFIN: .INTEN PRIO ; ; R4 = FLAG: +1 is SUSPEND, 0 is DONE, -1 is RESUME ; TST R4 BGT JBSPND BMI JBRSUM RETURN JBSPND: .SYNCH #JBSYNC RETURN CLR MASK BIT #IE,@#CSR BEQ 1$ BIS #IE,MASK BIC #IE,@#CSR 1$: .SPND RETURN ; JBRSUM: BIS MASK,@#CSR .SYNCH #JBSYNC RETURN ;Error return .RSUM RETURN CHSTAT: .WORD 0 ;Status channels open. RDSTAT: .WORD READQN ;READ protect. defaults. WTSTAT: .WORD WRITQN ;WRITE protect. defaults. JBSTAT: .BYTE 0,0 ;Job/SPF/Boot IOCOFF: .WORD IONRHI-IOCOFF TSTOFF: .WORD 0 PKTOFF: .WORD CMDPKT-PKTOFF .WORD 0 PRTOFF: .WORD CHSTAT-PRTOFF BR JBFIN ;Soft-interr. entry ;-----------------JOB MONITOR: interrupt service-------------------; QNINT:: .INTEN PRIO ;Lower priority. MOV @#CSR,R4 ;Get status-data BPL NOERR QNERR: MOVB #-3,IERR NOERR: CLR @#CSR ;Cleanup BIT #SND,R4 ;We were sending? BEQ 1$ JMP SNDTX 1$: TSTB FLAG BEQ INI ;=0 Listen BLT RDATA CMPB FLAG,#2 ;HEADER of packet or TAIL? BEQ TAIL HEADER: CMPB CMDPKT,#1 ;DATA-packet flag? BEQ 4$ ;O.K. go on MOVB #-2,IERR ;Try to send ENDPKT CLRB FLAG ;Go listening BR RESUME 4$: CLR R4 ;!? Do not use MOVB to registr.! BISB CMDPKT+1,R4 ;Nr. of Data-words to receive BNE 5$ ;O.K. MOV #256.,R4 ;Do them all. 5$: MOV R4,WCNT ;Store JMP GETBUF ;Sets FLAG, inits CHKSUM, jump to BUFINP RDATA: .IF NE,CKS .SYNCH #SYNBLK ;Lower interr. prio -> 0 because chk-calc. BR SFAIL ;Error return takes quite long! MOV WCNT,R1 MOV BUFDAT,R0 ;Get buffer pointer of DATA RLOOP: ADD (R0)+,CHKSUM ;Update ADC CHKSUM ; checksum SOB R1,RLOOP MOV R0,BUFDAT ;Update data pointer. .IFF ;CKS MOV WCNT,R5 ASL R5 ;Words->bytes ADD R5,BUFDAT .ENDC ;CKS MOVB #2,FLAG JMP ONEINP TAIL: CLRB FLAG ;Listen meanwhile. .IF NE,CKS CMP CMDPKT,CHKSUM ;Comp. received with calc. one. .IFF CMP CMDPKT,#CHECK ;Comp. received with fixed one. .ENDC; CKS BEQ RESUME ;O.K. MOVB #-1,IERR ;Give checksum error RESUME: CLR WCNTX .SYNCH #SYNBLK BR SFAIL ;Error return DEC SPCNT .RSUM RETURN SFAIL: INC SYNCNT ;Notifie. RET: RETURN ; ; HOST has something to do for us ? ; INI: CMP CMDPKT,#COMMND ;COMMAND? BEQ COMMD .IF NE,BSTRP CMP CMDPKT,#BOOT ;BOOT command? BEQ BOTCMD .ENDC ;BSTRP CMP CMDPKT,#INIT ; INIT? BEQ 1$ BR ONEINP ;Get next one. ;***** We received an INIT, so transmitter must be ready *****; 1$: MOV #CONTIN,ONEWRD ; CONTINUE CLR WCNTX ;TX: do nothing after interrupt MOVB #1,IERR ;Indicate INIT error. JMP ONEOUT .IF NE,BSTRP BOTCMD: MOV CMDPKT,OPCODE BR RESUME .ENDC ;BSTRP COMMD: MOV #OPCODE,BUFDAT ;Flag+packetsize already receiv. MOV #PKMSIZ,R4 ;R4 = WCNT, wordcount. MOV R4,WCNT GETBUF: MOVB #-1,FLAG ;Data next. .IF NE,CKS MOV CMDPKT,CHKSUM ;Init checksum! .IFF MOV #CHECK,CHKSUM ;Init checksum! .ENDC BR BUFINP ;-------------------------- Output(XT) service --------------------------; SNDTX: MOV WCNTX,R5 ;Get nr. to send BEQ ONEINP ;Go listening BMI CHKSND ;Send checksum/resume main MOV WCNTX,R4 ;Wordcount for QN MOV R4,WCNT ;Save MOV #-1,WCNTX BR BUFOUT CHKSND: CMP #-2,WCNTX BEQ RESUME .IF NE,CKS .SYNCH #SYNBLK ;Lower interr. prio -> 0 because chk-calc. BR SFAIL ;Error return takes quite long! MOV WCNT,R1 MOV BUFDAT,R0 ;BUFDAT sould be pointing to data XLOOP: ADD (R0)+,CHKSUM ;Calculate ADC CHKSUM ; checksum. SOB R1,XLOOP .ENDC; CKS MOV CHKSUM,ONEWRD MOV #-2,WCNTX ;Resume main next, goto ONEOUT ;------------------------- QN interface service ----------------------------; ONEOUT: BIS #SND,QNPATR MOV #ONEWRD,@#BAR BR QNGO1 ONEINP: BIC #SND,QNPATR MOV #CMDPKT,@#BAR QNGO1: MOV #-1,@#WCR BR QNGO BUFOUT: BIS #SND,QNPATR BR QNGOB BUFINP: BIC #SND,QNPATR QNGOB: MOV BUFDAT,@#BAR NEG R4 MOV R4,@#WCR QNGO: MOV QNPATR,@#CSR RETURN QNPATR: .WORD CE+IE+GO ;-----------------------------Packets-------------------------------; ; 1. COMMAND PACKET: CMDPKT::.BYTE 0 .BYTE 0 ;PKTWRD OPCODE: .BYTE 0 MODIF: .BYTE 0 UNIT: .BYTE 0 SPFCOD: .BYTE 0 SPDATA: .WORD 0 WRDCNT: .WORD 0 BLCKNR: .WORD 0 ; 2. END PACKET: ENDPKT: .BYTE 2 ENDWRD: .BYTE 5 ENDOPC: .BYTE 64. ;=64.,100 for ENDPKT ENDMOD: .BYTE 0 ;=SUCCES CODE for ENDPKT ENDINF: .WORD 0 ;SPFUN/SPDIR 1 error return .WORD 0 ; 2 .WORD 0 ; 3 .WORD 0 ; 4 ;----------------------Miccellaneous Storage-----------------------------; ONEWRD: .WORD 0 CHKSUM: .WORD 0 ;1 result current checksum calculation SPCNT: .WORD 0 ;2 Actual nr. .SPND's pending. WCNT: .WORD 0 ;3 Word count of packets WCNTX: .WORD 0 ;4 Word count of packets BUFDAT: .WORD 0 ;5 Pointer to DATA to SEND/RECEIVE IERR: .BYTE 0 ;6 ERROR on receive/send FLAG: .BYTE 0 ;6 RECEIVER FLAG, 0=listen, <0=data receive DLIST: .WORD CSR ;7 .WORD 0 .WORD 0 ;DLIST terminator. SYNBLK: .WORD 0 .WORD 0 .WORD 0 .WORD 0 .WORD 5 .WORD -1,0 JBSYNC: .WORD 0 .WORD 0 .WORD 0 .WORD 0 .WORD 5 .WORD -1,0 AREA: .BLKW 6 ;-------------------------- STATUS/ERROR logging --------------------------; PSTAT: .if EQ,TEST .PRINT #TEXT .iff MOV #TEXT,R0 MOVB #'-, COND+1 .PRINT MOVB #200,COND+1 .endc RETURN TEXT: .ASCII / -/ .if EQ,TEST COND: .ASCII / -/ .iff COND: .ASCII / /<200> .endc .ASCII /QNJOB/ .BYTE JBNUM+60 CRLF: .BYTE 0 ;CR, LF, Terminator. .EVEN ;--------------------- BUFFER / Initialisation code -----------------------; .PSECT INITJB BUFFER:: CLR @#CSR .SERR ;Soft-error reporting .DEVICE #AREA,#DLIST MOV #JOB,R5 .GTJB #AREA,R5 MOV (R5),SYNBLK+2 MOV (R5),JBSYNC+2 ; MOV #QNVEC,R1 .PROTECT #AREA,R1 BCS ERRPR MOV #QNINT,(R1)+ MOV #340,(R1) BR GETDEV ERRPR: .PRINT #CERR .EXIT ;************* User Edits this part ****************** ; *** Permanent list of devices *** ; --------------------------------------------- DVLIST: .RAD50 /DL0DL0LD0DSK/ ;DEV. # 0 .RAD50 /DL0DL0LD1DSK/ ;DEV. # 1 .RAD50 /DL0DL0LD2DSK/ ;DEV. # 2 .RAD50 /DL1DL1LD3DSK/ ;DEV # 3 .RAD50 /DL1DL1LD4DSK/ ;DEV # 4 .RAD50 /DL1DL1LD5DSK/ ;DEV # 5 .RAD50 /DL0DL0LD6DSK/ ;DEV # 6 .RAD50 /DL1DL1LD7DSK/ ;DEV # 7 .RAD50 /SY JBINFOSYS/ ;DEV # 8, Mailbox .RAD50 /HEL / ;DEV # 9, Remote mailbox .RAD50 /SP / ;DEV #10., SPOOLER .RAD50 /DL0 / ;DEV #11. .RAD50 /DL1 / ;DEV #12. .RAD50 /DL2 / ;DEV #13. .RAD50 /FRE / ;DEV #14. .RAD50 /PP0 / ;DEV #15. MESSAG= 8. ;Channel nr. for operator messages exchange. MTCHAN= 16. ; " " MAGTAPE. SPCHAN= 16. ; " " start list of SPDIR devices. ; -------------------------------------------------- ;****************** End User Edit ************************* QNBOOT: .RAD50 /SY QNBOOTSYS/ ;Bootstrap program!(From BOOT30.MAC) JOB: .BLKW 8. CERR: .ASCIZ /QN-VEC inuse!/ INITXT: .ASCII />QNJOB/ .BYTE JBNUM+60 .ASCII / runs!/<012><0> .EVEN ; Open channels on devices: GETDEV: CLR CHSTAT ;Clear channel status MOV #DVLIST,R1 MOV #FILDEV,R2 CLR R3 ;Channel nr. to open MOV #1,R4 ;Channel Bit OPENCH: CMP R3,#MTCHAN BNE 1$ .LOOKUP #AREA,R3,R1,#0 BR 2$ 1$: .LOOKUP #AREA,R3,R1 2$: BCS 3$ BIS R4,CHSTAT ;Channel open! 3$: ASL R4 ADD #8.,R1 ;Point to next device INC R3 SOB R2,OPENCH MOVB #JBNUM,JBSTAT .IIF NE,SPF BIS #200,JBSTAT .PRINT #INITXT ;Say hallo to console MOV #"IN,TEXT ;Init reports MOVB #'I,COND ;Information CALL PSTAT ;Print startup status .IF NE,BSTRP .SAVEST #AREA,#MESSAG,#CHINFO .LOOKUP #AREA,#MESSAG,#QNBOOT .SAVEST #AREA,#MESSAG,#CHBOOT .REOPEN #AREA,#MESSAG,#CHINFO .ENDC ;BSTRP MOV #-2,R0 .SETTOP SUB #BUFFER,R0 ;R0 = top of program TST (R0)+ ;R0 = available memory in bytes ASR R0 ;R0 = available memory in words MOV R0,BFSIZE CLRB R0 ;Multiple of 256. SWAB R0 MOV R0,BUFBLK ;No. of 256. word data buffers. RETURN ;Go running!! .=BUFFER+510. ;GET SPACE FOR 256. WORD LAST: .WORD 0 ; BUFFER! ;--------------End of initializing code / buffer area-----------------; .END START