#include "../sccshead/sfile.h"
#include "../sccshead/sint.h"

char rdmod__[] "~|^`rdmod.c:	3.3";
/*
	Routine to apply deltas.  See "The Source Code Control System"
	(TM75-9152-3).
*/

readmod(pkt)
register struct Packet *pkt;
{
	register struct Control *ctl;
	register struct Apply *ap;

	while(rdrec(pkt) != 1) {
		ctl = pkt->Pibuf.Irecptr;
		if (!ctlrec(ctl,pkt->Pibuf.Ilen)) {
			if(pkt->Pkeep == YES) {
				pkt->Plnno++;
				return(0);
			}
			continue;
		}
		if (ctl->Crel > maxrel(pkt) ||
			ctl->Clev > maxlev(pkt,ctl->Crel))
				fmterr(pkt);
		if(ctl->Cctl == END) {
			if(remq(pkt,ctl))
				break;
			continue;
		}
		ap = &pkt->Papply[ctl->Crel][ctl->Clev];
		if(ap->Acode == APPLY) {
			addq(pkt,ctl,ap,ctl->Cctl==INS?YES:NO);
			continue;
		}
		if(ap->Acode == NOAPPLY) {
			addq(pkt,ctl,ap,ctl->Cctl==INS?NO:NULL);
			continue;
		}
		fmterr(pkt);
	}
	if(pkt->Pq) fatal("premature eof (58)");
	return(1);
}


addq(pkt,ctl,ap,keep)
struct Packet *pkt;
struct Control *ctl;
struct Apply *ap;
int keep;
{
	register struct Queue *cur, *prev, *q;
	int dt;

	dt = ap->Adt;
	for(cur = &pkt->Pq; cur = (prev=cur)->Qnext;)
		if(cur->Qdt <= dt) break;
	prev->Qnext = q = alloc(sizeof(*q));
	q->Qnext = cur;
	q->Qrel = ctl->Crel;
	q->Qlev = ctl->Clev;
	q->Qdt = dt;
	q->Qkeep = keep;

	setkeep(pkt);
}


remq(pkt,ctl)
register struct Packet *pkt;
struct Control *ctl;
{
	register struct Queue *cur, *prev;

	for(cur = &pkt->Pq; cur = (prev=cur)->Qnext;)
		if(cur->Qlev == ctl->Clev &&
		  cur->Qrel == ctl->Crel) break;
	if(cur) {
		prev->Qnext = cur->Qnext;
		free(cur);
		setkeep(pkt);
		return(0);
	}
	if(ctl->Crel) fmterr(pkt);
	return(1);
}


setkeep(pkt)
register struct Packet *pkt;
{
	register struct Queue *q;

	for(q = &pkt->Pq; q = q->Qnext;)
		if(q->Qkeep != NULL) {
			if((pkt->Pkeep=q->Qkeep) == YES) {
				pkt->Pirel = q->Qrel;
				pkt->Pilev = q->Qlev;
			}
			return;
		}
	pkt->Pkeep = NO;
}
