Google
 

Trailing-Edge - PDP-10 Archives - bb-bt99e-bb - merge.mac
There are 10 other files named merge.mac in the archive. Click here to see a list.
	TITLE	MERGE MODULE FOR SOUPR
	SUBTTL	DEFINITIONS
;HANLEY A. STRAPPMAN
	SEARCH	PRS,JOBDAT,UUOSYM
	SALL
	TWOSEG
	EXTERN	PUTC,SIXI,DECO,CRLFO,LKP,NTR,WLDMAT,SWTCH,INDIR
	EXTERN	DECI,EATS,EATCR,SPCI,PROMPT,PUR
	EXTERN	STRO,BP,ICH,OCH,LSNI,CI,FNDNAM
	EXTERN	CPOPJ1,CPOPJ,RST,WILDP,WILDER,EATEOL
	EXTERN	SAVE1,SAVE2,SAVE3,GETBLK,LSTI,SPCO,CO,OCLS,ICLS
	EXTERN	WLDCNT,COLON,IREN,SLKP,SWINI

;DEFINE AC'S
	F=0				;FLAGS
	CH=12				;CH NUMBER
	A1=13				;ADR PREVIOUS BLK
	A2=A1+1				;ADR CURRENT BLK

;FLAGS
	F.LOG==1			;LOG FILE NAMES
	F.YN==2				;1=INCLUDE
	F.UNC==4			;1=UNCLUDE
	F.XID==10			;EXCLUDE IDENTICAL EDITS

;ASSEMBLY PARAMETERS
	PDLSIZ==100			;SIZE OF PDL
	IFNDEF	LINSIZ,<LINSIZ==^D640/5>;SIZE OF COMMAND LINE
	IFNDEF	CHAN,<CHAN==10>		;COR FILES MERGED AT ONCE
	IFNDEF	FLAGS,<FLAGS==F.LOG+F.UNC+F.XID>;DEFAULT FLAGS
	IFNDEF	CLSNM,<CLSNM==0>	;DEFAULT CLOSENESS FACTOR

;CH USAGE
					;0 TO CHAN-1 INPUT
	O==CHAN				;OUTPUT

;ADDITIONS TO SPEC BLOCK
	.SBNCL==SPCSIZ			;ADR OF /INCLUDE CHAIN
	.SBXCL==.SBNCL+1		;ADR OF /EXCLUDE CHAIN
	MYSIZ==SPCSIZ+2			;TOTAL SIZE
	SUBTTL	EDIT HISTORY

	VEDIT==1	;COMPLETE VMAJOR=2 AUG 77
	VEDIT==2	;SUPPORT LINE SEQUENCE NUMBERS 9-17-77
	VEDIT==3	;ADD /UNCLUD/UXCLUD 9-17-77
	VEDIT==4	;FIX BUG CREATED BY /UNCLUD 10-10-77
	VEDIT==5	;CHANGE SYMBOL NAMES TO FOLLOW CONVENTION 10-14-77
	VEDIT==6	;ADD ERROR RETURN TO OCLS 10-15-77
	VEDIT==7	;CHANGE FROM WILD TO WILDER 10-15-77
	VEDIT==10	;WILDCARDS NOT EXPANDED FOR OUTPUT FILE 1-24-81
	VEDIT==11	;EXCLUDE IDENTICAL EDITS 9-14-81
	VEDIT==12	;INDIRECT FILES
	VEDIT==13	;TYPE OUT HOW MANY CONFLICTS 11-30-82
	VEDIT==14	;SWITCH.INI 6-18-83

	VWHO==0
	VMAJOR==2
	VMINOR==0
	LOC	.JBVER
	BYTE	(3)VWHO(9)VMAJOR(6)VMINOR(18)VEDIT
	SUBTTL	INITIALIZATION
	RELOC	400000

MERGE:	JFCL				;NO CCL
	MOVE	P,[IOWD PDLSIZ,PDL]	;SETUP PDL
	PUSHJ	P,RST			;RESET
	MOVEI	T1,CLSNM		;DEFAULT CLOSENESS
	MOVEM	T1,CLSNUM
	MOVEI	F,FLAGS			;DEFAULT FLAGS
	MOVE	P2,[XWD -SWIL,SWN]	;READ SWITCH.INI 
	MOVEI	P3,SWX
	PUSHJ	P,SWINI
	 JFCL
	MOVEM	F,SAVFLG		;SAVE FLAGS
	MOVE	T1,CLSNUM		;SAVE CLOSENESS
	MOVEM	T1,SAVCLS
COMMAN:	PUSHJ	P,RST			;RESET
	SETZM	ZER			;ZERO CORE
	MOVE	T1,[XWD ZER,ZER+1]
	BLT	T1,ZER+ZERSIZ-1
	PUSHJ	P,PARSE			;PARSE THE COMMAND LINE
	JRST	COMMAN
	SUBTTL	PARSE THE COMMAND LINE
