--- /dev/null
+TITLE SRCCOM V.016 12-JUNE-69\r
+SUBTTL SOURCE FILE COMPARE - BOWERING/TWE\r
+;*****(C)COPYRIGHT 1969 BY DIGITAL EQUIPMENT CORP., MAYNARD, MASS.,USA*****\r
+\r
+INTERNAL JOBVER,PURE\r
+LOC <JOBVER==137>\r
+ EXP 16\r
+\r
+EXTERNAL JOBFF, JOBREL, JOBDA\r
+\r
+IFNDEF PURE,<PURE=1>\r
+ IFN PURE,<HISEG>\r
+\r
+ACDEV==1 ;COMMAND SCANNER ACCUMULATORS\r
+ACFILE==2\r
+ACEXT==3\r
+ACDEL==4\r
+ACPNTR==5\r
+ACPPN==6 ;COMMAND SCANNER AC FOR PROJ,PROG #\r
+\r
+CTL=0 ;I/O CHANNEL ASSIGNMENTS\r
+IN1=1\r
+IN2=2\r
+out=3\r
+AL=1 ;ASCII LINE MODE\r
+\r
+W1=1\r
+W2=2\r
+W3=3\r
+FIL=4 ;FILE # (0 IS FILE 1; 1 IS FILE 2)\r
+F1=5 ;LINE POINTER FILE 1 (CONTAINS INTEGER)\r
+F2=F1+1 ;DITTO FILE 2\r
+FR=7 ;FLAG REGISTER (LH) AND FILE #(0 OR 1)(RH)\r
+C=10 ;CONTAINS 1 CHAR FOR PROCESSING\r
+T=11 ;TEMPORARY AC\r
+TT=12 ;TEMP AC\r
+PP=17 ;PUSH DOWN POINTER\r
+LPDL==20 ;LENGTH OF PUSH DOWN LIST\r
+\r
+TAB==11\r
+LF==12\r
+FF==14\r
+CR==15\r
+VT==13 ;VERTICAL TAB\r
+\r
+NOFORM==1 ;DON'T OUTPUT FORM FEED\r
+PAGSW==2\r
+ENDSW==4 ;END SWITCH (SUPPRESS FORM-FEED IF FILES IDENTICAL)\r
+SSWBIT==100 ;/S SWITCH - IGNORE SPACING\r
+CSWBIT==200 ;/C SWITCH - IGNORE COMMENTS\r
+ALLSW==400 ;/B SWITCH (ALLOWS COMPARING BLANK LINES)\r
+EOF1SW==1000 ;EOF SEEN ON FILE 1\r
+EOF2SW==2000 ;EOF SEEN ON FILE 2\r
+IOTTY==4000 ;OUTPUT TO TTY\r
+CTYPF==10000 ;1 IF ANY CHARS TYPED FOR A COMMAND\r
+\r
+MATCH==3 ;# LINES TO BE MATCHED\r
+WPL==^D100/5+1 ;MEMORY WORDS/LINE\r
+LPP==^D52 ;LINES/PAGE\r
+\r
+COMP: MOVEI 0,106\r
+ MOVEM 0,CCNT\r
+COMPGO: CALLI\r
+ MOVEI 0,ENDP\r
+ MOVEM 0,JOBFF ;SET JOBFF AFTER VARIABLE AREA\r
+ MOVE PP,[IOWD LPDL,PPSET] ;SET UP PUSH DOWN LIST\r
+ MOVE 0,JOBFF\r
+ ADDI 0,500\r
+ CALLI 0,11 ;CORE UUO\r
+ JRST ERRCOR ;NOT AVAILABLE\r
+ SETZM PPSET ;THIS IS THE ZERO WHICH WILL ; BE "BLT"ED TO CLEAR CORE\r
+ MOVE [XWD PPSET,PPSET+1] ;ZERO STORAGE AREA\r
+ BLT ENDP-1 ;ZEROED\r
+ MOVEI 0,MATCH-1\r
+ MOVEM 0,NUMLIN ;MATCH IS NORMALLY 3 LINES (N-1)\r
+ AOS PAGNUM+0 ;ZEROED BY BLT ABOVE-1ST PAGE IS 1\r
+ AOS PAGNUM+1 ;DITTO FOR SECOND FILE\r
+ MOVSI FR,NOFORM+PAGSW ;INIT FR FOR NEW PAGE HEADING\r
+ PUSHJ PP,INITTY ;INITIALIZE TTY\r
+ PUSHJ PP,CRLF ;OUTPUT CARRIAGE RETURN - LINE FEED\r
+ MOVEI C,"*" ;TELL USER WE ARE READY FOR COMMAND\r
+ PUSHJ PP,TYO ;OUTPUT THE *\r
+ PUSHJ PP,DMPOUT ;OUT GOES THE *\r
+ PUSHJ PP,NAME1 ;ANALIZE OUTPUT DEVICE AND NAME\r
+ CAIN C,"_" ;ERROR IF NO ARROW\r
+ JRST CTLSE1 ;ITS THERE--PROCEED\r
+ TLNN FR,CTYPF ;ANY COMMAND TYPED?\r
+ JRST COMPGO ;NO\r
+CTLSER: JSP T,ERROUT\r
+ ASCIZ /?COMMAND ERROR/\r
+\r
+CTLSE1: JUMPN ACFILE,CTLSE2 ;NO DEFAULT IF DEVICE NOT 0\r
+ SKIPN ACDEV\r
+ MOVSI ACDEV,(SIXBIT /TTY/) ;IF FILENAME 0, ASSUME TTY\r
+CTLSE2: SKIPN ACDEV\r
+ MOVSI ACDEV,(SIXBIT /DSK/) ;IF FILENAME NOT 0, ASSUME DISK\r
+ MOVEM ACDEV,OUTDEV ;SAVE OUTPUT DEVICE IN DIRECTORY BLOCK\r
+ MOVEM ACFILE,OUTDIR ;PUT SIXBIT FILE NAME IN\r
+ MOVEM ACEXT,OUTDIR+1 ;AND SAVE EXTENSION\r
+\f;PROCESS INPUT PART OF COMMAND STRING\r
+ PUSHJ PP,NAME1 ;GET INPUT COMMAND STRING\r
+ CAIN C,"," ;COMMA TO TERMINATE 1ST INPUT FILE?\r
+ TLNN FR,CTYPF ;ANY FILE DESCRIPTOR TYPES?\r
+ JRST CTLSER ;NO, ERROR\r
+ SKIPN ACDEV ;ASSUME DSK IF NO SPECIFIED DEVICE\r
+ MOVSI ACDEV,(SIXBIT /DSK/)\r
+ MOVEM ACDEV,INDEV1\r
+ MOVEM ACFILE,INDIR1 ;FIRST INPUT FILE\r
+ MOVEM ACEXT,INDIR1+1 ;AND SAVE EXTENSION\r
+ MOVE 0,OPN1 ;INIT IN1,1\r
+ MOVE 2,OPN1+1 ;INBUF1\r
+ MOVE 3,OPN1+3 ;ERROR\r
+ MOVE 4,OPN1+4 ;JRST CTLSE3\r
+ JRST 0 ;OPEN FILE FILE #1\r
+\r
+CTLSE3: INBUF IN1,2 ;DO LOOKUP ON FIRST FILE NAME\r
+ LOOKUP IN1,INDIR1\r
+ JRST ERRIA ;ERROR RETURN\r
+ PUSHJ PP,NAME1\r
+ TLNN FR,CTYPF ;ANY FILE DESCRIPTOR TYPED?\r
+ JRST CTLSER ;NO, ERROR\r
+ SKIPN ACDEV\r
+ MOVSI ACDEV,(SIXBIT /DSK/) ;"DSK" IS DEFAULT\r
+ MOVEM ACDEV,INDEV1\r
+ SKIPE ACFILE\r
+ MOVEM ACFILE,INDIR1 ;INSERT FILE NAME AND EXTENSION\r
+ CAIN ACDEL,"." ;PERIOD MEANS EXPLICIT EXTENSION\r
+ MOVEM ACEXT,INDIR1+1\r
+ MOVE 0,OPN2 ;INIT IN2,2\r
+ MOVE 1,INDEV1\r
+ MOVE 2,OPN2+1\r
+ MOVE 3,OPN1+3\r
+ MOVE 4,OPN2+2\r
+ JRST 0 ;OPEN FILE IN REGISTERS.\r
+ERR2A: INBUF IN2,2 ;LOOKUP ON SECOND FILE NAMES\r
+ LOOKUP IN2,INDIR1\r
+ JRST ERRIA\r
+ MOVSI 0,41000 ;INIT \r
+ TLNE FR,40000\r
+ MOVSI 0,41140 ;INIT\r
+ MOVE ACDEV,OUTDEV\r
+ MOVSI ACFILE,CTOBUF\r
+ TLNE FR,40000\r
+ MOVSI 2,OUTBUF ; ADJUST REGISTERS.\r
+ MOVE 3,OPN1+2\r
+ MOVE 4,OPN2+3\r
+ JRST 0 ; EXECUTE IN REGISTERS\r
+CTLSE4: MOVE TT,OUTDEV\r
+ CALLI TT,4 ;DEVCHR\r
+ TLNN TT,1\r
+ JRST ERRO\r
+ TLNE TT,40010 ; CHECK IF TTY OR LPT\r
+ TLO FR,IOTTY\r
+ MOVE T,INDIR1 ; SETUP OUTPUT FILE\r
+ SKIPN OUTDIR\r
+ MOVEM T,OUTDIR\r
+ MOVSI T,(SIXBIT /SCM/)\r
+ TLNE FR,40000\r
+ MOVSI T,(SIXBIT /MRG/)\r
+ SKIPN OUTDIR+1\r
+ MOVEM T,OUTDIR+1\r
+ MOVE 0,[ENTER CTL,OUTDIR]\r
+ TLNE FR,40000\r
+ HRLI 0,(ENTER OUT,) ; ENTER OUTPUT FILE\r
+ XCT 0\r
+ JRST ERRO\r
+ OUTPUT CTL,\r
+ TLNE FR,40000\r
+ OUTPUT 3,\r
+ AOS W1,JOBFF\r
+ HRRZM W1,LBUFP1 ;SET 1ST ADDRESS FILE 0\r
+ SETZM 0,1(W1) ;FORCE NULLS INTO BUFFER\r
+ HRRZM W1,LBUFP2 ;DITTO FILE 2\r
+ MOVE W1,JOBREL\r
+ SUB W1,JOBFF ;COMPUTE SPACE AVAILABLE\r
+ HRRZS W1\r
+ LSH W1,-1 ;AVAILABLE SPACE/2\r
+ ADDB W1,LBUFP2 ;INPUT POINTER FILE 2 STARTS HALF WAY THROUGH BUFFER\r
+ SETZM 1(W1) ;FORCE NULLS INTO BUFFER\r
+ HRLOI 0,377777\r
+ MOVEM 0,OLDNUM ;ANY LINE # IS SMALLER THAN\r
+ MOVEM 0,OLDNUM+1 ; THIS ONE\r
+ SETOB F1,TOP1 ;INITIALIZE TOP OF EACH FILE\r
+ SETOB F2,TOP2 ;THE TOP IS THE HIGHEST LINE THAT WE HAVE EXAMINED\r
+ PUSHJ PP,GETTWO\r
+ JFCL \r
+ MOVE W1,LBUFP1\r
+ HRRZ W2,(W1)\r
+ MOVSI W1,1(W1)\r
+ HRRI W1,HBUF1\r
+ CAIL W2,25\r
+ MOVEI W2,25\r
+ BLT W1,HBUF1(W2)\r
+ SETZM HBUF2-1\r
+ MOVE W1,LBUFP2\r
+ HRRZ W2,(W1)\r
+ MOVSI W1,1(W1)\r
+ HRRI W1,HBUF2\r
+ CAIL W2,25\r
+ MOVEI W2,25\r
+ BLT W1,HBUF2(W2)\r
+ SETZM HBUF2+WPL-1\r
+ JRST MAINST ;START COMPARE WITH 1ST LINES\r
+\f;THE FOLLOWING CODE IS THE GUTS OF THE PROGRAM.\r
+;WHEN THE LOOP AROUND MAIN DETECTS THAT TWO LINES ARE NOT A MATCH\r
+;CONTROL GOES OFF TO DETERMINE THE EXTENT OF THESE DIFFERENCES.\r
+;THE TOTAL DIFFERENCES ARE DETERMINED AS FOLLOWS. FIRST GET TWO \r
+;MORE LINES. DOES THE ORGINAL LINE IN FILE 1 WHICH DID NOT MATCH\r
+;MATCH THE NEW LINE FROM FILE TWO. IF SO THEN THE ORGINAL LINE\r
+;IN FILE 2 WAS AN INSERTION. (OR A DELETION). IF NO MATCH THIS \r
+;WAY TRY IT THE OTHER WAY. IF STILL NO MATCH GET TWO MORE LINES\r
+;TAKE THE NEW LINE FROM FILE 1 AND TRY TO MATCH IT AGAINST ALL THE\r
+;LINES WE HAVE BEEN EXAMINING IN FILE TWO; THEN DO IT THE OTHER\r
+;WAY AROUND. EOF'S ARE DETECTED BY "GETTWO" WITH NO RETURN SKIP\r
+\r
+MAIN: TRZ FR,-1 ;THIS FOR FILE ONE\r
+ SETZM MPP(FR)\r
+ PUSHJ PP,MOVEUP ;MOVE UP THE BOTTOM, BECAUSE WE ARE FINISHED\r
+ ;WITH TWO LINES\r
+ HRRI FR,1 ;NOW FOR FILE TWO\r
+ TLNE FR,40000\r
+ SETOM MPP(FR)\r
+ PUSHJ PP,MOVEUP ;UP GOESA THE BOTTOM POINTER\r
+MAINST: SETOB F1,F2 ;INITIALIZE LINE POINTERS\r
+ PUSHJ PP,GETTWO ;GET TWO LINES\r
+ JRST MAIN15 ;ONE FILE SHORT\r
+ PUSHJ PP,COMPL ;COMPARE THESE TWO LINES\r
+ JRST MAIN ;THEY MATCH--LOOK AT NEXT TWO\r
+\r
+;WHEN WE GET HERE WE HAVE DETECTD A DIFFERENCE\r
+;NOW THE PROGRAM WILL LOOK AHEAD TO TRY AND FIND THE NEXT TWO\r
+;MATCHING LINES\r
+\r
+MAIN10: PUSHJ PP,GETTWO ;GET THE NEXT TWO LINES\r
+ JRST MAIN15 ;ONE FILE SHORT\r
+ SETZ F1, ;RESET POINTER FOR FIRST FILE TO\r
+ ;THE LINE IN WHICH THE DIFFERENCE WAS FOUND\r
+\r
+MAIN12: PUSHJ PP,COMPL ;NOW SEE IF WE CAN MATCH THAT LINE\r
+ JSP W1,MULTI ;FOUND 1 LINE MATCH- LOOK FOR MULTIPLE\r
+ CAME F1,F2 ;HAVE WE LOOKED FROM THE MISMATCHED LINE\r
+ ;TO THE CURRENT LINE?\r
+ AOJA F1,MAIN12 ;NO--UP LINE POINTER AND TRY AGAIN\r
+ SETZ F2, ;HAVEN'T FOUND A MATCH THIS TIME\r
+ ;NOW TRY IT THE OTHER WAY\r
+\r
+MAIN14: CAML F2,F1 ;LOOKED FAR ENOUGH? (THIS VERSION HAS\r
+ ;THE INEFFICIENCY MENTIONED IN THE LIBRARY\r
+ ;WRITE UP REMOVED- TWE)\r
+ JRST MAIN10 ;YES\r
+ PUSHJ PP,COMPL\r
+ JSP W1,MULTI ;LOOK FOR MULTI LINE MATCH\r
+ AOJA F2,MAIN14 ;INDEX AND LOOK SOME MORE\r
+\f\r
+;THE MAIN15 CODE HANDLES THE CASE OF EITHER (OR BOTH) FILES\r
+;HAVING NO LINES TO COMPARE. IF BOTH FILES HAVE NO LINES, "FINISH"\r
+;PRINTS OUT ALL LINES IN BOTH FILES (IF ANY) AS DIFFERENCES.\r
+;IF EITHER FILE HAS A NEW LINE, THE SHORTER FILE IS\r
+;SEARCHED FOR A MATCH FOR THAT LINE. THIS CONTINUES (READING A NEW LINE\r
+;FROM THE LONGER FILE) UNTIL NEITHER FILE HAS ANY LINES OR UNTIL A\r
+;MATCH IS FOUND.\r
+\r
+MAIN15: SKIPGE W1,GETFIL ;DOES EITHER FILE HAVE A LINE?\r
+ JRST FINISH ;NO\r
+ HRRZM W1,FIL ;SAVE FILE # THAT HAS LINES\r
+ HRR FR,W1 ;SETUP FR FOR MAIN18\r
+ JUMPL F1,MAIN18 ;TRA IF FILE 1 HAS NO LINES\r
+ JUMPL F2,MAIN18 ;DITTO FILE 2\r
+ TRC FIL,1 ;CHANGE 1 TO 0 (OR VICE VERSA)\r
+ SETOM F1(FIL) ;LOOK THRU SHORT FILE FOR MATCH\r
+MAIN17: MOVE W1,F1(FIL)\r
+ CAML W1,TOP(FIL) ;SEARCHED THRU SHORT FILE?\r
+ JRST MAIN10 ;YES, AND NO MATCH\r
+ AOS F1(FIL) ;INDEX LINE\r
+ PUSHJ PP,COMPL ;LOOK FOR A MATCHING LINE\r
+ JSP W1,MULTI ;FOUND A MATCH, NOW LOOK FOR MULTIPLE MATCH\r
+ JRST MAIN17 ;NO MULTI LINE MATCH\r
+\r
+MAIN18: PUSHJ PP,PNTTXT ;ALL LINES ARE GONE FROM 1 FILE.\r
+ ;OUTPUT THE OTHER WITHOUT USING CORE\r
+ PUSHJ PP,MULT9\r
+ JRST MAIN\r
+ JRST MAIN\r
+\r
+;AT THIS POINT NEITHER FILE HAS ANY MORE LINES TO BE READ.\r
+;PRINT AS DIFFERENCES ANY LINES REMAINING FOR EITHER FILE.\r
+\r
+FINISH: JUMPGE F1,FIN1 ;PRINT DIFFERENCES IF EITHER BUFFER\r
+ JUMPL F2,FIN2 ; HAS ANY LINES IN IT\r
+FIN1: PUSHJ PP,PNTBTH ;PRINT ANY LINES\r
+FIN2: MOVEI T,[ASCIZ /NO DIFFERENCES ENCOUNTERED/]\r
+ SKIPN 0,ERRCNT ;ANY DIFFERENCES?\r
+ PUSHJ PP,TYPMSG ;NO, PRINT MESSAGE\r
+ SKIPE 0,ERRCNT\r
+ TLNN FR,40000\r
+ JRST CARR1\r
+ MOVEI T,[ASCIZ /END OF MERGE/]\r
+ PUSHJ PP,TYPMSG\r
+ JRST CARR1 ;END OF SOURCE COMPARE\r
+\f\r
+;THIS SECTION LOOKS FOR MULTI LINE MATCH\r
+\r
+MULTI: SKIPG NUMLIN ;MULTIPLE LINE TEST?\r
+ JRST MULT8 ;NO\r
+ HRRZM W1,RTNTMP ;YES, SAVE RETURN ADDRESS\r
+ SETZM NUMTMP ;INIT MULTI-LINE COUNTER\r
+ MOVEM F1,TEMPF1 ;SAVE CURRENT POINTERS\r
+ MOVEM F2,TEMPF2\r
+MULT2: PUSHJ PP,GETTWO ;GET NEXT TWO LINES\r
+ JRST MULT4 ;ONE FILE DOESN'T HAVE A LINE\r
+ PUSHJ PP,COMPL ;COMPARE THEM\r
+ JRST MULT6 ;MATCH, TEST MULTI COUNTER\r
+MULT4: MOVE F1,TEMPF1 ;NO MATCH, RESET REGS\r
+ MOVE F2,TEMPF2\r
+ JRST @RTNTMP ;RETURN TO WHERE WE GOT TO MULTI FROM\r
+\r
+MULT6: AOS W1,NUMTMP ;INDEX MULTI-LINE COUNTER\r
+ CAMGE W1,NUMLIN ;TEST FOR END\r
+ JRST MULT2 ;TEST NEXT TWO\r
+ SUB F1,W1 ;RESET TO 1ST COMPARISON\r
+ SUB F2,W1\r
+MULT8: PUSHJ PP,PNTBTH ;PRINT DIFFERENCES\r
+ PUSHJ PP,MULT9\r
+ JRST MULT8A\r
+\r
+;THE TEXT OF DIFFERENCES HAS BEEN PRINTED--PUT IN ******\r
+;AND A CARRIAGE RETURN-LINE FEED AND GO BACK AND START COMPARING\r
+;WHEN WE START COMPARING AGAIN THE LINE POINTERA WILL\r
+;BE POINTING TO THE FIRST TWO LINES AFTER THE MATCHING LINES\r
+\r
+ MOVE W1,[POINT 7,[ASCIZ /***************/]]\r
+ PUSHJ PP,PRINT\r
+ PUSHJ PP,PCRLF ;PRINT CARRIAGE RETURN-LINE FEED\r
+MULT8A: ADD F1,NUMLIN ;CAUSE MOVEUP TO FLUSH ALL THE\r
+ ADD F2,NUMLIN ; LINES THAT WERE JUST MATCHED\r
+ JRST MAIN ;DIFFERENCES PRINTED- LOOK FOR MORE\r
+MULT9: TLNN FR,40000\r
+ JRST CPOPJ1\r
+ SUBI F1,1\r
+ SUBI F2,1\r
+ PUSHJ PP,DMP3\r
+MULT10: PUSHJ PP,GETC\r
+ HRRI FR,0\r
+ CAIN C,61\r
+ JRST MULT11\r
+ HRRI FR,NOFORM\r
+ CAIE C,62\r
+ JRST MULT12\r
+MULT11: SETOM MPP(FR)\r
+ PUSHJ PP,MOVEUP\r
+ SETOM F1(FR)\r
+ JRST MULT10\r
+MULT12: CAIE C,124\r
+ JRST .+6\r
+MULT13: PUSHJ PP,TTYIN1\r
+ CAIN C,33\r
+ JRST MULT10\r
+ PUSHJ PP,FILEO\r
+ JRST MULT13\r
+ CAIE C,0\r
+ HALT .+1\r
+ HRRI FR,0\r
+ SETZM MPP(FR)\r
+ SKIPL F1(FR)\r
+ PUSHJ PP,MOVEUP\r
+ HRRI FR,NOFORM\r
+ SETZM MPP(FR)\r
+ SKIPL F1(FR)\r
+ PUSHJ PP,MOVEUP\r
+ ADDI F1,1\r
+ ADDI F2,1\r
+ POPJ PP,\r
+\f;THIS ROUTINE SETS UP THE POINTERS TO THE TEXT\r
+\r
+;MEMORY STORAGE AREA LOOKS LIKE THIS:\r
+;1) BUFFER SPACE FOR FILE # 0 (POINTED TO BY LBUFP1)\r
+; A) XWD (PAGE #),(WORD COUNT FOR LINE (INCLUDING THIS WORD))\r
+; TEXT FOR LINE 0\r
+; MORE TEXT FOR LINE 0\r
+; & MORE, ENDED WITH A NULL\r
+; B) MORE LINES (EACH WITH PAGE #,WORD COUNT, AND TEXT\r
+;2) BUFFER SPACE FOR FILE 1 (POINTED TO BY LBUFP2)\r
+; A) AS ABOVE\r
+\r
+SETP: HRRI FR,1 ;SET UP POINTER FILE 1\r
+ PUSHJ PP,SETONE\r
+ HRRI FR,0 ;DITTO FILE 0\r
+\r
+SETONE: MOVE W3,F1(FR) ;GET LINE #\r
+SETON1: MOVE TT,OLDNUM(FR) ;GET LAST # COMPUTED FOR\r
+ MOVEM W3,OLDNUM(FR) ;SAVE NEW # AS OLD\r
+ CAML W3,TT ;IS NEW LARGER THAN OLD?\r
+ SKIPA T,OLDPNT(FR) ;YES, START FROM OLD BYTE POINTER\r
+ SKIPA T,LBUFP1(FR) ;NO, START FROM BEGINNING\r
+ SUB W3,TT ;LOOP ONLY FROM OLD POINTER\r
+ MOVSI TT,(ADD T,(T)) ;(SET UP IN AC)\r
+ MOVE TT+2,[JRST SETON2];SET UP AC\r
+ MOVE TT+1,.+1 ;SET UP AC\r
+ SOJGE W3,TT\r
+ ;TT/ ADD T,(T) ;ADD IN WORD COUNT FOR LINE\r
+ ;TT+1/ SOJGE W3,.-1 ;MORE LINES LEFT?\r
+ ;TT+2/ JRST SETON2 ;NO\r
+\r
+SETON2: HRRZM T,OLDPNT(FR) ;SAVE POINTER TO THIS LINE\r
+ HRLI T,700 ;NO, CHANGE TO BYTE POINTER\r
+ MOVEM T,1(FR)\r
+ POPJ PP,\r
+\r
+;MOVE UP THE POINTERS WHICH POINT TO THE LINES FROM WHICH WE\r
+;ARE EXAMINING. THIS IS DONE EVERYTIME A MATCH IS FOUND\r
+\r
+MOVEUP: SKIPE MPP(FR) \r
+ SKIPGE W3,F1(FR) \r
+ JRST MOVEY \r
+ CAMLE W3,TOP(FR)\r
+ MOVE W3,TOP(FR)\r
+ HRRZ T,LBUFP1(FR)\r
+MOVE0: MOVEI W1,1(T)\r
+ HRLI W1,(POINT 7,,)\r
+ ILDB C,W1\r
+ JUMPE C,.+3\r
+ PUSHJ PP,FILEO\r
+ JRST .-3\r
+ ADD T,(T)\r
+ SOJGE W3,MOVE0\r
+MOVEY: MOVE W3,F1(FR) ;GET LINE # FOR THIS\r
+ CAML W3,TOP(FR) ;GETTING RID OF ALL LINES?\r
+ JRST MOVEX ;YES, DON'T MOVE MEMORY\r
+ AOS W3,F1(FR) ;GET LINE # OF LINE TO SAVE\r
+ PUSHJ PP,SETON1 ;GET ADR OF 1ST LINE TO SAVE\r
+ HRL T,LBUFP1(FR) ;SET UP BLT AC (REVERSED)\r
+ PUSH PP,T ;SAVE\r
+ AOS W3,TOP(FR) ;GET 1ST NON-EXISTANT LINE #\r
+ PUSHJ PP,SETON1 ;GET CORRESPONDING 1ST ADR\r
+ POP PP,W1\r
+ SUB T,W1 ;CALCULATE WORD COUNT OF TRANSFER\r
+ ADD T,LBUFP1(FR) ;CALCULATE "E" OF BLT AC,E\r
+ MOVSS 0,W1 ;SWITCH AC TO XWD FROM,TO\r
+ BLT W1,(T) ;AND AWAY WE GO\r
+\r
+MOVEX: SETCM W2,F1(FR) ;W2_-<(F1)+1>\r
+ ADDM W2,TOP(FR) ;CHANGE TO OP TO ACCOUNT FOR DEAR DEPARTED LINES\r
+ HRLOI 0,377777\r
+ MOVEM 0,OLDNUM(FR) ;FORCE SETON1 TO RECALCULATE\r
+ POPJ PP,\r
+\f;CODE FOR GETTING TWO LINES\r
+;CALLING SEQUENCE IS:\r
+; PUSHJ PP,GETTWO\r
+; RETURN 1 IF EITHER FILE HAS NO MORE LINES\r
+; RETURN 2 IF ONE LINE READ FROM EACH FILE\r
+; C(GETFIL)=THE # OF FILE FOR WHICH A LINE WAS READ (OR -1 IF NONE)\r
+\r
+GETTWO: SETOM GETCNT ;INIT # LINESOBTAINDED\r
+ SETOM GETFIL ;INIT FILE # LINE CAME FROM\r
+ TRZ FR,-1 ;ZERO RIGHT HALF OF "FR"--SET FOR FIRST FILE\r
+ PUSHJ PP,GLINE ;GET A LINE FROM FIRST FILE\r
+ HRRI FR,1 ;NOW DO FOR SECOND FILE\r
+ PUSHJ PP,GLINE\r
+ SKIPLE GETCNT ;GETCNT .G. 0 IF TWO LINES WERE GOT\r
+ AOS (PP) ;SKIP IF 2 LINES WERE AVAILABLE\r
+ POPJ PP,\r
+\r
+GLINE: TLZ FR,20000\r
+ AOS W1,F1(FR) ;BUMP THE LINE POINTERS\r
+ CAMG W1,TOP(FR) ;HAVE WE GONE OVER THE TOP\r
+ JRST GLEXIT ;NO, LINE WAS AVAILABLE\r
+ SOS F1(FR) ;NOT CLEAR YET THAT A NEW LINE EXISTS\r
+GLINE1: HRLS PAGNUM(FR) ;SAVE PAGE # AT BEGINNING OF LINE\r
+ PUSHJ PP,GCHAR ;GET A CHARACTER\r
+ TLNE FR,@EOFTBL(FR) ;END OF FILE?\r
+ POPJ PP, ;YES, NO LINE\r
+ TLNN FR,ALLSW ;SKIP IF COMPARING BLANK LINES\r
+ JUMPE C,GLINE1 ;NULLS INDICATE BLANK LINES\r
+ AOS W1,F1(FR) ;THERE ARE CHARS FOR A NEW LINE\r
+ MOVEM W1,TOP(FR) ;THIS LINE IS THE TOP LINE\r
+ PUSHJ PP,SETONE ;CALCUATE BYTE POINTER\r
+ MOVE W1,1(FR) ;GET BYTE POINTER IN W1\r
+ MOVEM W1,WCADR ;SAVE ADR OF LINE WORD COUNT\r
+ MOVE W2,PAGNUM(FR) ;PICKUP PAGE # AT BEGINNING OF LINE\r
+ HLLZM W2,(W1) ;SAVE WITH THIS LINE\r
+ JRST GLINE3\r
+\f\r
+MLON ;MULTI LINE LITERAL\r
+\r
+GLINE2: PUSHJ PP,GCHAR ;GET NEXT CHAR FOR LINE\r
+GLINE3: TLNN W1,760000 ;WITH NEXT IDPB GO INTO NEXT WORD?\r
+ JRST [HRRZ W3,@GLTBL(FR);YES,GET HIGHEST ADR FOR THIS BUFFER\r
+ CAIG W3,3(W1) ;CHECK ADR. (LEAVE 1 WORD FOR WORD\r
+ ;COUNT FOR NEXT LINE PLUS 1 WORD\r
+ ;SLOP TO BE SAVE\r
+ JRST NOROOM ;NO ROOM IN THE INN\r
+ HLRZM C,1(W1) ;PUT BIT17 INTO BIT35 (FOR SEQUENCE #)\r
+ JRST .+1] ;GO INTO MAIN LOOP\r
+ IDPB C,W1 ;STORE CHARS IN LINE BUFFER\r
+ JUMPN C,GLINE2 ;NULL CHARACTER IS END OF LINE\r
+ MOVE W3,WCADR ;GET BACK ADR OF WORD COUNT\r
+ SUBI W1,-1(W3) ;CACLULATE WORD COUNT\r
+ HRRM W1,(W3) ;SAVE WORD COUNT IN BUFFER\r
+GLEXIT: AOS GETCNT ;INDEX # LINES FOUNT\r
+ HRRZM FR,GETFIL ;SAVE # OF THIS FILE\r
+ POPJ PP,\r
+\r
+GLTBL: LBUFP2 ;POINTS TO TOP ADR FILE 0\r
+ JOBREL ;POINTS TO TOP ADR FILE 1\r
+\f;IF A "CORE" UUO IS INSTALLED HERE, IT MUST ADJUST THE FOLLOWING\r
+;LIST OF LOCATIONS (ALL BY THE AMOUNT THE SECOND BUFFER AREA\r
+;IS MOVED, IF ANY):\r
+;1) BYTE POINTER ADDRESS IN: W1\r
+;2) BUFFER POINTER IN: LBUFP2\r
+;3) 1ST ADDRESS FOR LINE IN: 0(PP) ON PUSH DOWN LIST\r
+;THEN RETURN TO THE IDPB NEAR GLINE2+6\r
+\r
+\r
+NOROOM: PUSH PP,W1 ;SAVE BYTE POINTER\r
+ TRC FR,1 ;CHANGE 1 TO 0 (OR VICE VERSA)\r
+ MOVE W3,TOP(FR) ;GET TOP LINE # FOR "OTHER" FILE\r
+ ADDI W3,1 ;FIND 1ST ADR OF THE NEXT LINE ABOVE TOP\r
+ PUSHJ PP,SETON1 ;GET ADR\r
+ HRRZM T,HIGH ;SAVE 1ST FREE ADR OF NON-FULL FILE\r
+ HRRZ T,@GLTBL(FR);GET HIGHEST ADR AVAILABLE TO NON-FULL FILE\r
+ SUB T,HIGH ;GET SPACE AVAILABLE\r
+ SUBI T,2 ;LEAVE 1 WRD FOR NEXT LINE WORD COUNT\r
+ ;PLUS 1 WORD SLOP TO BE SAVE\r
+ TRC FR,1 ;CHANGE FILE # BACK TO THE WAY IT WAS\r
+ MOVEM T,ROOM ;SAVE ROOM AVAILABLE\r
+ CAIL T,^D400 ;COMPARE WITH 400. (NO MAGIC SIGNIFICANCE)\r
+ JRST NOR2 ;PLENTY ROOM AVAILABLE- DON'T GET MORE CORE\r
+\r
+ HRRZ T,JOBREL\r
+ MOVEM T,W1 ;SAVE THIS JOBREL AS "OLD" JOBREL\r
+ ADDI T,1 ;REQUEST CORE SIZE CONTAINING THIS ADDRESS\r
+NOR1: CALLI T,11 ;CORE UUO\r
+ SKIPA T,ROOM ;FAIL\r
+ JRST NOR4 ;SUCCESS\r
+NOR11: JUMPG T,NOR2+1 ;ANY CORE LEFT AT ALL?\r
+NORERR: JSP T,ERROUT ;NO, PRINT MESSAGE\r
+ ASCIZ /?BUFFER CAPACITY EXCEEDED AND NO CORE AVAILABLE/\r
+\f\r
+NOR4: HRRZ T,44 ;CORE UUO SUCCESFUL- GET "NEW" JOBREL\r
+ SUB T,W1 ;FIND OUT HOW MUCH WAS ADDED\r
+ ADDB T,ROOM ;UPDATE TOTAL ROOM AVAILABLE\r
+NOR3: TRNE FR,1 ;WHICH FILE NEEDS ROOM?\r
+ JRST NOR98 ;FILE #1, IT JUST GOT IT\r
+ ;FILE #0, SHUFFLE CORE\r
+NOR2: ASH T,-1 ;DIVIDE AVAILABLE SPACE BETWEEN FILES\r
+ MOVEM T,ROOM ;FILE #1 GETS MOVED THIS AMOUNT\r
+ TRNN FR,1 ;WHICH FILE NEEDED ROOOM?\r
+ JRST NOR7 ;FILE #0. MOVE #1 TOWARD 777777\r
+ ;FILE #1. MOVE #1 TOWARD 0\r
+NOR6: MOVNS T,ROOM ;FIOLE IS MOVING IN NEGATIVE DIRECTION\r
+ ADDM T,WCADR ;WORD COUNT ADR FOR FILE# 1 IS MOVED DOWN\r
+ ADDM T,(PP) ;SAME WITH BYTE POINTER\r
+ MOVE W1,(PP) ;GET LAST ADR TO MOVE FROM BYTE POINTER\r
+ ADD T,LBUFP2 ;GET "TO" ADR. [(LBUFP2)-D OF M]\r
+ HRL T,LBUFP2 ;GET "FROM" ADR\r
+ BLT T,(W1) ;BLT T,"E" (T/ XWD "FROM","TO")\r
+ JRST NOR90\r
+\r
+NOR7: MOVE W1,T ;GET D OF M\r
+ HRLI W1,(POP T,(T)) ;SETUP- POP T,<D OF M>(T) INTO W1\r
+ MOVE W2,HIGH ;GET HIGH(+1) ADR OF FILE #1\r
+ SUB W2,LBUFP2 ;GET LENGTH OF FILE #1\r
+ SOS T,HIGH ;GET LAST ADR IN FILE #1\r
+ HRLI T,400000(W2);PUT WORD COUNT(+400000) IN LEFT HALF\r
+ ;400000 AVOIDS PDL OVERFLOW PROBLEM IN AC LOOP\r
+ MOVE W3,[JRST NOR90]\r
+ MOVE W2,.+1\r
+ JUMPL T,W1 ;W1/ POP T,<DISTANCE OF MOVE>(T)\r
+ ;W2/ JUMPL T,W1\r
+ ;W3/ JRST NOR90\r
+;THE ABOVE INSTRUCTIONS ARE A REVERSE BLT AND ARE IN THE AC'S FOR SPEED\r
+\r
+NOR90: MOVE T,ROOM ;GET DISTANCE FILE #1 WAS MOVED\r
+ ADDM T,LBUFP2 ;MODIFY STARTING ADR OF FILE #1\r
+ HRLOI 0,377777\r
+ MOVEM 0,OLDNUM+1 ;FORCE "SETONE" TO RECALCULATE BYTE POINTER\r
+NOR98: POP PP,1\r
+NOR99: JRST GLINE3 ;CHECK COMPUTATIONS ON RETURNING\r
+\r
+\f;THIS PAGE CONTAINS ROUTINE FOR COMPARING TWO LINES\r
+;IT HAS TWO RETURNS--CALLING ADR.+1 IF LINES MATCH OR\r
+;CALLING ADR+2 IF NO MATCH\r
+\r
+COMPL: PUSHJ PP,SETP ;CALCULATE POINTER TO TEXT\r
+ MOVEM W1,P1 ;P1=TEMP POINTER TO TEXT FOR FIRST FILE\r
+ MOVEM W2,P2 ;P2 FOR SECOND FILE\r
+\r
+ MOVEI W3,1\r
+ TDNN W3,1(W1) ;TEST SEQUENCE # BIT\r
+ JRST .+3 ;NOT SEQ. #\r
+ AOS P1 ;SKIP OVER SEQ. # AND\r
+ IBP P1 ;THE TAB\r
+ TDNN W3,1(W2) ;SAME THING FOR FILE #2\r
+ JRST .+3\r
+ AOS P2\r
+ IBP P2\r
+\r
+COMPL1: ILDB W1,P1 ;GET A CHARACTER FROM LINE FROM FIRST FILE\r
+COMPL2: ILDB W2,P2 ;AND ONE FROM SECOND FILE\r
+ CAME W1,2 ;THIS IS THE BIG TEST--ARE THEY EQUAL\r
+ JRST COMPL4 ;NO\r
+COMPL7: CAIN W1,";" ;YES, COMMENT?\r
+ TLNN FR,CSWBIT ;YES, SUPPRESS COMMENTS?\r
+ JUMPN W1,COMPL1 ;NO,NO. TEST FOR END OF LINE\r
+ POPJ PP, ;LINES MATCH, RETURN\r
+\r
+COMPL3: ILDB W1,P1 ;GET NEW CHAR FOR FILE 1\r
+COMPL4: CAIE W1,40 ;SPACE?\r
+ CAIN W1,TAB ;OR TAB?\r
+ TLNN FR,SSWBIT ;AND IS SPACING BEING IGNORED?\r
+ SKIPA ;NO\r
+ JRST COMPL3 ;FLUSH SPACE OR TAB FOR FILE 1\r
+\r
+ CAIE W2,40 ;SPACE?\r
+ CAIN W2,TAB ;OR TAB?\r
+ TLNN FR,SSWBIT ;AND IS SPACING BEING IGNORED?\r
+ SKIPA ;NO\r
+ JRST COMPL2 ;YES, FLUSH A SPACE OR TAB FOR FILE 2\r
+\r
+ CAMN W1,W2 ;ARE THE CHARACTERS NOW THE SAME?\r
+ JRST COMPL7 ;YES, TEST FOR END OF LINES\r
+\r
+ CAIE W1,";" ;COMMENT IN FILE 1?\r
+ CAIN W2,";" ;OR IN FILE 2?\r
+ TLNN FR,CSWBIT ;AND ARE COMMENTS BEING IGNORED?\r
+ JRST CPOPJ1 ;NO, FILES DON'T MATCH, SKIP RETURN\r
+ JUMPE W1,CPOPJ ;YES, OTHER CHAR MUST BE NULL OR ELSE ON\r
+ JUMPE W2,CPOPJ ; LINE IS LONGER THAN OTHER AND FILES DIFFER\r
+CPOPJ1: AOS (PP)\r
+CPOPJ: POPJ PP,\r
+\f;WHEN WE GET TO THIS POINT WE HAVE FOUND\r
+;THE EXTENT OF THE DIFFERENCES AND WE ARE READY TO PRINT\r
+;THESE DIFFERENCES OUT\r
+\r
+PNTBTH: TRZ FR,-1 ;OUTPUT FILE 1\r
+ PUSHJ PP,PNTTXT ;PRINT FILE 1 DIFFERENCES\r
+ MOVE W1,[POINT 7,[ASCIZ /****/]]\r
+ PUSHJ PP,PRINT\r
+ PUSHJ PP,PCRLF\r
+ HRRI FR,1 ;THEN PRINT FILE 2 DIFFERNCES\r
+\r
+;THIS SUBROUTINE PRINTS ALL THE TEXT IN THE\r
+;BUFFER SPECIFIED BY C(FR)R. I. E. FILE 1 OR FILE 2\r
+\r
+PNTTXT: SETOM TEMP ;START POINTER AT -1\r
+ SETOM PAGEN ;GUARANTEE PAGE # MISMATCH- THERFORE PRINT IT\r
+PNTTX1: AOS W1,TEMP ;INDEX LINE COUNTER\r
+ CAMLE W1,F1(FR) ;PRINTED ALL LINES?\r
+ POPJ PP, ;YES, RETURN\r
+ AOS ERRCNT ;MAKE ERRCNT NON-ZERO\r
+ PUSH PP,F1 ;NO, SAVE LINE POINTERS\r
+ PUSH PP,F2\r
+ SETZB F1,F2 ;F1=F2=0\r
+ MOVEM W1,F1(FR) ;SET UP EITHER FOR F1 OR F2\r
+ PUSHJ PP,SETONE ;CALCULATE BYTE POINTERS TO TEXT\r
+ MOVE W1,W1(FR) ;UNNECESSARY FOR FILE 1- MOVES BYTE PNT FILE 2\r
+ PUSHJ PP,PLINEN ;PRINT: 1) TEXT\r
+ TLNN FR,ALLSW\r
+ PUSHJ PP,PCRLF\r
+ POP PP,F2\r
+ POP PP,F1 ;RESTORE REGS\r
+ JRST PNTTX1 ;FINISH OUT ALL LINES\r
+\r
+\f;THE FOLLOWING CODE IS USED TO OUTPUT A LINE OF TEXT\r
+PLINEN: MOVEI C,"1"(FR)\r
+ PUSHJ PP,PCHART ;PRINT 1 OR 2\r
+ MOVEI C,")"\r
+ PUSHJ PP,PCHART ;PRINT )\r
+ HLRZ C,(W1) ;GET PAGE NUMBER OF THIS LINE\r
+ CAME C,PAGEN ;IS IT THE SAME AS PREVIOUS LINE?\r
+ PUSHJ PP,PGNUM ;PRINT NEW PAGE NUMBER\r
+ MOVEI C,TAB ;PRINT TAB\r
+ PUSHJ PP,PCHART\r
+\r
+PRINT: ILDB C,W1 ;GET CHARACTER\r
+ JUMPN C,.-2 ;LOOP UNTIL A NULL SHOWS UP\r
+ POPJ PP,\r
+\r
+\r
+PCRLF: ;THIS CODE OUTPUTS A CARRAIGE RETURN-LINE\r
+ ;FEED AND DECREMENTS THE LINE COUNT\r
+\r
+ PUSHJ PP,CRLF \r
+ SETZM COLCNT\r
+ TLNE FR,40000\r
+ POPJ PP,\r
+ SOSN LINCNT ;DECREMENT THE LINES/PAGE COUNT\r
+ TLO FR,PAGSW ;THIS MEAN WE GET A NEW HEADING\r
+ POPJ PP,\r
+\r
+PGNUM: MOVEM C,PAGEN ;SAVE NEW PAGE # AS OLD\r
+PGNUM1: IDIVI C,12 ;STANDARD DECIMAL PRINT ROUTINE\r
+ HRLM T,(PP)\r
+ SKIPE C\r
+ PUSHJ PP,PGNUM1\r
+ HLRZ C,(PP)\r
+ ADDI C,"0"\r
+ JRST PCHART\r
+\f;THIS PAGE CONTAINS ROUTINES FOR CHARACTER OUTPUT\r
+\r
+;CHARACTERS OUTPUTED AS A STRING OF TEXT COME THROUGH HERE\r
+\r
+PCHART: JUMPE C,CPOPJ ;ZERO MEANS A CARRIAGE RETURN\r
+ ;IF SO WE ARE THROUGH WITH LINE\r
+ AOS T,COLCNT\r
+ CAIGE C," " ;A PRINTING CHAR?\r
+ JRST PCHAR2\r
+PCHAR0: TLNE FR,40000\r
+ CAMG T,CCNT\r
+ JRST PCHAR\r
+ POPJ PP,\r
+PCHAR2: SKIPG CCNT\r
+ POPJ PP,\r
+ CAIE C,TAB ;OR A TAB?\r
+ JRST .+4\r
+ IORI T,7\r
+ MOVEM T,COLCNT\r
+ JRST PCHAR0\r
+ CAIE C,CR\r
+ JRST .+3\r
+ SETZM COLCNT\r
+ JRST PCHAR\r
+ CAIE C,LF\r
+ JRST .+3\r
+ SOS COLCNT\r
+ JRST PCHAR ;YES\r
+ MOVSI C,100(C) ;NO, CONTROL CHAR --SAVE\r
+ HRRI C,"^" ;THIS IS CONTROL SYMBOL\r
+ PUSHJ PP,PCHAR ;OUTPUT THE "^"\r
+ MOVSS C ;AND NOW FOR THE LETTER\r
+PCHAR: TLZN FR,PAGSW ;DO WE NEED A NEW HEADING\r
+ JRST TYO ;NO--SIMPLE CHARACTER OUTPUT\r
+ SETOM LINCNT ;YES\r
+;THIS CODE OUTPUTS A HEADING COMPRISES OF THE TITLE OF\r
+;EACH FILE AFTER "FILE 1)" AND "FILE 2)"\r
+\r
+ MOVEM 16,SAVEXS+16 ;SAVE ACCUMULATORS WHILE OUTPUTING HEADING\r
+ MOVEI 16,SAVEXS\r
+ BLT 16,SAVEXS+15 ;ACCUMULATORS ARE NOW SAVED\r
+ TLNE FR,ENDSW ;DON'T BOTHER IF NO ERRORS DETECTED\r
+ JRST PCHAR1\r
+ MOVEI C,FF ;FOR NEW PAGE, ISSUE FORM FEED\r
+ TLNN FR,NOFORM ;IF 1, SUPPRESS FORM FEED\r
+ PUSHJ PP,TYO\r
+ MOVE W1,[POINT 7,[ASCIZ /FILE 1) /]]\r
+ PUSHJ PP,PRINT\r
+ MOVE W1,[POINT 7,HBUF1]\r
+ PUSHJ PP,PRINT ;PRINT FILE 1 NAME\r
+ PUSHJ PP,PCRLF\r
+ MOVE W1,[POINT 7,[ASCIZ /FILE 2) /]]\r
+ PUSHJ PP,PRINT\r
+ MOVE W1,[POINT 7,HBUF2]\r
+ PUSHJ PP,PRINT ;PRINT FILE 2 NAME\r
+PCHAR1: PUSHJ PP,PCRLF ;FOLLOWED BY TWO CARRIAGE RETURNS FINE FEEDS\r
+ PUSHJ PP,PCRLF\r
+ MOVEI LPP ;RESET LINES/PAGE COUNT\r
+ MOVEM LINCNT\r
+ MOVSI 16,SAVEXS ;AND RESTORE ACS\r
+ BLT 16,15\r
+ MOVE 16,SAVEXS+16\r
+ TLZ FR,NOFORM ;CLEAR SUPPRESS FF FLAG AFTER RESTORING AC'S\r
+ JRST TYO ;DON'T FORGET ABOUT THAT ORIGINAL CHARACTER\r
+\r
+\f;THE CODE ON THIS PAGE IS FOR HANDLING INPUT ERRORS\r
+;THERE ARE TWO TYPES OF ERRORS--EITHER THE FILE IS NOT FOUND\r
+;OR THE DEVICE IS NOT AVAILABLE--THE FORMAT FOR THESE MESSAGES\r
+;IS THE SAME FORMAT USED FOR THE "TECO" MESSAGES.\r
+\r
+\r
+ERRIA: MOVEI T,[ASCIZ /?INPUT ERROR- /]\r
+ PUSHJ PP,TYPMSG ;TYPE FIRST PART OF MESSAGE\r
+ MOVE T,INDIR1 ;GET FILE NAME\r
+ PUSHJ PP,PNTSIX ;PRINT\r
+ HLLZS T,INDIR1+1 ;GET EXTENSION FREED FROM GARBAGE\r
+ JUMPE T,NOEXT ;ANY EXTENSION?\r
+ MOVEI C,"." ;YES, TYPE DOT\r
+ PUSHJ PP,TYO\r
+ MOVE T,INDIR1+1 ;GET EXTENION\r
+ PUSHJ PP,PNTSIX ;PRINT\r
+NOEXT: MOVEI T,[ASCIZ / FILE NOT FOUND/] ;FINISH MESSAGE\r
+ PUSHJ PP,TYPMS2\r
+ JRST CARR ;THIS WILL OUTPUT TWO C.R. AND EXIT\r
+\r
+\r
+ERRA: MOVE T,OUTDEV ;OUTPUT INIT FAIL\r
+ MOVEM T,INDEV1\r
+\r
+ERRI: MOVEI T,[ASCIZ /?DEVICE /]\r
+ PUSHJ PP,TYPMSG ;TYPE BEGINING OF MESSAGE\r
+ MOVE T,INDEV1\r
+ PUSHJ PP,PNTSIX\r
+ MOVEI T,[ASCIZ /: NOT AVAILABLE/]\r
+ PUSHJ PP,TYPMS2 ;TYPE REST OF MESSAGE\r
+ JRST CARR ;INSERT CARRIAGE RETURNS AND EXIT\r
+\r
+PNTSIX: MOVE TT,[POINT 6,T] ;INIT SIXBIT BYTE POINTER\r
+PNTS1: TLNN TT,770000 ;FINISHED WITH WORD?\r
+ POPJ PP, ;YES\r
+ ILDB C,TT ;NO, GET CHARACTER\r
+ JUMPE C,PNTS1 ;FLUSH SPACES\r
+ ADDI C,40 ;CHANGE TO ASCII\r
+ PUSHJ PP,TYO\r
+ JRST PNTS1\r
+\fCRLF: MOVEI C,CR ;OUTPUT A CARRIAGE RETURN-LINE FEED\r
+ PUSHJ PP,TYO\r
+ MOVEI C,LF ;NOW THE LINE FEED\r
+\r
+TYO: SOSG CTOBUF+2 ;DECREMENT BUFFER COUNT\r
+ PUSHJ PP,DMPOUT ;BUFFER WAS FULL\r
+ IDPB C,CTOBUF+1 ;DEPOSIT CHAR.\r
+ CAIN C,LF ;LINE FEED?\r
+ TLNN FR,IOTTY ;WHILE DOING 1 OUTPUT PER LINE\r
+ POPJ PP, ;NO\r
+DMPOUT: OUT CTL, ;YES, OUTPUT BUFFER\r
+ POPJ PP, ;OK\r
+ JSP T,ERROUT\r
+ ASCIZ /?OUTPUT DEVICE ERROR/\r
+\r
+ERRO: JSP T,ERROUT\r
+ ASCIZ /?OUTPUT INITIALIZATION ERROR/\r
+ERRCOR: MOVEI T,[ASCIZ /?2K CORE NEEDED AND NOT AVAILABLE/]\r
+ PUSHJ PP,TYPMSG\r
+ CALLI 12 ;PRINT MESSAGE AND EXIT\r
+\r
+ERROUT: PUSHJ PP,TYPMSG ;OUTPUT ERROR\r
+ JRST CARR ;THROW IN TWO CR AND TRY AGAIN\r
+\r
+FILEO: SOSG OUTBUF+2\r
+ PUSHJ PP,DMPFIL\r
+ IDPB C,OUTBUF+1\r
+ POPJ PP,\r
+DMPFIL: OUT 3,\r
+ POPJ PP,\r
+ JSP T,ERROUT\r
+ ASCIZ /?MERGE OUTPUT FILE WRITE ERROR/\r
+DMP2: MOVEM W1,CCNT\r
+DMP3: MOVEI C,52\r
+ PUSHJ PP,TYO\r
+ PUSHJ PP,DMPOUT\r
+ MOVE W1,[POINT 7,MPP1]\r
+DMPFL1: MOVEI C,0\r
+ CAIE W1,[POINT 7,MPP2,7]\r
+ PUSHJ PP,TTYIN\r
+ CAIGE C,40\r
+ MOVEI C,0\r
+ IDPB C,1\r
+ CAIE C,61\r
+ CAIN C,62\r
+ JRST DMPFL1\r
+ CAIN C,124\r
+ JRST DMPFL1\r
+ CAIE C,103\r
+ JRST SAVP\r
+\r
+GETDEC: MOVEI W1,0\r
+ PUSHJ PP,TTYIN\r
+ CAIGE C,40\r
+ JRST DMP2\r
+ CAIL C,"0"\r
+ CAILE C,"9"\r
+ JRST ERRD\r
+ IMULI W1,^D10\r
+ ADDI W1,-"0"(C)\r
+ JRST GETDEC+1\r
+\r
+SAVP: MOVE W1,[POINT 7,MPP1]\r
+ MOVEM W1,MPPX\r
+ JUMPE C,CPOPJ\r
+ERRD: MOVE W1,[POINT 7,[ASCIZ Z?ONLY 1, 2, AND/OR T ARE LEGAL IN MERGE COMMANDS\r
+OR C### TO SET MAX. COL.\r
+Z]]\r
+ PUSHJ PP,PRINT\r
+ JRST DMP3\r
+GETC: ILDB C,MPPX\r
+ POPJ PP,\r
+\f;ROUTINES FOR OUTPUTING ERROR MESSAGES\r
+\r
+TYPMSG: PUSHJ PP,INITTY ;INITALIZE TTY\r
+ PUSHJ PP,CRLF ;OUTPUT A CARRIAGE RETURN\r
+TYPMS2: HRLI T,(POINT 7,,) ;THIS IS POINTER FOR ERROR MESSAGE\r
+ SKIPA \r
+ PUSHJ PP,TYO\r
+TYPMS1: ILDB C,T ;LOAD A CHAR. FROM ERROR MESSAGE\r
+ JUMPN C,.-2 ;ALL ERROR MESSAGES END WITH A ZERO\r
+ POPJ PP, ;THROUGH WITH ERROR MESSAGE\r
+\r
+CARR: PUSHJ PP,CRLF ;COMMON EXIT FOR ERROR MESSAGES\r
+CARR1: PUSHJ PP,CRLF\r
+\r
+ CLOSE CTL,\r
+ RELEASE CTL,\r
+ RELEASE IN1,\r
+ RELEASE IN2,\r
+ RELEASE OUT,\r
+ JRST COMPGO\r
+\r
+;INITIALIZE TTY FOR ERROR MESSAGES\r
+INITTY: CLOSE CTL,\r
+ RELEASE CTL,\r
+ INIT CTL,1\r
+ SIXBIT /TTY/\r
+ XWD CTOBUF,CTIBUF\r
+ HALT\r
+ INBUF CTL,1\r
+ OUTBUF CTL,1\r
+ POPJ PP,\r
+\r
+GCHAR0: TLNE FR,ALLSW\r
+ POPJ PP,\r
+GCHAR: TLZN FR,20000\r
+ TLNE FR,@EOFTBL(FR) ;EOF SEEN?\r
+ JRST NULL ;YES, RETURN NULL\r
+ SOSG @CNTTBL(FR) ;DECREMENT BUFFER COUNT\r
+ JSP C,@[EXP GCHAR1,GCHAR2](FR) ;BUFFER EMPTY- DO "INPUT"\r
+ SKIPN @CNTTBL(FR) ;DID WE GET ANY DATA\r
+ JRST GCHAR ;NO\r
+ ILDB C,@BYTTBL(FR) ;YES, GET A CHARACTER\r
+ JUMPE C,GCHAR ;GET RID OF NULLS\r
+ CAIE C,LF ;LINE FEED?\r
+ CAIN C,VT ;NO-VERTICAL TAB?\r
+ JRST FORM+1 ;YES, RETURN NULL\r
+ CAIN C,CR ;CARRIAGE RETURN?\r
+ JRST GCHAR0 ;YES FLUSH\r
+ CAIN C,FF ;IS IT A FORM FEED?\r
+ JRST FORM ;YES\r
+ HRL C,@SEQTBL(FR) ;GET SEQUENCE # BIT (IF IT EXISTS)\r
+ TLZ C,777776 ;TURN OFF ALL BUT SEQ. # BIT\r
+ POPJ PP, ;NO, RETURN WITH CHAR\r
+\r
+FORM: AOS PAGNUM(FR) ;INDEX PAGE NUMBER\r
+ TLO FR,20000\r
+ TLNE FR,ALLSW\r
+ POPJ PP,\r
+ JRST NULL\r
+\r
+EOF: TLO FR,@EOFTBL(FR) ;SET EOF FLAG\r
+NULL: MOVEI C,0 ;EOF IS A NULL\r
+ POPJ PP,\r
+\r
+GCHAR1: INPUT IN1, ;INPUT FOR FILE 1\r
+ STATO IN1,762000 ;ERRORS OR END OF FILE?\r
+ JRST (C) ;NO\r
+ STATO IN1,742000 ;YES, EOF?\r
+ JRST EOF ;YES END OF FILE\r
+ JSP T,ERROUT\r
+ ASCIZ /?FILE 1 READ ERROR/\r
+\r
+GCHAR2: INPUT IN2,\r
+ STATO IN2,762000\r
+ JRST (C)\r
+ STATO IN2,742000\r
+ JRST EOF\r
+ JSP T,ERROUT\r
+ ASCIZ /?FILE 2 READ ERROR/\r
+\r
+SEQTBL: Z @INBUF1+1 ;POINTS TO ADR OF LAST CHAR FILE #0\r
+ Z @INBUF2+1 ;DITTO FILE #1\r
+\r
+BYTTBL: INBUF1+1 ;ADR OF BYTE POINTER FILE #0\r
+ INBUF2+1 ;DITTO FILE #1\r
+\r
+EOFTBL: EOF1SW ;EOF FLAG FOR FILE 1\r
+ EOF2SW ;EOF FLAG FOR FILE 2\r
+\r
+CNTTBL: INBUF1+2 ;POINTS TO FILE 1 CHAR COUNT\r
+ INBUF2+2 ;DITTO FILE 2\r
+\fNAME1: SETZB ACDEV,ACDEL ;ZERO REGISTERS WHICH WILL RETURN THE NAMES\r
+ SETZB ACFILE,ACEXT\r
+ TLZ FR,CTYPF ;CLEAR COMMAND TYPED FLAG\r
+\r
+NAME3: MOVSI ACPNTR,(POINT 6,0) ;SET POINTER\r
+ SETZB TT,0 ;THE SIXBIT NAME WILL BE STORED IN THE AC0\r
+\r
+GETIOC: PUSHJ PP,TTYIN ;GET INPUT CHARACTER\r
+ CAIE C,32 ;AND EOF TERMINATES A FILE NAME\r
+ CAIG C,CR ;THIS IS ANOTHER WAY TO GET A FILE NAME\r
+ JRST TERM ;CATCHES CR,LF,FF,VT\r
+ CAIN C,33 ;ALT MODE?\r
+ JRST TERM ;YES\r
+ CAIE C,"_" ;ONE KIND OF SEPERATOR\r
+ CAIN C,"," ;THIS ALSO MANES WE HAVE FINISHED A TERM\r
+ JRST TERM ;TERM HAS BEEN READ\r
+ CAIN C,"/" ;IS THERE A SWITCH?\r
+ JRST GETSW ;YES\r
+ TLO FR,CTYPF ;SET COMMAND TYPED FLAG\r
+ CAIN C,":" ;HAVE WE BEEN GETTING A DEVICE NAME\r
+ JRST DEVICE ;YES\r
+ CAIN C,"." ;OR A FILE NAME\r
+ JRST NAME ;YES\r
+ TRC C,40 ;CONVERT TO SIXBIT\r
+ TLNE ACPNTR,770000 ;HAVE WE STORED SIX BYTES?\r
+ IDPB C,ACPNTR ;NO\r
+ JRST GETIOC ;GET ANOTHER CHAR.\r
+\r
+TTYIN: PUSHJ PP,TTYIN1 \r
+ CAIL C,140\r
+ TRZ C,40 ;CHANGE LOWER CASE TO UPPER CASE\r
+ CAIE C," " ;SKIP BLANKS\r
+ CAIN C,TAB ;AND TABS\r
+ JRST TTYIN\r
+ CAIN C,CR\r
+ JRST TTYIN\r
+ POPJ PP,\r
+TTYIN1: SOSG CTIBUF+2 ;DECREMENT CHARACTER COUNT, ANY LEFT?\r
+ INPUT CTL, ;NO, GET A BUFFER FULL\r
+ ILDB C,CTIBUF+1 ;GET CHARACTER\r
+ JUMPE C,TTYIN1 ;FLUSH NULLS\r
+ CAIE C,176\r
+ CAIN C,175\r
+ MOVEI C,33 ;CHANGE ALL ALT MODES TO NEW\r
+ POPJ PP,\r
+\fDEVICE: SKIPA ACDEV,0 ;DEVICE NAME\r
+NAME: MOVE ACFILE,0 ;FILE NAME\r
+ MOVE ACDEL,C ;SET DELIMITER\r
+ JRST NAME3 ;GET NEXT SYMBOL\r
+\r
+TERM: JUMPE ACDEL,.+3 ;IF NO PREVIOUS DELIMITOR, OR\r
+ CAIE ACDEL,":" ;IF PREVIOUS DELIMITER\r
+ JRST TERM1\r
+ MOVE ACFILE,0 ;SET FILE\r
+TERM1: CAIE ACDEL,"." ;IF PERIOD,\r
+ POPJ PP,\r
+ HLLZ ACEXT,0 ;SET EXTENSION\r
+ POPJ PP, ;EXIT\r
+\r
+GETSW: PUSHJ PP,TTYIN ;A SWITCH HAS BEEN DETECTED\r
+ MOVSI T,SWTBL-SWTBLE ;SET UP NEG. COUNT FOR TABLE SEARCH\r
+ CAIE C,@SWTBL(T) ;FOUND CHAR? (INDIRECT=INDEX=0\r
+ AOBJN T,.-1\r
+ JUMPGE T,GETSW1 ;JUMP IF NOTHING FOUND\r
+ TDO FR,SWTBL(T) ;TURN ON FLAG (GARBAGE IN RIGHT)\r
+ JRST GETIOC ;GET NEXT PART OF COMMAND\r
+\r
+GETSW1: MOVEI C,-"1"(C) ;CHANGE CHAR TO NUMBER\r
+ CAILE C,10\r
+ JRST CTLSER ;ERROR IF CHARACTER ISN'T 1-9\r
+ MOVEM C,NUMLIN ;SAVE AS # EXTRA LINES TO MATCH (AFTER 1ST)\r
+ JRST GETIOC\r
+\r
+SWTBL: XWD SSWBIT,"S"\r
+ XWD CSWBIT+SSWBIT,"C"\r
+ XWD ALLSW,"B"\r
+ XWD 40000+IOTTY+ALLSW,"M"\r
+SWTBLE: ;END OF TABLE\r
+\r
+OPN1: INIT IN1,1\r
+ INBUF1\r
+ JRST ERRA\r
+ JRST ERRI\r
+ JRST CTLSE3\r
+OPN2: INIT IN2,1\r
+ INBUF2\r
+ JRST ERR2A\r
+ JRST CTLSE4\r
+ LIT\r
+IFN PURE,<LOC 140> ;IMPURE AREA\r
+CCNT: BLOCK 1\r
+OUTDEV: BLOCK 1\r
+PPSET: BLOCK LPDL ;PUSH DOWN LIST STORAGE\r
+\r
+CTIBUF: BLOCK 3\r
+CTOBUF: BLOCK 3\r
+INBUF1: BLOCK 3\r
+INBUF2: BLOCK 3\r
+OUTBUF: BLOCK 3\r
+ERRCNT: BLOCK 1 ;DIFFERENCES COUNTER (0 MEANS NO DIFFERENCES)\r
+\r
+INDEV1: BLOCK 1\r
+\r
+INDIR1: BLOCK 4\r
+\r
+OUTDIR: BLOCK 4\r
+\r
+TOP: ;CONTAINS # LINES ACTUALLY STORED IN BUFFER FOR:\r
+TOP1: BLOCK 1 ;FILE #1\r
+TOP2: BLOCK 1 ;FILE #2\r
+\r
+LBUFP:\r
+LBUFP1: BLOCK 1 ;POINTER TO BEGINNING OF LINE STORAGE FOR FILE #1\r
+LBUFP2: BLOCK 1 ;DITTO FILE #2\r
+\r
+P1: BLOCK 1 ;BYTE POINTERS USED BY "COMPL" SUBROUTINE\r
+P2: BLOCK 1\r
+\r
+HBUF1: BLOCK WPL ;HOLDS HEADER FOR FIRST FILE\r
+HBUF2: BLOCK WPL ;FOR SECOND FILE\r
+PAGNUM: BLOCK 2 ;PAGE NUMBERS FOR THE TWO FILES\r
+ ; LH(# AT BEGIN OF LINE), RH(# AFTER LAST CHAR)\r
+PAGEN: BLOCK 1 ;TEMPORARY FOR PAGE #'S IN PLINEN SUBROUTINE\r
+OLDNUM: BLOCK 2 ;LAST LINE # USED IN "SETONE"\r
+OLDPNT: BLOCK 2 ;LAST BYTE POINTER CALCULATED BY "SETONE"\r
+MPP: BLOCK 2 \r
+MPP1: BLOCK 1 \r
+MPP2: BLOCK 1 \r
+ BLOCK 1 \r
+MPPX: BLOCK 1 \r
+SAVEXS: BLOCK 17 ;STORAGE FOR AC'S WHEN PRINTING PAGE HEADERS\r
+\r
+TEMP: BLOCK 1\r
+LINCNT: BLOCK 1\r
+COLCNT: BLOCK 1\r
+RTNTMP: BLOCK 1 ;RETURN ADDRESS FOR "MULTI" SUBROUTINE\r
+WCADR: BLOCK 1 ;TEMP IN GLINE SUBROUTINE\r
+HIGH: BLOCK 1 ;USED BY NOROOM\r
+ROOM: BLOCK 1 ;USED BY "NOROOM"\r
+GETCNT: BLOCK 1 ;# LINES (-1) "GETTWO" GOT\r
+GETFIL: BLOCK 1 ;# OF FILE FROM WHICH "GETTWO" GOT LINE (.L. 0 IF NONE)\r
+NUMLIN: BLOCK 1 ;# LINES FOR A MATCH\r
+NUMTMP: BLOCK 1 ;TEMP FOR NUMLIN\r
+TEMPF1: BLOCK 1 ;TEMP FOR F1\r
+TEMPF2: BLOCK 1 ;TEMP FOR F2\r
+\r
+ENDP:\r
+\r
+END COMPGO\r
+\r