PARSE:	MOVEI	P1,COMLIN-.SBNCL	;IN CASE /NCL/XCL AT PROMPT LEVEL
	MOVE	P2,[XWD -SWL,SWN]	;PROMPT USER
	MOVEI	P3,SWX
	PUSHJ	P,PROMPT
	 POPJ	P,
	PUSHJ	P,INDIR			;DO INDIRECT FILES
	MOVE	T1,[XWD HGH,LOW]	;COPY NON-NULL DATA
	BLT	T1,LOW+LOWSIZ-1
	MOVE	F,SAVFLG		;DEFAULT FLAGS
	MOVE	T1,SAVCLS		;DEFAULT CLOSENESS
	MOVEM	T1,CLSNUM
	PUSHJ	P,PURSPC		;PURGE OLD FILESPECS
	PJOB	T2,			;MAKE TEMP SPEC UNIQUE
	IDIVI	T2,^D10
	MOVE	T1,T2
	IDIVI	T1,^D10
	LSH	T1,6
	ADD	T1,T2
	LSH	T1,6
	ADD	T1,T3
	ADDM	T1,TMPSPC+.SBNAM
	MOVEI	P1,OSPC			;PASS ADR O SPC
	PUSHJ	P,SPCI			;GET OUTPUT SPC
	 POPJ	P,
	PUSHJ	P,EATS			;EAT EQUAL
	 POPJ	P,
	CAIE	C,"="
	FATAL	MERSYN,<Syntax error>
	PUSHJ	P,CI
	 POPJ	P,
	MOVEI	P1,ASPC			;PARSE THE LIST OF INPUT SPECS
	MOVEI	P4,APAT
	PUSHJ	P,SPCSI
	 POPJ	P,
	PUSHJ	P,EATCR			;TEST FOR BREAK CHAR
	 POPJ	P,
	PUSHJ	P,BP
	 FATAL	MERSYN,<Syntax error>
	MOVEI	P1,OSPC			;IS OUTPUT WILD?
	PUSHJ	P,WILDP
	 JRST	NOTWLD			;NO
	MOVE	P1,ASPC			;FIND A WILD INPUT
MERLOP:	PUSHJ	P,WILDP
	 CAIA
	JRST	WLDER
	HRRZ	P1,.SBNXT(P1)
	JUMPN	P1,MERLOP
	MOVE	P1,ASPC			;NONE, JUST USE 1ST

;HERE WITH P1=ADR OF THE WILD INPUT SPC
WLDER:	MOVEI	P2,WR			;DO WR FOR EACH FILE
	PUSHJ	P,WILDER
	 JFCL
	JRST	DONE

;ROUTINE TO MATCH EACH SPC WITH THE WILD SPC
;AND FEED THEM INTO MAIN
WR:	PUSHJ	P,SAVE3			;SAVE P1-P3
	SETOM	CHS			;0 CH'S USED SO FAR
	MOVE	P2,ASPC			;ADR 1ST INPUT SPC
	MOVEI	P3,ASPC2
WRLOP:	PUSHJ	P,WLDMAT		;MATCH WILDCARDS
	EXCH	P1,P3			;MAIN WANTS IN P1
	PUSHJ	P,MAIN			;DO MAIN
	 POPJ	P,
	EXCH	P1,P3			;PUT P1 BACK
	HRRZ	P2,.SBNXT(P2)		;FOLLOW LINK TO NEXT SPC
	JUMPN	P2,WRLOP		;LOOP UNTIL NONE LEFT
	MOVEI	P2,OSPC			;MATCH OUTPUT TO INPUT
	MOVEI	P3,OSPC2
	PUSHJ	P,WLDMAT
	MOVEI	P1,OSPC2		;DO EVERYTHING THAT'S LEFT
	JRST	DOIT
;HERE WHEN OUTPUT IS NOT WILD
NOTWLD:	SETOM	CHS			;0 CH'S USED SO FAR
	MOVE	P1,ASPC			;FEED EACH SPC INTO WILD
	MOVEI	P2,MAIN			;WILD FEEDS THEM TO MAIN
NTWLD1:	PUSHJ	P,WILDER
	 JFCL
	HRRZ	P1,.SBNXT(P1)
	JUMPN	P1,NTWLD1
	MOVEI	P1,OSPC			;DO EVERYTHING THAT'S LEFT
	PUSHJ	P,DOIT
	 JFCL

;HERE TO DELETE TMP FILE
DONE:	MOVEI	T1,1			;ISELECT
	MOVEM	T1,ICH
	MOVEI	P1,TMPSPC		;LOOKUP TMP FILE
	PUSHJ	P,SLKP
	 POPJ	P,			;NONE
	SETZM	TMPSPC+.SBNAM		;DELETE TMP FILE
	PUSHJ	P,IREN
	 JFCL
	POPJ	P,
	SUBTTL	SWITCHES

	DEFINE	SW,<
	X	LOG,<TRO F,F.LOG>
	X	NOLOG,<TRZ F,F.LOG>
	X	CLOSE,<PUSHJ P,CLOS>
	X	UNCLUD,<TRO F,F.UNC>
	X	UXCLUD,<TRZ F,F.UNC>
	X	XID,<TRO F,F.XID>
	X	NOXID,<TRZ F,F.XID>	;;LAST SWITCH IN SWITCH.INI
	X	EXIT,<JRST EXT##>
	X	HELP,<PUSHJ P,HELPER##>
	X	NCLUDE,<PUSHJ P,INCLUD>
	X	XCLUDE,<PUSHJ P,EXCLUD>
>

	DEFINE	X(A,B),<
	SIXBIT	/A/
>
SWN:	SW
	SWL=.-SWN
	SWIL==7				;NUMBER OF SWITCHES IN SWITCH.INI

	DEFINE	X(A,B),<
	B
>
SWX:	SW

;/INCLUDE SWITCH
INCLUD:	PUSHJ	P,SAVE1			;SAVE P1
	MOVEI	T1,.SBNCL(P1)		;HE CHANGED HIS MIND, PURGE OLD CORE
	PUSHJ	P,PUR
	PUSHJ	P,COLON			;EAT COLON
	 JRST	CPOPJ1
	PUSHJ	P,LSTI			;GET A SIXBIT LIST
	 JRST	CPOPJ1			;LOOSE
	MOVE	T1,-1(P)		;STORE ADR
	MOVEM	P1,.SBNCL(T1)
	POPJ	P,			;WIN

;/EXCLUDE SWITCH
EXCLUD:	PUSHJ	P,SAVE1			;SAVE P1
	MOVEI	T1,.SBXCL(P1)		;HE CHANGE HIS MIND, PURGE OLD CORE
	PUSHJ	P,PUR
	PUSHJ	P,COLON			;EAT COLON
	 JRST	CPOPJ1
	PUSHJ	P,LSTI			;GET A SIXBIT LIST
	 JRST	CPOPJ1			;LOOSE
	MOVE	T1,-1(P)		;STORE ADR
	MOVEM	P1,.SBXCL(T1)
	POPJ	P,			;WIN

;/CLOSE:N SWITCH
CLOS:	PUSHJ	P,COLON			;EAT COLON
	 JRST	CPOPJ1
	PUSHJ	P,DECI			;GET ARG
	 JRST	CPOPJ1
	MOVEM	T1,CLSNUM		;STORE IT
	POPJ	P,
;ROUTINE TO PARSE A STRING OF FILE SPECS
;P1 PASSES ADDR TO STORE POINTER TO LIST
;P2+P3 PASS SWITCH ARGS
;P4 PASSES ADDR OF DEFAULT SPEC
SPCSI:	HLRZ	T1,.SBSIZ(P4)		;GET CORE FOR ANOTHER SPC
	PUSHJ	P,GETBLK
	 POPJ	P,
	MOVE	T1,T2			;COPY DEFAULT SPEC
	HRL	T1,P4
	BLT	T1,SPCSIZ-1(T2)
	SETZM	.SBNCL(T2)		;/NCL NOT STICKY
	SETZM	.SBXCL(T2)		;/XCL NOT STICKY
	HLLZS	.SBNXT(T2)		;APPEND TO LINKED LIST
	HRRM	T2,.SBNXT(P1)
	MOVE	P1,T2			;POINT TO NEW SPEC
	MOVE	P4,P1			;NEW SPEC WILL BE DEFAULT NEXT TIME
	PUSHJ	P,SPCI			;GET FILE SPEC
	 POPJ	P,
	PUSHJ	P,SWTCH			;DO SWITCHES
	 POPJ	P,
	PUSHJ	P,EATS			;ANOTHER SPC COMING?
	 POPJ	P,
	CAIE	C,","
	JRST	CPOPJ1			;NO
	PUSHJ	P,CI			;YES, EAT THE COMMA
	 POPJ	P,
	JRST	SPCSI			;GO GET THE SPC
;ROUTINE TO PURGE OLD FILSPECS
PURSPC:	PUSHJ	P,SAVE1			;SAVE P1
	MOVEI	P1,ASPC
PRSPC1:	HRRZ	P1,(P1)
	JUMPE	P1,PRSPC2
	MOVEI	T1,.SBNCL(P1)		;PURGE NCLUDE LIST
	PUSHJ	P,PUR
	MOVEI	T1,.SBXCL(P1)		;PURGE XCLUDE LIST
	PUSHJ	P,PUR
	JRST	PRSPC1
PRSPC2:	MOVEI	T1,ASPC			;PURGE FILESPECS THEMSELVES
	PJRST	PUR
	SUBTTL	MAINSTREAM

TOOMNY:	PUSHJ	P,DONOW			;DO WHAT WE GOT SO FAR
	 POPJ	P,
;ENTER HERE
MAIN:	AOS	WLDCNT			;BUMP WILD COUNT
	MOVE	CH,CHS			;TOO MANY?
	CAIN	CH,CHAN-1
	JRST	TOOMNY			;YES
	ADDI	CH,1			;BUMP COUNT
	MOVEM	CH,CHS
	MOVE	T1,.SBNCL(P1)		;STORE INCLUDE SWITCH
	MOVEM	T1,NCLD(CH)
	MOVE	T1,.SBXCL(P1)		;STORE EXCLUDE SWITCH
	MOVEM	T1,XCLD(CH)
	MOVE	T1,CH			;STORE REST OF SPC
	IMULI	T1,SPCSIZ
	ADDI	T1,SPCS
	MOVEI	T2,SPCSIZ-1(T1)
	HRL	T1,P1
	BLT	T1,(T2)
	JRST	CPOPJ1

DONOW:	PUSHJ	P,SAVE1			;SAVE P1
	MOVEI	P1,TMPSPC		;OUTPUT=TEMP FILE
	PUSHJ	P,DOIT			;DO A MERGE
	 POPJ	P,
	SETOM	CHS			;CLEAR COUNT
	JRST	MAIN			;FEED TEMP FILE BACK INTO INPUT

DOIT:	PUSHJ	P,DOALL			;MERGE OUTPUT=INPUT
	 JRST	DOIT0
	JRST	CPOPJ1
DOIT0:	TRNN	C,IO.EOF		;REAL ERROR OR JUST EOF?
	POPJ	P,			;ERROR
	ERR	ER.EAT,"?",MEREOF,<Premature EOF>
DOALL:	PUSHJ	P,SAVE1			;SAVE P1
	MOVE	T1,SPCS+.SBNAM		;OUTPUT DEFAULT TO INPUT
	SKIPN	.SBNAM(P1)
	MOVEM	T1,.SBNAM(P1)
	PUSHJ	P,LOG			;DO LOGGING
	 POPJ	P,
	MOVEI	T1,O			;ENTER OUTPUT
	MOVEM	T1,OCH
	PUSHJ	P,NTR
	 POPJ	P,
	MOVE	CH,CHS			;LOOP COUNT
INILOP:	MOVEM	CH,ICH			;ISELECT IT
	MOVE	P1,CH			;LOOK IT UP
	IMULI	P1,SPCSIZ
	ADDI	P1,SPCS
	PUSHJ	P,LKP
	 POPJ	P,
	SETZM	CHKSUM(CH)		;CLEAR CHECKSUM
	PUSHJ	P,PRS			;PARSE 1ST COMMAND
	 POPJ	P,
	PUSHJ	P,PARS			;PARSE 2ND COMMAND
	 POPJ	P,
	SOJGE	CH,INILOP		;LOOP FOR EACH CH
	SETZM	LSTSEQ			;POINT TO TOP OF FILE
	SETZM	CFLG			;CLEAR CONFLICT FLAG
	SETZM	CNUM			;RESET CONFLICT COUNT
LOOP:	MOVE	CH,CHS			;ALL CH'S AT EOF?
	SKIPN	CHKSM(CH)
	JRST	NOTDON			;NO
	SOJGE	CH,.-2

;HERE WHEN MERGE IS DONE
	PUSHJ	P,EC			;END CONFLICT
	 POPJ	P,
	MOVE	T1,CHKSM		;ALL CH'S SAME CHECKSUM?
	MOVE	CH,CHS
	CAME	T1,CHKSM(CH)
	FATAL	MERSUM,<Checksum error>
	SOJG	CH,.-2
	MOVEI	T1,[ASCIZ / SUM /]	;OUTPUT CHECKSUM COMMAND
	PUSHJ	P,STRO
	 POPJ	P,
	MOVE	T1,CHKSM
	PUSHJ	P,DECO
	 POPJ	P,
	PUSHJ	P,CRLFO
	 POPJ	P,
	PUSHJ	P,OCLS			;CLOSE OUTPUT
	 JFCL
	MOVE	CH,CHS			;CLOSE ALL INPUT
	MOVEM	CH,ICH
	PUSHJ	P,ICLS
	SOJGE	CH,.-2
	MOVEI	T1,MRFLT
	SKIPE	CNUM			;CONFLICTS?
	PUSHJ	P,VERBO
	JRST	CPOPJ1

	MRFLT2
	MRFLT1
MRFLT:	VB	0,"%",MERFLT,<^ Conflict^>
MRFLT1:	MOVE	T1,CNUM
	PJRST	DECO
MRFLT2:	MOVEI	C,"s"
	MOVE	T1,CNUM
	CAIE	T1,1
	PJRST	CO
	POPJ	P,
;HERE WITH A CH THAT HASN'T REACHED EOF
NOTDON:	MOVE	T1,CHS			;FIND CH WITH LOWEST SEQ
NOTDN2:	SKIPE	CHKSM(T1)
	JRST	NOTDN1
	MOVE	T2,SQ(CH)
	CAMLE	T2,SQ(T1)
	MOVE	CH,T1
NOTDN1:	SOJGE	T1,NOTDN2
	SKIPN	T1,LSTSEQ		;CONFLICT WITH PREVIOUS COR?
	JRST	NOTDN3
	ADD	T1,CLSNUM
	CAML	T1,SQ(CH)
	JRST	CNFLCT			;YES
NOTDN3:	MOVE	T1,ESQ(CH)		;SEQ OF LAST LINE AFFECTED
	MOVEM	T1,LSTSEQ		;SAVE FOR NEXT TIME
	ADD	T1,CLSNUM		;PLUS CLOSENESS FACTOR
	SKIPE	CHKSUM(CH)		;CONFLICT WITH NEXT COR?
	JRST	NOTDN4
	CAML	T1,SEQ(CH)
	JRST	CNFLCT			;YES
NOTDN4:	MOVE	T2,CHS			;CONFLICT WITH OTHER CH'S?
NOTDN5:	CAME	T2,CH
	SKIPE	CHKSM(T2)
	JRST	NOTDN6
	CAML	T1,SQ(T2)
	JRST	CNFLCT			;YES
NOTDN6:	SOJGE	T2,NOTDN5
	JRST	OK			;NO

;HERE WHEN THERE IS A CONFLICT
CNFLCT:	PUSHJ	P,BC			;BEGIN CONFLICT
	 POPJ	P,
	JRST	NOCARE

;HERE WHEN CONFLICT CHECK IS OK
OK:	PUSHJ	P,EC			;END CONFLICT
	 POPJ	P,

NOCARE:	MOVEI	C," "			;COMMAND PREFIX
	PUSHJ	P,PUTC
	 POPJ	P,
	MOVEI	A1,COMLN(CH)		;OUTPUT THE COMMAND
	PUSHJ	P,PUTA
	 POPJ	P,
	MOVEI	A1,DELLN(CH)		;OUTPUT TEXT TO DELETE
	PUSHJ	P,PUTA
	 POPJ	P,
	SKIPE	DELLN(CH)		;DELIMIT IF REPLACE
	SKIPN	INSLN(CH)
	JRST	.+4
	MOVEI	T1,[ASCIZ / WIT
/]
	PUSHJ	P,STRO
	 POPJ	P,
	MOVEI	A1,INSLN(CH)		;OUTPUT TEXT TO INSERT
	PUSHJ	P,PUTA
	 POPJ	P,
	PUSHJ	P,PARS			;PARSE NEXT COMMAND
	 POPJ	P,
	JRST	LOOP
	SUBTTL	CONFLICT MESSAGES

;ROUTINE TO TYPE BEGIN CONFLICT MESSAGE IF NEEDED
BC:	SKIPE	CFLG			;ALREADY FLAGED IT?
	JRST	CPOPJ1			;YES, IGNORE IT
	SETOM	CFLG			;NO, FLAG NOW
	AOS	CNUM			;COUNT IT
	MOVEI	T1,[ASCIZ / ;***BEGINNING OF CONFLICT /]
	JRST	BEC

;ROUTINE TO TYPE END CONFLICT MESSAGE IF NEEDED
EC:	SKIPN	CFLG			;WAS PREVIOUS ONE A CONFLICT?
	JRST	CPOPJ1			;NO, GOOD
	SETZM	CFLG			;YES, CLEAR FLAG
	MOVEI	T1,[ASCIZ / ;***END OF CONFLICT /]
BEC:	PUSHJ	P,STRO
	 POPJ	P,
	MOVE	T1,CNUM			;SAY WHICH CONFLICT
	PUSHJ	P,DECO
	 POPJ	P,
	MOVEI	T1,[ASCIZ /***
/]
	JRST	STRO
	SUBTTL	PARSE

;ROUTINE TO LOOKAHEAD ON COMMAND
;I.E. PARSE AN EXTRA COMMAND AND STORE IT IN CORE
PARS:	PUSHJ	P,PURGE2		;RECLAIM LEFTOVER CORE
	MOVE	T1,COMLIN(CH)		;COPY OLD LOOKAHEAD TO BUF
	MOVEM	T1,COMLN(CH)
	SETZM	COMLIN(CH)
	MOVE	T1,DELLIN(CH)
	MOVEM	T1,DELLN(CH)
	SETZM	DELLIN(CH)
	MOVE	T1,INSLIN(CH)
	MOVEM	T1,INSLN(CH)
	SETZM	INSLIN(CH)
	MOVE	T1,SEQ(CH)
	MOVEM	T1,SQ(CH)
	MOVE	T1,ESEQ(CH)
	MOVEM	T1,ESQ(CH)
	MOVE	T1,CHKSUM(CH)
	MOVEM	T1,CHKSM(CH)
	PUSHJ	P,PRS			;PARSE NEW LOOKAHEAD
	 POPJ	P,
	SKIPE	CHKSUM(CH)		;OLD BEFORE NEW
	JRST	CPOPJ1
	MOVE	T1,SQ(CH)
	CAMLE	T1,SEQ(CH)
	FATAL	MEROOO,<Out of order>
	JRST	CPOPJ1
;ROUTINE TO PARSE A COMMAND FROM COR FILE
PRS:	SKIPE	CHKSUM(CH)		;READ CHECKSUM ALREADY?
	JRST	CPOPJ1			;YES, NO FURTHER
	PUSHJ	P,PURGE			;RECLAIM LEFTOVER CORE
	MOVEM	CH,ICH			;ISELECT
	PUSHJ	P,LSNI			;GET 1ST CHAR
	 POPJ	P,
	PUSHJ	P,EATS			;EAT SPACES
	 POPJ	P,
	MOVEI	A1,COMLIN(CH)		;GET A COMMAND
	PUSHJ	P,GETA
	 POPJ	P,
	HRRZ	T1,COMLIN(CH)		;ISELECT CORE
	ADD	T1,[POINT 7,1]
	MOVEM	T1,ICH
	ILDB	C,ICH			;GET 1ST CHAR
	CAIN	C,";"			;COMMENT?
	JRST	PRS			;YES, EAT IT
	PUSHJ	P,SIXI			;GET CMD NAME
	 POPJ	P,
	MOVE	T2,[XWD -CMDL,CMDN]	;FIND IN TABLE
	PUSHJ	P,FNDNAM
	 POPJ	P,
	PUSHJ	P,@CMDX(T2)		;DISPATCH IT
	 POPJ	P,
	PUSHJ	P,XID			;EXCLUDE IDENTICAL EDITS
	TRNN	F,F.YN			;INCLUDE?
	JRST	PRS			;NO, EAT IT
	JRST	CPOPJ1
;ROUTINE TO EXCLUDE IDENTICAL EDITS
XID:	TRNE	F,F.XID			;SHOULD WE?
	TRNN	F,F.YN			;DON'T BOTHER IF CONDITIONAL IS OFF
	POPJ	P,
	SKIPE	CHKSUM(CH)		;EOF?
	POPJ	P,			;YES
	PUSHJ	P,SAVE1			;SAVE P1
	MOVE	P1,CHS			;SETUP LOOP
XID3:	CAMN	CH,P1			;DON'T COMPARE AGAINST SELF
	JRST	XID1
	MOVE	T1,SEQ(CH)		;SAME SEQUENCE NUMBER?
	SKIPN	CHKSUM(P1)		;AND NOT EOF?
	CAME	T1,SEQ(P1)
	JRST	XID1			;NOT EQUAL
	MOVEI	A1,INSLIN(CH)		;INSERT IDENTICAL?
	MOVEI	A2,INSLIN(P1)
	PUSHJ	P,CMPLNS
	 JRST	XID1
	MOVEI	A1,DELLIN(CH)		;DELETE IDENTICAL?
	MOVEI	A2,DELLIN(P1)
	PUSHJ	P,CMPLNS
	 JRST	XID1
	MOVE	T1,COMLIN(CH)		;OUR EDIT NAME
	MOVE	T2,COMLIN(P1)		;HIS EDIT NAME
	CAMGE	CH,P1			;WHICH IS THE LATER FILE?
	EXCH	T1,T2			;HE IS, GIVE HIM OUR NAME
	MOVEM	T1,COMLIN(CH)		;OUR EDIT NAME (TO BE CHUCKED)
	MOVEM	T2,COMLIN(P1)		;HIS EDIT NAME (TO BE RETAINED)
	TRZ	F,F.YN			;CHUCK OUR EDIT
	POPJ	P,
XID1:	MOVE	T1,SEQ(CH)		;SAME SEQUENCE NUMBER?
	SKIPN	CHKSM(P1)		;AND NOT EOF?
	CAME	T1,SQ(P1)
	JRST	XID2			;NOT EQUAL
	MOVEI	A1,INSLIN(CH)		;INSERT IDENTICAL?
	MOVEI	A2,INSLN(P1)
	PUSHJ	P,CMPLNS
	 JRST	XID2
	MOVEI	A1,DELLIN(CH)		;DELETE IDENTICAL?
	MOVEI	A2,DELLN(P1)
	PUSHJ	P,CMPLNS
	 JRST	XID2
	MOVE	T1,COMLIN(CH)		;OUR EDIT NAME
	MOVE	T2,COMLN(P1)		;HIS EDIT NAME
	CAMGE	CH,P1			;WHICH IS THE LATER FILE?
	EXCH	T1,T2			;HE IS, GIVE HIM OUR NAME
	MOVEM	T1,COMLIN(CH)		;OUR EDIT NAME (TO BE CHUCKED)
	MOVEM	T2,COMLN(P1)		;HIS EDIT NAME (TO BE RETAINED)
	TRZ	F,F.YN			;CHUCK OUR EDIT
	POPJ	P,
XID2:	SOJGE	P1,XID3			;LOOP FOR EACH FILE
	POPJ	P,

;ROUTINE TO COMPARE TEXT
;A1 PASSES ADDR OF ADDR OF 1ST LINE OF 1ST FILE
;A2 PASSES ADDR OF ADDR OF 1ST LINE OF 2ND FILE
;SKIP IF IDENTICAL
CMPLNS:	HRRZ	A1,(A1)			;STEP TO NEXT LINE
	HRRZ	A2,(A2)
	SKIPN	A1			;QUIT IF BOTH ZERO
	JUMPE	A2,CPOPJ1
	JUMPE	A1,CPOPJ		;ERROR IF ONLY A1 ZERO
	JUMPE	A2,CPOPJ		;ERROR IF ONLY A2 ZERO
	HLRZ	T1,(A1)			;ERROR IF UNEQUAL LENGTH
	HLRZ	T2,(A2)
	CAME	T1,T2
	POPJ	P,
CMPLN1:	SOJE	T1,CMPLNS		;IF COUNT EXPIRE DO NEXT LINE
	MOVE	T2,A1			;GET WORD FROM 1ST FILE
	ADD	T2,T1
	MOVE	T2,(T2)
	MOVE	T3,A2			;SAME AS 2ND FILE?
	ADD	T3,T1
	CAME	T2,(T3)
	POPJ	P,			;NO, RETURN IMMEDIATELY
	JRST	CMPLN1			;YES, KEEP CHECKING
;CHECKSM COMMAND
SUM:	PUSHJ	P,DECI			;GET CHECKSUM
	 POPJ	P,
	MOVEM	T1,CHKSUM(CH)
	JRST	COMI			;EAT COMMENTS

;INSERT COMMAND
INS:	PUSHJ	P,SEQI			;GET STARTING LINE
	 POPJ	P,
	MOVE	T1,SEQ(CH)		;IS ENDING LINE TOO
	MOVEM	T1,ESEQ(CH)
INS2:	MOVEI	A1,INSLIN(CH)		;GET TEXT TO INSERT
	JRST	GETAS

;DELETE COMMAND
DEL:	PUSHJ	P,SEQI			;GET STARTING LINE
	 POPJ	P,
	MOVEI	A1,DELLIN(CH)		;GET TEXT TO DELETE
	PUSHJ	P,GETAS
	 POPJ	P,
	MOVE	T1,SAVSEQ		;ENDING LINE
	MOVEM	T1,ESEQ(CH)
	JRST	CPOPJ1

;REPLACE COMMAND
REP:	PUSHJ	P,DEL			;DO DELETE STUFF
	 POPJ	P,
	PUSHJ	P,EATEOL		;EAT THE DELIMITER
	 POPJ	P,
	JRST	INS2			;DO THE INSERT STUFF
;ROUTINE TO PARSE SEQUENCE NUMBERS
SEQI:	PUSHJ	P,DECI			;GET LINE NUMBER
	 POPJ	P,
	HRRZM	T1,SEQ(CH)
	PUSHJ	P,EATS			;EAT SLASH
	 POPJ	P,
	CAIE	C,"/"
	FATAL	MERSYN,<Syntax error in COR file>
	PUSHJ	P,CI
	 POPJ	P,
	PUSHJ	P,DECI			;GET PAGE NUMBER
	 POPJ	P,
	HRLM	T1,SEQ(CH)
;FALL TO COMI

;ROUTINE TO LOAD COMMENTS
COMI:	TRZ	F,F.YN			;ASSUME EXCLUDE
	TRNE	F,F.UNC			;UNCLUDE?
	TRO	F,F.YN			;OOPS, INCLUDE
	PUSHJ	P,EATCR			;BREAK CHAR?
	 POPJ	P,
	PUSHJ	P,BP
	 CAIA
	JRST	CPOPJ1			;YES
	CAIE	C,";"			;NO, COMMENT?
	FATAL	MERSYN,<Syntax error in COR file>
	PUSHJ	P,CI			;YES, EAT THE SEMI
	 POPJ	P,
	PUSHJ	P,SIXI			;GET NAME
	 POPJ	P,
	TRO	F,F.YN			;ASSUME INCLUDE
	SKIPN	T2,NCLD(CH)		;INCLUDE SWITCH?
	JRST	NONCLD			;NO
NCLDLP:	MOVE	T3,1(T2)		;YES, GET AN ITEM
	XOR	T3,T1			;MATCHES?
	ANDCM	T3,2(T2)
	JUMPE	T3,CPOPJ1		;YES, INCLUDE
	HRRZ	T2,(T2)			;ADVANCE TO NEXT ITEM
	JUMPN	T2,NCLDLP		;LOOP UNTIL NONE LEFT
	TRZ	F,F.YN			;NONE LEFT, EXCLUDE
NONCLD:	SKIPN	T2,XCLD(CH)		;EXCLUDE SWITCH?
	JRST	CPOPJ1			;NO
	TRZ	F,F.YN			;YES, ASSUME EXCLUDE
XCLDLP:	MOVE	T3,1(T2)		;GET AN ITEM
	XOR	T3,T1			;MATCHES?
	ANDCM	T3,2(T2)
	JUMPE	T3,CPOPJ1		;YES, EXCLUDE
	HRRZ	T2,(T2)			;ADVANCE TO NEXT ITEM
	JUMPN	T2,XCLDLP		;LOOP UNTIL NONE LEFT
	TRO	F,F.YN			;NONE LEFT, INCLUDE
	JRST	CPOPJ1
	DEFINE	CMD,<
	X	DELETE,DEL
	X	INSERT,INS
	X	REPLAC,REP
	X	SUM,SUM
>	;END OF CMD

	DEFINE	X(A,B),<
	SIXBIT	/A/
>
CMDN:	CMD
	CMDL=.-CMDN

	DEFINE	X(A,B),<
	B
>
CMDX:	CMD
	SUBTTL	INPUT ROUTINES

;ROUTINE TO GET SEVERAL LINES
;A1 PASSES ADR TO STORE ADR OF LINKAGE LIST
GETAS:	MOVEM	CH,ICH			;ISELECT
	MOVE	T1,SEQ(CH)		;SAVE INITIAL SEQ
	MOVEM	T1,SAVSEQ
GTSLP:	MOVEM	T1,DSEQ			;STORE RUNNING SEQ
	PUSHJ	P,LSNI			;GET 1ST CHAR
	 POPJ	P,
	CAIN	C," "			;NEW COMMAND?
	JRST	CPOPJ1			;YES
	PUSHJ	P,GETA			;NO, INPUT A LINE
	 POPJ	P,
	MOVE	A1,A2			;ADVANCE PNTR
	MOVE	T1,DSEQ			;SAVE THE SEQ
	MOVEM	T1,SAVSEQ
	ADDI	T1,1			;BUMP LINE COUNT
	CAIE	C,14			;FORM FEED?
	JRST	GTSLP			;NO
	TRZ	T1,-1			;YES, BUMP PAGE COUNT
	AOBJP	T1,GTSLP

;ROUTINE TO GET A LINE
;A1 PASSES ADR TO STORE ADR OF LINE
;ENTER WITH 1ST CHAR ALREADY IN C
;A2 RETURNS ADR OF LINE
GETA:	PUSHJ	P,SAVE2			;SAVE P1-P2
	MOVE	P1,[POINT 7,LINE]	;BP TO BLK
	MOVEI	P2,LINSIZ*5-1		;CHAR COUNT
GETLP:	IDPB	C,P1			;STORE THE CHAR
	PUSHJ	P,BP			;BREAK CHAR?
	 CAIA				;NO
	JRST	GETDN			;YES, QUIT
	PUSHJ	P,LSNI			;GET ANOTHER
	 POPJ	P,
	SOJG	P2,GETLP		;COUNT IT
	ERR	ER.EAT,"?",MERLTL,<Line too long>
GETDN:	SETZ	T1,			;MAKE ASCIZ
GETDN1:	IDPB	T1,P1
	TLNE	P1,760000
	JRST	GETDN1
	SUBI	P1,LINE			;LENGHT-1
	HRRZI	T1,2(P1)		;GET SOME CORE
	PUSHJ	P,GETBLK
	 POPJ	P,
	MOVE	A2,T2			;ADR IN A2
	HRRM	A2,(A1)			;LINK TO LIST
	ADDI	T1,-1(A2)		;ADR LAST WORD
	ADDI	T2,1			;BLT LINE TO BLK
	HRLI	T2,LINE
	BLT	T2,(T1)
	JRST	CPOPJ1
	SUBTTL	OUTPUT ROUTINES

;ROUTINE TO OUTPUT SEVERAL LINES
;A1 PASSES ADR OF ADR OF LINKAGE LIST
PUTA:	HRRZ	A1,(A1)			;ADR NEXT BLK
	JUMPE	A1,CPOPJ1		;QUIT IF NONE
	MOVEI	T1,1(A1)		;OUTPUT THE LINE
	PUSHJ	P,STRO
	 POPJ	P,
	JRST	PUTA			;TRY ANOTHER
	SUBTTL	CORE RECLAIMATION

;ROUTINE TO RECLAIM CORE FROM LOOKAHEAD
PURGE:	MOVEI	T1,COMLIN(CH)		;COMMAND TEXT
	PUSHJ	P,PUR
	MOVEI	T1,DELLIN(CH)		;DELETE TEXT
	PUSHJ	P,PUR
	MOVEI	T1,INSLIN(CH)		;INSERT TEXT
	JRST	PUR

;ROUTINE TO RECLAIM CORE FROM CURRENT COMMAND
PURGE2:	MOVEI	T1,COMLN(CH)		;COMMAND TEXT
	PUSHJ	P,PUR
	MOVEI	T1,DELLN(CH)		;DELETE TEXT
	PUSHJ	P,PUR
	MOVEI	T1,INSLN(CH)		;INSERT TEXT
	JRST	PUR
	SUBTTL	LOGGING
LOG:	TRNN	F,F.LOG			;LOGGING?
	JRST	CPOPJ1			;NO
	PUSHJ	P,SAVE1			;SAVE P1
	SETOM	OCH			;OSELECT TTY
	PUSHJ	P,CRLFO
	 POPJ	P,
	PUSHJ	P,SPCO			;TYPE THE OUTPUT SPC
	 POPJ	P,
	MOVEI	C,"="
	PUSHJ	P,CO
	 POPJ	P,
	MOVE	CH,CHS			;LOOP COUNT
	MOVEI	P1,SPCS			;ADR 1ST SPC
LOGLOP:	PUSHJ	P,SPCO			;TYPE THE SPC
	 POPJ	P,
	JUMPE	CH,CPOPJ1		;QUIT IF LAST
	MOVEI	C,","			;COMMA
	PUSHJ	P,CO
	 POPJ	P,
	ADDI	P1,SPCSIZ		;NEXT SPC
	SOJA	CH,LOGLOP
	SUBTTL	DATA AREAS
;PROTOTYPE INPUT SPEC
APAT:	XWD	MYSIZ,0			;SIZE OF BLK
	SIXBIT	/DSK/			;DEVICE
	0				;DEVICE MASK
	BLOCK	SFDS+1			;PPN&SFDS
	IFN	SFDS,<0>
	BLOCK	SFDS+1			;PPN&SFDS MASKS
	0				;FILENAME
	0				;FILENAME MASK
	SIXBIT	/COR/			;EXTENSION
	.IOASC				;ASCII MODE
	LIT				;PUT LITERALS IN HISEG
	RELOC	0			;SWITCH TO LOWSEG

PDL:	BLOCK	PDLSIZ			;PUSH DOWN LIST
DSEQ:	BLOCK	1			;DONE SEQ
SAVSEQ:	BLOCK	1			;SAVE AREA FOR DSEQ
CHKSUM:	BLOCK	CHAN			;LOOKAHEAD CHECKSUM
SEQ:	BLOCK	CHAN			;LOOKAHEAD STARTING SEQ
ESEQ:	BLOCK	CHAN			;LOOKAHEAD ENDING SEQ
CHKSM:	BLOCK	CHAN			;CHECKSUM
SQ:	BLOCK	CHAN			;STARTING SEQ
ESQ:	BLOCK	CHAN			;ENDING SEQ
NCLD:	BLOCK	CHAN			;ADR INCLUDE CHAIN
XCLD:	BLOCK	CHAN			;ADR EXCLUDE CHAIN
SPCS:	BLOCK	CHAN*SPCSIZ		;FILE SPECS
ASPC2:	BLOCK	MYSIZ			;A SPC, WITHOUT WILDCARDS
OSPC2:	BLOCK	SPCSIZ			;O SPC, WITHOUT WILDCARDS
LINE:	BLOCK	LINSIZ			;AN ASCIZ LINE
CFLG:	BLOCK	1			;CONFLICT FLAG
CNUM:	BLOCK	1			;CONFLICT NUMBER
CHS:	BLOCK	1			;HIGHEST INPUT CH IN USE
LSTSEQ:	BLOCK	1			;SEQ OF LAST LINE AFFECTED
SAVFLG:	BLOCK	1			;FLAGS FROM SWITCH.INI
SAVCLS:	BLOCK	1			;CLOSENESS FROM SWITCH.INI
CLSNUM:	BLOCK	1			;HOW CLOSE BEFORE CONFLICT

ZER:!					;BEGIN REGION TO BE ZEROED
ASPC:	BLOCK	1			;ADDR OF 1ST INPUT SPEC
INSLIN:	BLOCK	CHAN			;ADR OF LOOKAHEAD INSERT TEXT
DELLIN:	BLOCK	CHAN			;ADR OF LOOKAHEAD DELETE TEXT
COMLIN:	BLOCK	CHAN			;ADR OF LOOKAHEAD COMMAND TEXT
INSLN:	BLOCK	CHAN			;ADR OF INSERT TEXT
DELLN:	BLOCK	CHAN			;ADR OF DELETE TEXT
COMLN:	BLOCK	CHAN			;ADR OF COMMAND TEXT
	ZERSIZ==.-ZER			;END REGION TO BE ZEROED

LOW:					;NON-NULL DATA
	RELOC				;BACK TO HIGHSEG
HGH:	PHASE	LOW
;BEGIN IMPURE DATA
;O SPC, WITH WILDCARDS
OSPC:	XWD	SPCSIZ,0		;SIZE OF BLK
	SIXBIT	/DSK/			;DEVICE
	0				;DEVICE MASK
	BLOCK	SFDS+1			;PPN&SFDS
	IFN	SFDS,<0>
	BLOCK	SFDS+1			;PPN&SFDS MASKS
	0				;FILENAME
	0				;FILENAME MASK
	SIXBIT	/COR/			;EXTENSION
	.IOASC				;ASCII MODE
;TEMP SPEC
TMPSPC:	XWD	SPCSIZ,0		;SIZE OF BLK
	SIXBIT	/DSK/			;DEVICE
	0				;DEVICE MASK
	BLOCK	SFDS+1			;PPN&SFDS
	IFN	SFDS,<0>
	BLOCK	SFDS+1			;PPN&SFDS MASKS
	SIXBIT	/MER000/		;FILENAME
	0				;FILENAME MASK
	SIXBIT	/TMP/			;EXTENSION
	.IOASC				;ASCII MODE
;END IMPURE DATA
	DEPHASE
	LOWSIZ==.-HGH
	RELOC	LOW			;BACK TO LOWSEG
	BLOCK	LOWSIZ

	END	MERGE