xref: /plan9/sys/src/ape/cmd/sed/sed0.c (revision 027288c8a8763d34db13dc89d8bcd6514dbc2163)
1219b2ee8SDavid du Colombier #include <stdlib.h>
2219b2ee8SDavid du Colombier #include <unistd.h>
3219b2ee8SDavid du Colombier #include <stdio.h>
4219b2ee8SDavid du Colombier #include "sed.h"
5219b2ee8SDavid du Colombier 
6219b2ee8SDavid du Colombier struct label	*labtab = ltab;
7219b2ee8SDavid du Colombier char	CGMES[]	= "sed: Command garbled: %s\n";
8219b2ee8SDavid du Colombier char	TMMES[]	= "sed: Too much text: %s\n";
9219b2ee8SDavid du Colombier char	LTL[]	= "sed: Label too long: %s\n";
10219b2ee8SDavid du Colombier char	AD0MES[]	= "sed: No addresses allowed: %s\n";
11219b2ee8SDavid du Colombier char	AD1MES[]	= "sed: Only one address allowed: %s\n";
12219b2ee8SDavid du Colombier uchar	bittab[]  = {
13219b2ee8SDavid du Colombier 		1,
14219b2ee8SDavid du Colombier 		2,
15219b2ee8SDavid du Colombier 		4,
16219b2ee8SDavid du Colombier 		8,
17219b2ee8SDavid du Colombier 		16,
18219b2ee8SDavid du Colombier 		32,
19219b2ee8SDavid du Colombier 		64,
20219b2ee8SDavid du Colombier 		128
21219b2ee8SDavid du Colombier 	};
22219b2ee8SDavid du Colombier 
23*027288c8SDavid du Colombier void
main(int argc,char ** argv)24219b2ee8SDavid du Colombier main(int argc, char **argv)
25219b2ee8SDavid du Colombier {
26219b2ee8SDavid du Colombier 
27219b2ee8SDavid du Colombier 	eargc = argc;
28219b2ee8SDavid du Colombier 	eargv = (uchar**)argv;
29219b2ee8SDavid du Colombier 
30219b2ee8SDavid du Colombier 	badp = &bad;
31219b2ee8SDavid du Colombier 	aptr = abuf;
32219b2ee8SDavid du Colombier 	hspend = holdsp;
33219b2ee8SDavid du Colombier 	lab = labtab + 1;	/* 0 reserved for end-pointer */
34219b2ee8SDavid du Colombier 	rep = ptrspace;
35219b2ee8SDavid du Colombier 	rep->r1.ad1 = respace;
36219b2ee8SDavid du Colombier 	lbend = &linebuf[LBSIZE];
37219b2ee8SDavid du Colombier 	hend = &holdsp[LBSIZE];
38219b2ee8SDavid du Colombier 	lcomend = &genbuf[64];
39219b2ee8SDavid du Colombier 	ptrend = &ptrspace[PTRSIZE];
40219b2ee8SDavid du Colombier 	reend = &respace[RESIZE];
41219b2ee8SDavid du Colombier 	labend = &labtab[LABSIZE];
42219b2ee8SDavid du Colombier 	lnum = 0;
43219b2ee8SDavid du Colombier 	pending = 0;
44219b2ee8SDavid du Colombier 	depth = 0;
45219b2ee8SDavid du Colombier 	spend = linebuf;
46219b2ee8SDavid du Colombier 	hspend = holdsp;
47219b2ee8SDavid du Colombier 	fcode[0] = stdout;
48219b2ee8SDavid du Colombier 	nfiles = 1;
49219b2ee8SDavid du Colombier 	lastre = NULL;
50219b2ee8SDavid du Colombier 
51219b2ee8SDavid du Colombier 	if(eargc == 1)
52219b2ee8SDavid du Colombier 		exit(0);
53219b2ee8SDavid du Colombier 
54219b2ee8SDavid du Colombier 
55219b2ee8SDavid du Colombier 	while (--eargc > 0 && (++eargv)[0][0] == '-')
56219b2ee8SDavid du Colombier 		switch (eargv[0][1]) {
57219b2ee8SDavid du Colombier 
58219b2ee8SDavid du Colombier 		case 'n':
59219b2ee8SDavid du Colombier 			nflag++;
60219b2ee8SDavid du Colombier 			continue;
61219b2ee8SDavid du Colombier 
62219b2ee8SDavid du Colombier 		case 'f':
63219b2ee8SDavid du Colombier 			if(eargc-- <= 0)	exit(2);
64219b2ee8SDavid du Colombier 
65219b2ee8SDavid du Colombier 			if((fin = fopen((char*)(*++eargv), "r")) == NULL) {
66219b2ee8SDavid du Colombier 				fprintf(stderr, "sed: Cannot open pattern-file: %s\n", *eargv);
67219b2ee8SDavid du Colombier 				exit(2);
68219b2ee8SDavid du Colombier 			}
69219b2ee8SDavid du Colombier 
70219b2ee8SDavid du Colombier 			fcomp();
71219b2ee8SDavid du Colombier 			fclose(fin);
72219b2ee8SDavid du Colombier 			continue;
73219b2ee8SDavid du Colombier 
74219b2ee8SDavid du Colombier 		case 'e':
75219b2ee8SDavid du Colombier 			eflag++;
76219b2ee8SDavid du Colombier 			fcomp();
77219b2ee8SDavid du Colombier 			eflag = 0;
78219b2ee8SDavid du Colombier 			continue;
79219b2ee8SDavid du Colombier 
80219b2ee8SDavid du Colombier 		case 'g':
81219b2ee8SDavid du Colombier 			gflag++;
82219b2ee8SDavid du Colombier 			continue;
83219b2ee8SDavid du Colombier 
84219b2ee8SDavid du Colombier 		default:
85219b2ee8SDavid du Colombier 			fprintf(stderr, "sed: Unknown flag: %c\n", eargv[0][1]);
86219b2ee8SDavid du Colombier 			continue;
87219b2ee8SDavid du Colombier 		}
88219b2ee8SDavid du Colombier 
89219b2ee8SDavid du Colombier 
90219b2ee8SDavid du Colombier 	if(compfl == 0) {
91219b2ee8SDavid du Colombier 		eargv--;
92219b2ee8SDavid du Colombier 		eargc++;
93219b2ee8SDavid du Colombier 		eflag++;
94219b2ee8SDavid du Colombier 		fcomp();
95219b2ee8SDavid du Colombier 		eargv++;
96219b2ee8SDavid du Colombier 		eargc--;
97219b2ee8SDavid du Colombier 		eflag = 0;
98219b2ee8SDavid du Colombier 	}
99219b2ee8SDavid du Colombier 
100219b2ee8SDavid du Colombier 	if(depth) {
101219b2ee8SDavid du Colombier 		fprintf(stderr, "sed: Too many {'s\n");
102219b2ee8SDavid du Colombier 		exit(2);
103219b2ee8SDavid du Colombier 	}
104219b2ee8SDavid du Colombier 
105219b2ee8SDavid du Colombier 	labtab->address = rep;
106219b2ee8SDavid du Colombier 
107219b2ee8SDavid du Colombier 	dechain();
108219b2ee8SDavid du Colombier 
109219b2ee8SDavid du Colombier /*	abort();	/*DEBUG*/
110219b2ee8SDavid du Colombier 
111219b2ee8SDavid du Colombier 	if(eargc <= 0)
112219b2ee8SDavid du Colombier 		execute((uchar *)NULL);
113219b2ee8SDavid du Colombier 	else while(--eargc >= 0) {
114219b2ee8SDavid du Colombier 		execute(*eargv++);
115219b2ee8SDavid du Colombier 	}
116219b2ee8SDavid du Colombier 	fclose(stdout);
117219b2ee8SDavid du Colombier 	exit(0);
118219b2ee8SDavid du Colombier }
119219b2ee8SDavid du Colombier void
fcomp(void)120219b2ee8SDavid du Colombier fcomp(void)
121219b2ee8SDavid du Colombier {
122219b2ee8SDavid du Colombier 
123219b2ee8SDavid du Colombier 	uchar	*p, *op, *tp;
1247dd7cddfSDavid du Colombier     uchar *address(uchar*);
125219b2ee8SDavid du Colombier 	union reptr	*pt, *pt1;
126219b2ee8SDavid du Colombier 	int	i;
127219b2ee8SDavid du Colombier 	struct label	*lpt;
128219b2ee8SDavid du Colombier 
129219b2ee8SDavid du Colombier 	compfl = 1;
130219b2ee8SDavid du Colombier 	op = lastre;
131219b2ee8SDavid du Colombier 
132219b2ee8SDavid du Colombier 	if(rline(linebuf) < 0) {
133219b2ee8SDavid du Colombier 		lastre = op;
134219b2ee8SDavid du Colombier 		return;
135219b2ee8SDavid du Colombier 	}
136219b2ee8SDavid du Colombier 	if(*linebuf == '#') {
137219b2ee8SDavid du Colombier 		if(linebuf[1] == 'n')
138219b2ee8SDavid du Colombier 			nflag = 1;
139219b2ee8SDavid du Colombier 	}
140219b2ee8SDavid du Colombier 	else {
141219b2ee8SDavid du Colombier 		cp = linebuf;
142219b2ee8SDavid du Colombier 		goto comploop;
143219b2ee8SDavid du Colombier 	}
144219b2ee8SDavid du Colombier 
145219b2ee8SDavid du Colombier 	for(;;) {
146219b2ee8SDavid du Colombier 		if(rline(linebuf) < 0)	break;
147219b2ee8SDavid du Colombier 
148219b2ee8SDavid du Colombier 		cp = linebuf;
149219b2ee8SDavid du Colombier 
150219b2ee8SDavid du Colombier comploop:
151219b2ee8SDavid du Colombier /*	fprintf(stdout, "cp: %s\n", cp);	/*DEBUG*/
152219b2ee8SDavid du Colombier 		while(*cp == ' ' || *cp == '\t')	cp++;
153219b2ee8SDavid du Colombier 		if(*cp == '\0' || *cp == '#')		continue;
154219b2ee8SDavid du Colombier 		if(*cp == ';') {
155219b2ee8SDavid du Colombier 			cp++;
156219b2ee8SDavid du Colombier 			goto comploop;
157219b2ee8SDavid du Colombier 		}
158219b2ee8SDavid du Colombier 
159219b2ee8SDavid du Colombier 		p = address(rep->r1.ad1);
160219b2ee8SDavid du Colombier 		if(p == badp) {
161219b2ee8SDavid du Colombier 			fprintf(stderr, CGMES, linebuf);
162219b2ee8SDavid du Colombier 			exit(2);
163219b2ee8SDavid du Colombier 		}
164219b2ee8SDavid du Colombier 
165219b2ee8SDavid du Colombier 		if(p == 0) {
166219b2ee8SDavid du Colombier 			p = rep->r1.ad1;
167219b2ee8SDavid du Colombier 			rep->r1.ad1 = 0;
168219b2ee8SDavid du Colombier 		} else {
169219b2ee8SDavid du Colombier 			if(p == rep->r1.ad1) {
170219b2ee8SDavid du Colombier 				if(op)
171219b2ee8SDavid du Colombier 					rep->r1.ad1 = op;
172219b2ee8SDavid du Colombier 				else {
173219b2ee8SDavid du Colombier 					fprintf(stderr, "sed: First RE may not be null\n");
174219b2ee8SDavid du Colombier 					exit(2);
175219b2ee8SDavid du Colombier 				}
176219b2ee8SDavid du Colombier 			}
177219b2ee8SDavid du Colombier 			if(*rep->r1.ad1 != CLNUM && *rep->r1.ad1 != CEND)
178219b2ee8SDavid du Colombier 				op = rep->r1.ad1;
179219b2ee8SDavid du Colombier 			if(*cp == ',' || *cp == ';') {
180219b2ee8SDavid du Colombier 				cp++;
181219b2ee8SDavid du Colombier 				if((rep->r1.ad2 = p) > reend) {
182219b2ee8SDavid du Colombier 					fprintf(stderr, TMMES, linebuf);
183219b2ee8SDavid du Colombier 					exit(2);
184219b2ee8SDavid du Colombier 				}
185219b2ee8SDavid du Colombier 				p = address(rep->r1.ad2);
186219b2ee8SDavid du Colombier 				if(p == badp || p == 0) {
187219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
188219b2ee8SDavid du Colombier 					exit(2);
189219b2ee8SDavid du Colombier 				}
190219b2ee8SDavid du Colombier 				if(p == rep->r1.ad2)
191219b2ee8SDavid du Colombier 					rep->r1.ad2 = op;
192219b2ee8SDavid du Colombier 				else{
193219b2ee8SDavid du Colombier 				if(*rep->r1.ad2 != CLNUM && *rep->r1.ad2 != CEND)
194219b2ee8SDavid du Colombier 					op = rep->r1.ad2;
195219b2ee8SDavid du Colombier 				}
196219b2ee8SDavid du Colombier 
197219b2ee8SDavid du Colombier 			} else
198219b2ee8SDavid du Colombier 				rep->r1.ad2 = 0;
199219b2ee8SDavid du Colombier 		}
200219b2ee8SDavid du Colombier 
201219b2ee8SDavid du Colombier 		if(p > reend) {
202219b2ee8SDavid du Colombier 			fprintf(stderr, "sed: Too much text: %s\n", linebuf);
203219b2ee8SDavid du Colombier 			exit(2);
204219b2ee8SDavid du Colombier 		}
205219b2ee8SDavid du Colombier 
206219b2ee8SDavid du Colombier 		while(*cp == ' ' || *cp == '\t')	cp++;
207219b2ee8SDavid du Colombier 
208219b2ee8SDavid du Colombier swit:
209219b2ee8SDavid du Colombier 		switch(*cp++) {
210219b2ee8SDavid du Colombier 
211219b2ee8SDavid du Colombier 			default:
212219b2ee8SDavid du Colombier /*fprintf(stderr, "cp = %d; *cp = %o\n", cp - linebuf, *cp);*/
213219b2ee8SDavid du Colombier 				fprintf(stderr, "sed: Unrecognized command: %s\n", linebuf);
214219b2ee8SDavid du Colombier 				exit(2);
215219b2ee8SDavid du Colombier 
216219b2ee8SDavid du Colombier 			case '!':
217219b2ee8SDavid du Colombier 				rep->r1.negfl = 1;
218219b2ee8SDavid du Colombier 				goto swit;
219219b2ee8SDavid du Colombier 
220219b2ee8SDavid du Colombier 			case '{':
221219b2ee8SDavid du Colombier 				rep->r1.command = BCOM;
222219b2ee8SDavid du Colombier 				rep->r1.negfl = !(rep->r1.negfl);
223219b2ee8SDavid du Colombier 				cmpend[depth++] = &rep->r2.lb1;
224219b2ee8SDavid du Colombier 				if(++rep >= ptrend) {
225219b2ee8SDavid du Colombier 					fprintf(stderr, "sed: Too many commands: %s\n", linebuf);
226219b2ee8SDavid du Colombier 					exit(2);
227219b2ee8SDavid du Colombier 				}
228219b2ee8SDavid du Colombier 				rep->r1.ad1 = p;
229219b2ee8SDavid du Colombier 				if(*cp == '\0')	continue;
230219b2ee8SDavid du Colombier 
231219b2ee8SDavid du Colombier 				goto comploop;
232219b2ee8SDavid du Colombier 
233219b2ee8SDavid du Colombier 			case '}':
234219b2ee8SDavid du Colombier 				if(rep->r1.ad1) {
235219b2ee8SDavid du Colombier 					fprintf(stderr, AD0MES, linebuf);
236219b2ee8SDavid du Colombier 					exit(2);
237219b2ee8SDavid du Colombier 				}
238219b2ee8SDavid du Colombier 
239219b2ee8SDavid du Colombier 				if(--depth < 0) {
240219b2ee8SDavid du Colombier 					fprintf(stderr, "sed: Too many }'s\n");
241219b2ee8SDavid du Colombier 					exit(2);
242219b2ee8SDavid du Colombier 				}
243219b2ee8SDavid du Colombier 				*cmpend[depth] = rep;
244219b2ee8SDavid du Colombier 
245219b2ee8SDavid du Colombier 				rep->r1.ad1 = p;
246219b2ee8SDavid du Colombier 				if(*cp == 0)	continue;
247219b2ee8SDavid du Colombier 				goto comploop;
248219b2ee8SDavid du Colombier 
249219b2ee8SDavid du Colombier 			case '=':
250219b2ee8SDavid du Colombier 				rep->r1.command = EQCOM;
251219b2ee8SDavid du Colombier 				if(rep->r1.ad2) {
252219b2ee8SDavid du Colombier 					fprintf(stderr, AD1MES, linebuf);
253219b2ee8SDavid du Colombier 					exit(2);
254219b2ee8SDavid du Colombier 				}
255219b2ee8SDavid du Colombier 				break;
256219b2ee8SDavid du Colombier 
257219b2ee8SDavid du Colombier 			case ':':
258219b2ee8SDavid du Colombier 				if(rep->r1.ad1) {
259219b2ee8SDavid du Colombier 					fprintf(stderr, AD0MES, linebuf);
260219b2ee8SDavid du Colombier 					exit(2);
261219b2ee8SDavid du Colombier 				}
262219b2ee8SDavid du Colombier 
263219b2ee8SDavid du Colombier 				while(*cp++ == ' ');
264219b2ee8SDavid du Colombier 				cp--;
265219b2ee8SDavid du Colombier 
266219b2ee8SDavid du Colombier 
267219b2ee8SDavid du Colombier 				tp = lab->asc;
268219b2ee8SDavid du Colombier 				while((*tp = *cp++) && *tp != ';')
269219b2ee8SDavid du Colombier 					if(++tp >= &(lab->asc[8])) {
270219b2ee8SDavid du Colombier 						fprintf(stderr, LTL, linebuf);
271219b2ee8SDavid du Colombier 						exit(2);
272219b2ee8SDavid du Colombier 					}
273219b2ee8SDavid du Colombier 				*tp = '\0';
274219b2ee8SDavid du Colombier 				if(*lab->asc == 0) {
275219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
276219b2ee8SDavid du Colombier 					exit(2);
277219b2ee8SDavid du Colombier 				}
278219b2ee8SDavid du Colombier 
279219b2ee8SDavid du Colombier 				if(lpt = search(lab)) {
280219b2ee8SDavid du Colombier 					if(lpt->address) {
281219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: Duplicate labels: %s\n", linebuf);
282219b2ee8SDavid du Colombier 						exit(2);
283219b2ee8SDavid du Colombier 					}
284219b2ee8SDavid du Colombier 				} else {
285219b2ee8SDavid du Colombier 					lab->chain = 0;
286219b2ee8SDavid du Colombier 					lpt = lab;
287219b2ee8SDavid du Colombier 					if(++lab >= labend) {
288219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: Too many labels: %s\n", linebuf);
289219b2ee8SDavid du Colombier 						exit(2);
290219b2ee8SDavid du Colombier 					}
291219b2ee8SDavid du Colombier 				}
292219b2ee8SDavid du Colombier 				lpt->address = rep;
293219b2ee8SDavid du Colombier 				rep->r1.ad1 = p;
294219b2ee8SDavid du Colombier 
295219b2ee8SDavid du Colombier 				continue;
296219b2ee8SDavid du Colombier 
297219b2ee8SDavid du Colombier 			case 'a':
298219b2ee8SDavid du Colombier 				rep->r1.command = ACOM;
299219b2ee8SDavid du Colombier 				if(rep->r1.ad2) {
300219b2ee8SDavid du Colombier 					fprintf(stderr, AD1MES, linebuf);
301219b2ee8SDavid du Colombier 					exit(2);
302219b2ee8SDavid du Colombier 				}
303219b2ee8SDavid du Colombier 				if(*cp == '\\')	cp++;
304219b2ee8SDavid du Colombier 				if(*cp++ != '\n') {
305219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
306219b2ee8SDavid du Colombier 					exit(2);
307219b2ee8SDavid du Colombier 				}
308219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
309219b2ee8SDavid du Colombier 				p = text(rep->r1.re1);
310219b2ee8SDavid du Colombier 				break;
311219b2ee8SDavid du Colombier 			case 'c':
312219b2ee8SDavid du Colombier 				rep->r1.command = CCOM;
313219b2ee8SDavid du Colombier 				if(*cp == '\\')	cp++;
314219b2ee8SDavid du Colombier 				if(*cp++ != ('\n')) {
315219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
316219b2ee8SDavid du Colombier 					exit(2);
317219b2ee8SDavid du Colombier 				}
318219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
319219b2ee8SDavid du Colombier 				p = text(rep->r1.re1);
320219b2ee8SDavid du Colombier 				break;
321219b2ee8SDavid du Colombier 			case 'i':
322219b2ee8SDavid du Colombier 				rep->r1.command = ICOM;
323219b2ee8SDavid du Colombier 				if(rep->r1.ad2) {
324219b2ee8SDavid du Colombier 					fprintf(stderr, AD1MES, linebuf);
325219b2ee8SDavid du Colombier 					exit(2);
326219b2ee8SDavid du Colombier 				}
327219b2ee8SDavid du Colombier 				if(*cp == '\\')	cp++;
328219b2ee8SDavid du Colombier 				if(*cp++ != ('\n')) {
329219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
330219b2ee8SDavid du Colombier 					exit(2);
331219b2ee8SDavid du Colombier 				}
332219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
333219b2ee8SDavid du Colombier 				p = text(rep->r1.re1);
334219b2ee8SDavid du Colombier 				break;
335219b2ee8SDavid du Colombier 
336219b2ee8SDavid du Colombier 			case 'g':
337219b2ee8SDavid du Colombier 				rep->r1.command = GCOM;
338219b2ee8SDavid du Colombier 				break;
339219b2ee8SDavid du Colombier 
340219b2ee8SDavid du Colombier 			case 'G':
341219b2ee8SDavid du Colombier 				rep->r1.command = CGCOM;
342219b2ee8SDavid du Colombier 				break;
343219b2ee8SDavid du Colombier 
344219b2ee8SDavid du Colombier 			case 'h':
345219b2ee8SDavid du Colombier 				rep->r1.command = HCOM;
346219b2ee8SDavid du Colombier 				break;
347219b2ee8SDavid du Colombier 
348219b2ee8SDavid du Colombier 			case 'H':
349219b2ee8SDavid du Colombier 				rep->r1.command = CHCOM;
350219b2ee8SDavid du Colombier 				break;
351219b2ee8SDavid du Colombier 
352219b2ee8SDavid du Colombier 			case 't':
353219b2ee8SDavid du Colombier 				rep->r1.command = TCOM;
354219b2ee8SDavid du Colombier 				goto jtcommon;
355219b2ee8SDavid du Colombier 
356219b2ee8SDavid du Colombier 			case 'b':
357219b2ee8SDavid du Colombier 				rep->r1.command = BCOM;
358219b2ee8SDavid du Colombier jtcommon:
359219b2ee8SDavid du Colombier 				while(*cp++ == ' ');
360219b2ee8SDavid du Colombier 				cp--;
361219b2ee8SDavid du Colombier 
362219b2ee8SDavid du Colombier 				if(*cp == '\0') {
363219b2ee8SDavid du Colombier 					if(pt = labtab->chain) {
364219b2ee8SDavid du Colombier 						while(pt1 = pt->r2.lb1)
365219b2ee8SDavid du Colombier 							pt = pt1;
366219b2ee8SDavid du Colombier 						pt->r2.lb1 = rep;
367219b2ee8SDavid du Colombier 					} else
368219b2ee8SDavid du Colombier 						labtab->chain = rep;
369219b2ee8SDavid du Colombier 					break;
370219b2ee8SDavid du Colombier 				}
371219b2ee8SDavid du Colombier 				tp = lab->asc;
372219b2ee8SDavid du Colombier 				while((*tp = *cp++) && *tp != ';')
373219b2ee8SDavid du Colombier 					if(++tp >= &(lab->asc[8])) {
374219b2ee8SDavid du Colombier 						fprintf(stderr, LTL, linebuf);
375219b2ee8SDavid du Colombier 						exit(2);
376219b2ee8SDavid du Colombier 					}
377219b2ee8SDavid du Colombier 				cp--;
378219b2ee8SDavid du Colombier 				*tp = '\0';
379219b2ee8SDavid du Colombier 				if(*lab->asc == 0) {
380219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
381219b2ee8SDavid du Colombier 					exit(2);
382219b2ee8SDavid du Colombier 				}
383219b2ee8SDavid du Colombier 
384219b2ee8SDavid du Colombier 				if(lpt = search(lab)) {
385219b2ee8SDavid du Colombier 					if(lpt->address) {
386219b2ee8SDavid du Colombier 						rep->r2.lb1 = lpt->address;
387219b2ee8SDavid du Colombier 					} else {
388219b2ee8SDavid du Colombier 						pt = lpt->chain;
389219b2ee8SDavid du Colombier 						while(pt1 = pt->r2.lb1)
390219b2ee8SDavid du Colombier 							pt = pt1;
391219b2ee8SDavid du Colombier 						pt->r2.lb1 = rep;
392219b2ee8SDavid du Colombier 					}
393219b2ee8SDavid du Colombier 				} else {
394219b2ee8SDavid du Colombier 					lab->chain = rep;
395219b2ee8SDavid du Colombier 					lab->address = 0;
396219b2ee8SDavid du Colombier 					if(++lab >= labend) {
397219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: Too many labels: %s\n", linebuf);
398219b2ee8SDavid du Colombier 						exit(2);
399219b2ee8SDavid du Colombier 					}
400219b2ee8SDavid du Colombier 				}
401219b2ee8SDavid du Colombier 				break;
402219b2ee8SDavid du Colombier 
403219b2ee8SDavid du Colombier 			case 'n':
404219b2ee8SDavid du Colombier 				rep->r1.command = NCOM;
405219b2ee8SDavid du Colombier 				break;
406219b2ee8SDavid du Colombier 
407219b2ee8SDavid du Colombier 			case 'N':
408219b2ee8SDavid du Colombier 				rep->r1.command = CNCOM;
409219b2ee8SDavid du Colombier 				break;
410219b2ee8SDavid du Colombier 
411219b2ee8SDavid du Colombier 			case 'p':
412219b2ee8SDavid du Colombier 				rep->r1.command = PCOM;
413219b2ee8SDavid du Colombier 				break;
414219b2ee8SDavid du Colombier 
415219b2ee8SDavid du Colombier 			case 'P':
416219b2ee8SDavid du Colombier 				rep->r1.command = CPCOM;
417219b2ee8SDavid du Colombier 				break;
418219b2ee8SDavid du Colombier 
419219b2ee8SDavid du Colombier 			case 'r':
420219b2ee8SDavid du Colombier 				rep->r1.command = RCOM;
421219b2ee8SDavid du Colombier 				if(rep->r1.ad2) {
422219b2ee8SDavid du Colombier 					fprintf(stderr, AD1MES, linebuf);
423219b2ee8SDavid du Colombier 					exit(2);
424219b2ee8SDavid du Colombier 				}
425219b2ee8SDavid du Colombier 				if(*cp++ != ' ') {
426219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
427219b2ee8SDavid du Colombier 					exit(2);
428219b2ee8SDavid du Colombier 				}
429219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
430219b2ee8SDavid du Colombier 				p = text(rep->r1.re1);
431219b2ee8SDavid du Colombier 				break;
432219b2ee8SDavid du Colombier 
433219b2ee8SDavid du Colombier 			case 'd':
434219b2ee8SDavid du Colombier 				rep->r1.command = DCOM;
435219b2ee8SDavid du Colombier 				break;
436219b2ee8SDavid du Colombier 
437219b2ee8SDavid du Colombier 			case 'D':
438219b2ee8SDavid du Colombier 				rep->r1.command = CDCOM;
439219b2ee8SDavid du Colombier 				rep->r2.lb1 = ptrspace;
440219b2ee8SDavid du Colombier 				break;
441219b2ee8SDavid du Colombier 
442219b2ee8SDavid du Colombier 			case 'q':
443219b2ee8SDavid du Colombier 				rep->r1.command = QCOM;
444219b2ee8SDavid du Colombier 				if(rep->r1.ad2) {
445219b2ee8SDavid du Colombier 					fprintf(stderr, AD1MES, linebuf);
446219b2ee8SDavid du Colombier 					exit(2);
447219b2ee8SDavid du Colombier 				}
448219b2ee8SDavid du Colombier 				break;
449219b2ee8SDavid du Colombier 
450219b2ee8SDavid du Colombier 			case 'l':
451219b2ee8SDavid du Colombier 				rep->r1.command = LCOM;
452219b2ee8SDavid du Colombier 				break;
453219b2ee8SDavid du Colombier 
454219b2ee8SDavid du Colombier 			case 's':
455219b2ee8SDavid du Colombier 				rep->r1.command = SCOM;
456219b2ee8SDavid du Colombier 				seof = *cp++;
457219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
458219b2ee8SDavid du Colombier 				p = compile(rep->r1.re1);
459219b2ee8SDavid du Colombier 				if(p == badp) {
460219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
461219b2ee8SDavid du Colombier 					exit(2);
462219b2ee8SDavid du Colombier 				}
463219b2ee8SDavid du Colombier 				if(p == rep->r1.re1) {
464219b2ee8SDavid du Colombier 					if(op == NULL) {
465219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: First RE may not be null.\n");
466219b2ee8SDavid du Colombier 						exit(2);
467219b2ee8SDavid du Colombier 					}
468219b2ee8SDavid du Colombier 					rep->r1.re1 = op;
469219b2ee8SDavid du Colombier 				} else {
470219b2ee8SDavid du Colombier 					op = rep->r1.re1;
471219b2ee8SDavid du Colombier 				}
472219b2ee8SDavid du Colombier 
473219b2ee8SDavid du Colombier 				if((rep->r1.rhs = p) > reend) {
474219b2ee8SDavid du Colombier 					fprintf(stderr, TMMES, linebuf);
475219b2ee8SDavid du Colombier 					exit(2);
476219b2ee8SDavid du Colombier 				}
477219b2ee8SDavid du Colombier 
478219b2ee8SDavid du Colombier 				if((p = compsub(rep->r1.rhs)) == badp) {
479219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
480219b2ee8SDavid du Colombier 					exit(2);
481219b2ee8SDavid du Colombier 				}
482219b2ee8SDavid du Colombier 				if(*cp == 'g') {
483219b2ee8SDavid du Colombier 					cp++;
484219b2ee8SDavid du Colombier 					rep->r1.gfl++;
485219b2ee8SDavid du Colombier 				} else if(gflag)
486219b2ee8SDavid du Colombier 					rep->r1.gfl++;
487219b2ee8SDavid du Colombier 
488219b2ee8SDavid du Colombier 				if(*cp == 'p') {
489219b2ee8SDavid du Colombier 					cp++;
490219b2ee8SDavid du Colombier 					rep->r1.pfl = 1;
491219b2ee8SDavid du Colombier 				}
492219b2ee8SDavid du Colombier 
493219b2ee8SDavid du Colombier 				if(*cp == 'P') {
494219b2ee8SDavid du Colombier 					cp++;
495219b2ee8SDavid du Colombier 					rep->r1.pfl = 2;
496219b2ee8SDavid du Colombier 				}
497219b2ee8SDavid du Colombier 
498219b2ee8SDavid du Colombier 				if(*cp == 'w') {
499219b2ee8SDavid du Colombier 					cp++;
500219b2ee8SDavid du Colombier 					if(*cp++ !=  ' ') {
501219b2ee8SDavid du Colombier 						fprintf(stderr, CGMES, linebuf);
502219b2ee8SDavid du Colombier 						exit(2);
503219b2ee8SDavid du Colombier 					}
504219b2ee8SDavid du Colombier 					if(nfiles >= MAXFILES) {
505219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: Too many files in w commands 1 \n");
506219b2ee8SDavid du Colombier 						exit(2);
507219b2ee8SDavid du Colombier 					}
508219b2ee8SDavid du Colombier 
509219b2ee8SDavid du Colombier 					text((uchar*)fname[nfiles]);
510219b2ee8SDavid du Colombier 					for(i = nfiles - 1; i >= 0; i--)
511219b2ee8SDavid du Colombier 						if(cmp((uchar*)fname[nfiles],(uchar*)fname[i]) == 0) {
512219b2ee8SDavid du Colombier 							rep->r1.fcode = fcode[i];
513219b2ee8SDavid du Colombier 							goto done;
514219b2ee8SDavid du Colombier 						}
515219b2ee8SDavid du Colombier 					if((rep->r1.fcode = fopen(fname[nfiles], "w")) == NULL) {
516219b2ee8SDavid du Colombier 						fprintf(stderr, "sed: Cannot open %s\n", fname[nfiles]);
517219b2ee8SDavid du Colombier 						exit(2);
518219b2ee8SDavid du Colombier 					}
519219b2ee8SDavid du Colombier 					fcode[nfiles++] = rep->r1.fcode;
520219b2ee8SDavid du Colombier 				}
521219b2ee8SDavid du Colombier 				break;
522219b2ee8SDavid du Colombier 
523219b2ee8SDavid du Colombier 			case 'w':
524219b2ee8SDavid du Colombier 				rep->r1.command = WCOM;
525219b2ee8SDavid du Colombier 				if(*cp++ != ' ') {
526219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
527219b2ee8SDavid du Colombier 					exit(2);
528219b2ee8SDavid du Colombier 				}
529219b2ee8SDavid du Colombier 				if(nfiles >= MAXFILES){
530219b2ee8SDavid du Colombier 					fprintf(stderr, "sed: Too many files in w commands 2 \n");
531219b2ee8SDavid du Colombier 					fprintf(stderr, "nfiles = %d; MAXF = %d\n", nfiles, MAXFILES);
532219b2ee8SDavid du Colombier 					exit(2);
533219b2ee8SDavid du Colombier 				}
534219b2ee8SDavid du Colombier 
535219b2ee8SDavid du Colombier 				text((uchar*)fname[nfiles]);
536219b2ee8SDavid du Colombier 				for(i = nfiles - 1; i >= 0; i--)
537219b2ee8SDavid du Colombier 					if(cmp((uchar*)fname[nfiles], (uchar*)fname[i]) == 0) {
538219b2ee8SDavid du Colombier 						rep->r1.fcode = fcode[i];
539219b2ee8SDavid du Colombier 						goto done;
540219b2ee8SDavid du Colombier 					}
541219b2ee8SDavid du Colombier 
542219b2ee8SDavid du Colombier 				if((rep->r1.fcode = fopen(fname[nfiles], "w")) == NULL) {
543219b2ee8SDavid du Colombier 					fprintf(stderr, "sed: Cannot create %s\n", fname[nfiles]);
544219b2ee8SDavid du Colombier 					exit(2);
545219b2ee8SDavid du Colombier 				}
546219b2ee8SDavid du Colombier 				fcode[nfiles++] = rep->r1.fcode;
547219b2ee8SDavid du Colombier 				break;
548219b2ee8SDavid du Colombier 
549219b2ee8SDavid du Colombier 			case 'x':
550219b2ee8SDavid du Colombier 				rep->r1.command = XCOM;
551219b2ee8SDavid du Colombier 				break;
552219b2ee8SDavid du Colombier 
553219b2ee8SDavid du Colombier 			case 'y':
554219b2ee8SDavid du Colombier 				rep->r1.command = YCOM;
555219b2ee8SDavid du Colombier 				seof = *cp++;
556219b2ee8SDavid du Colombier 				rep->r1.re1 = p;
557219b2ee8SDavid du Colombier 				p = ycomp(rep->r1.re1);
558219b2ee8SDavid du Colombier 				if(p == badp) {
559219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
560219b2ee8SDavid du Colombier 					exit(2);
561219b2ee8SDavid du Colombier 				}
562219b2ee8SDavid du Colombier 				if(p > reend) {
563219b2ee8SDavid du Colombier 					fprintf(stderr, TMMES, linebuf);
564219b2ee8SDavid du Colombier 					exit(2);
565219b2ee8SDavid du Colombier 				}
566219b2ee8SDavid du Colombier 				break;
567219b2ee8SDavid du Colombier 
568219b2ee8SDavid du Colombier 		}
569219b2ee8SDavid du Colombier done:
570219b2ee8SDavid du Colombier 		if(++rep >= ptrend) {
571219b2ee8SDavid du Colombier 			fprintf(stderr, "sed: Too many commands, last: %s\n", linebuf);
572219b2ee8SDavid du Colombier 			exit(2);
573219b2ee8SDavid du Colombier 		}
574219b2ee8SDavid du Colombier 
575219b2ee8SDavid du Colombier 		rep->r1.ad1 = p;
576219b2ee8SDavid du Colombier 
577219b2ee8SDavid du Colombier 		if(*cp++ != '\0') {
578219b2ee8SDavid du Colombier 			if(cp[-1] == ';')
579219b2ee8SDavid du Colombier 				goto comploop;
580219b2ee8SDavid du Colombier 			fprintf(stderr, CGMES, linebuf);
581219b2ee8SDavid du Colombier 			exit(2);
582219b2ee8SDavid du Colombier 		}
583219b2ee8SDavid du Colombier 
584219b2ee8SDavid du Colombier 	}
585219b2ee8SDavid du Colombier }
586219b2ee8SDavid du Colombier 
587219b2ee8SDavid du Colombier uchar	*
compsub(uchar * rhsbuf)588219b2ee8SDavid du Colombier compsub(uchar *rhsbuf)
589219b2ee8SDavid du Colombier {
590219b2ee8SDavid du Colombier 	uchar	*p, *q, *r;
591219b2ee8SDavid du Colombier 	p = rhsbuf;
592219b2ee8SDavid du Colombier 	q = cp;
593219b2ee8SDavid du Colombier 	for(;;) {
594219b2ee8SDavid du Colombier 		if((*p = *q++) == '\\') {
595219b2ee8SDavid du Colombier 			*++p = *q++;
596219b2ee8SDavid du Colombier 			if(*p >= '1' && *p <= '9' && *p > numbra + '0')
597219b2ee8SDavid du Colombier 				return(badp);
598219b2ee8SDavid du Colombier 			if(*p == 'n')
599219b2ee8SDavid du Colombier 				*--p = '\n';
600219b2ee8SDavid du Colombier 		} else if(*p == seof) {
601219b2ee8SDavid du Colombier 			*p++ = '\0';
602219b2ee8SDavid du Colombier 			cp = q;
603219b2ee8SDavid du Colombier 			return(p);
604219b2ee8SDavid du Colombier 		}
605219b2ee8SDavid du Colombier 		if(*p++ == '\0') {
606219b2ee8SDavid du Colombier 			return(badp);
607219b2ee8SDavid du Colombier 		}
608219b2ee8SDavid du Colombier 
609219b2ee8SDavid du Colombier 	}
610219b2ee8SDavid du Colombier }
611219b2ee8SDavid du Colombier 
612219b2ee8SDavid du Colombier uchar *
compile(uchar * expbuf)613219b2ee8SDavid du Colombier compile(uchar *expbuf)
614219b2ee8SDavid du Colombier {
615219b2ee8SDavid du Colombier 	int c;
616219b2ee8SDavid du Colombier 	uchar *ep, *sp;
617219b2ee8SDavid du Colombier 	uchar	neg;
618219b2ee8SDavid du Colombier 	uchar *lastep, *cstart;
619219b2ee8SDavid du Colombier 	int cclcnt;
620219b2ee8SDavid du Colombier 	int	closed;
621219b2ee8SDavid du Colombier 	uchar	bracket[NBRA], *bracketp;
622219b2ee8SDavid du Colombier 
623219b2ee8SDavid du Colombier 	if(*cp == seof) {
624219b2ee8SDavid du Colombier 		cp++;
625219b2ee8SDavid du Colombier 		return(expbuf);
626219b2ee8SDavid du Colombier 	}
627219b2ee8SDavid du Colombier 
628219b2ee8SDavid du Colombier 	ep = expbuf;
629219b2ee8SDavid du Colombier 	lastep = 0;
630219b2ee8SDavid du Colombier 	bracketp = bracket;
631219b2ee8SDavid du Colombier 	closed = numbra = 0;
632219b2ee8SDavid du Colombier 	sp = cp;
633219b2ee8SDavid du Colombier 	if (*sp == '^') {
634219b2ee8SDavid du Colombier 		*ep++ = 1;
635219b2ee8SDavid du Colombier 		sp++;
636219b2ee8SDavid du Colombier 	} else {
637219b2ee8SDavid du Colombier 		*ep++ = 0;
638219b2ee8SDavid du Colombier 	}
639219b2ee8SDavid du Colombier 	for (;;) {
640219b2ee8SDavid du Colombier 		if (ep >= reend) {
641219b2ee8SDavid du Colombier 			cp = sp;
642219b2ee8SDavid du Colombier 			return(badp);
643219b2ee8SDavid du Colombier 		}
644219b2ee8SDavid du Colombier 		if((c = *sp++) == seof) {
645219b2ee8SDavid du Colombier 			if(bracketp != bracket) {
646219b2ee8SDavid du Colombier 				cp = sp;
647219b2ee8SDavid du Colombier 				return(badp);
648219b2ee8SDavid du Colombier 			}
649219b2ee8SDavid du Colombier 			cp = sp;
650219b2ee8SDavid du Colombier 			*ep++ = CEOF;
651219b2ee8SDavid du Colombier 			return(ep);
652219b2ee8SDavid du Colombier 		}
653219b2ee8SDavid du Colombier 		if(c != '*')
654219b2ee8SDavid du Colombier 			lastep = ep;
655219b2ee8SDavid du Colombier 		switch (c) {
656219b2ee8SDavid du Colombier 
657219b2ee8SDavid du Colombier 		case '\\':
658219b2ee8SDavid du Colombier 			if((c = *sp++) == '(') {
659219b2ee8SDavid du Colombier 				if(numbra >= NBRA) {
660219b2ee8SDavid du Colombier 					cp = sp;
661219b2ee8SDavid du Colombier 					return(badp);
662219b2ee8SDavid du Colombier 				}
663219b2ee8SDavid du Colombier 				*bracketp++ = numbra;
664219b2ee8SDavid du Colombier 				*ep++ = CBRA;
665219b2ee8SDavid du Colombier 				*ep++ = numbra++;
666219b2ee8SDavid du Colombier 				continue;
667219b2ee8SDavid du Colombier 			}
668219b2ee8SDavid du Colombier 			if(c == ')') {
669219b2ee8SDavid du Colombier 				if(bracketp <= bracket) {
670219b2ee8SDavid du Colombier 					cp = sp;
671219b2ee8SDavid du Colombier 					return(badp);
672219b2ee8SDavid du Colombier 				}
673219b2ee8SDavid du Colombier 				*ep++ = CKET;
674219b2ee8SDavid du Colombier 				*ep++ = *--bracketp;
675219b2ee8SDavid du Colombier 				closed++;
676219b2ee8SDavid du Colombier 				continue;
677219b2ee8SDavid du Colombier 			}
678219b2ee8SDavid du Colombier 
679219b2ee8SDavid du Colombier 			if(c >= '1' && c <= '9') {
680219b2ee8SDavid du Colombier 				if((c -= '1') >= closed)
681219b2ee8SDavid du Colombier 					return(badp);
682219b2ee8SDavid du Colombier 
683219b2ee8SDavid du Colombier 				*ep++ = CBACK;
684219b2ee8SDavid du Colombier 				*ep++ = c;
685219b2ee8SDavid du Colombier 				continue;
686219b2ee8SDavid du Colombier 			}
687219b2ee8SDavid du Colombier 			if(c == '\n') {
688219b2ee8SDavid du Colombier 				cp = sp;
689219b2ee8SDavid du Colombier 				return(badp);
690219b2ee8SDavid du Colombier 			}
691219b2ee8SDavid du Colombier 			if(c == 'n') {
692219b2ee8SDavid du Colombier 				c = '\n';
693219b2ee8SDavid du Colombier 			}
694219b2ee8SDavid du Colombier 			goto defchar;
695219b2ee8SDavid du Colombier 
696219b2ee8SDavid du Colombier 		case '\0':
697219b2ee8SDavid du Colombier 		case '\n':
698219b2ee8SDavid du Colombier 			cp = sp;
699219b2ee8SDavid du Colombier 			return(badp);
700219b2ee8SDavid du Colombier 
701219b2ee8SDavid du Colombier 		case '.':
702219b2ee8SDavid du Colombier 			*ep++ = CDOT;
703219b2ee8SDavid du Colombier 			continue;
704219b2ee8SDavid du Colombier 
705219b2ee8SDavid du Colombier 		case '*':
706219b2ee8SDavid du Colombier 			if (lastep == 0)
707219b2ee8SDavid du Colombier 				goto defchar;
708219b2ee8SDavid du Colombier 			if(*lastep == CKET) {
709219b2ee8SDavid du Colombier 				cp = sp;
710219b2ee8SDavid du Colombier 				return(badp);
711219b2ee8SDavid du Colombier 			}
712219b2ee8SDavid du Colombier 			*lastep |= STAR;
713219b2ee8SDavid du Colombier 			continue;
714219b2ee8SDavid du Colombier 
715219b2ee8SDavid du Colombier 		case '$':
716219b2ee8SDavid du Colombier 			if (*sp != seof)
717219b2ee8SDavid du Colombier 				goto defchar;
718219b2ee8SDavid du Colombier 			*ep++ = CDOL;
719219b2ee8SDavid du Colombier 			continue;
720219b2ee8SDavid du Colombier 
721219b2ee8SDavid du Colombier 		case '[':
722219b2ee8SDavid du Colombier 			if(&ep[33] >= reend) {
723219b2ee8SDavid du Colombier 				fprintf(stderr, "sed: RE too long: %s\n", linebuf);
724219b2ee8SDavid du Colombier 				exit(2);
725219b2ee8SDavid du Colombier 			}
726219b2ee8SDavid du Colombier 
727219b2ee8SDavid du Colombier 			*ep++ = CCL;
728219b2ee8SDavid du Colombier 
729219b2ee8SDavid du Colombier 			neg = 0;
730219b2ee8SDavid du Colombier 			if((c = *sp++) == '^') {
731219b2ee8SDavid du Colombier 				neg = 1;
732219b2ee8SDavid du Colombier 				c = *sp++;
733219b2ee8SDavid du Colombier 			}
734219b2ee8SDavid du Colombier 
735219b2ee8SDavid du Colombier 			cstart = sp;
736219b2ee8SDavid du Colombier 			do {
737219b2ee8SDavid du Colombier 				if(c == '\0') {
738219b2ee8SDavid du Colombier 					fprintf(stderr, CGMES, linebuf);
739219b2ee8SDavid du Colombier 					exit(2);
740219b2ee8SDavid du Colombier 				}
741219b2ee8SDavid du Colombier 				if (c=='-' && sp>cstart && *sp!=']') {
742219b2ee8SDavid du Colombier 					for (c = sp[-2]; c<*sp; c++)
743219b2ee8SDavid du Colombier 						ep[c>>3] |= bittab[c&07];
744219b2ee8SDavid du Colombier 				}
745219b2ee8SDavid du Colombier 				if(c == '\\') {
746219b2ee8SDavid du Colombier 					switch(c = *sp++) {
747219b2ee8SDavid du Colombier 						case 'n':
748219b2ee8SDavid du Colombier 							c = '\n';
749219b2ee8SDavid du Colombier 							break;
750219b2ee8SDavid du Colombier 					}
751219b2ee8SDavid du Colombier 				}
752219b2ee8SDavid du Colombier 
753219b2ee8SDavid du Colombier 				ep[c >> 3] |= bittab[c & 07];
754219b2ee8SDavid du Colombier 			} while((c = *sp++) != ']');
755219b2ee8SDavid du Colombier 
756219b2ee8SDavid du Colombier 			if(neg)
757219b2ee8SDavid du Colombier 				for(cclcnt = 0; cclcnt < 32; cclcnt++)
758219b2ee8SDavid du Colombier 					ep[cclcnt] ^= -1;
759219b2ee8SDavid du Colombier 			ep[0] &= 0376;
760219b2ee8SDavid du Colombier 
761219b2ee8SDavid du Colombier 			ep += 32;
762219b2ee8SDavid du Colombier 
763219b2ee8SDavid du Colombier 			continue;
764219b2ee8SDavid du Colombier 
765219b2ee8SDavid du Colombier 		defchar:
766219b2ee8SDavid du Colombier 		default:
767219b2ee8SDavid du Colombier 			*ep++ = CCHR;
768219b2ee8SDavid du Colombier 			*ep++ = c;
769219b2ee8SDavid du Colombier 		}
770219b2ee8SDavid du Colombier 	}
771219b2ee8SDavid du Colombier }
772219b2ee8SDavid du Colombier int
rline(uchar * lbuf)773219b2ee8SDavid du Colombier rline(uchar *lbuf)
774219b2ee8SDavid du Colombier {
775219b2ee8SDavid du Colombier 	uchar	*p, *q;
776219b2ee8SDavid du Colombier 	int	t;
777219b2ee8SDavid du Colombier 	static uchar	*saveq;
778219b2ee8SDavid du Colombier 
779219b2ee8SDavid du Colombier 	p = lbuf - 1;
780219b2ee8SDavid du Colombier 
781219b2ee8SDavid du Colombier 	if(eflag) {
782219b2ee8SDavid du Colombier 		if(eflag > 0) {
783219b2ee8SDavid du Colombier 			eflag = -1;
784219b2ee8SDavid du Colombier 			if(eargc-- <= 0)
785219b2ee8SDavid du Colombier 				exit(2);
786219b2ee8SDavid du Colombier 			q = *++eargv;
787219b2ee8SDavid du Colombier 			while(*++p = *q++) {
788219b2ee8SDavid du Colombier 				if(*p == '\\') {
789219b2ee8SDavid du Colombier 					if((*++p = *q++) == '\0') {
790219b2ee8SDavid du Colombier 						saveq = 0;
791219b2ee8SDavid du Colombier 						return(-1);
792219b2ee8SDavid du Colombier 					} else
793219b2ee8SDavid du Colombier 						continue;
794219b2ee8SDavid du Colombier 				}
795219b2ee8SDavid du Colombier 				if(*p == '\n') {
796219b2ee8SDavid du Colombier 					*p = '\0';
797219b2ee8SDavid du Colombier 					saveq = q;
798219b2ee8SDavid du Colombier 					return(1);
799219b2ee8SDavid du Colombier 				}
800219b2ee8SDavid du Colombier 			}
801219b2ee8SDavid du Colombier 			saveq = 0;
802219b2ee8SDavid du Colombier 			return(1);
803219b2ee8SDavid du Colombier 		}
804219b2ee8SDavid du Colombier 		if((q = saveq) == 0)	return(-1);
805219b2ee8SDavid du Colombier 
806219b2ee8SDavid du Colombier 		while(*++p = *q++) {
807219b2ee8SDavid du Colombier 			if(*p == '\\') {
808219b2ee8SDavid du Colombier 				if((*++p = *q++) == '0') {
809219b2ee8SDavid du Colombier 					saveq = 0;
810219b2ee8SDavid du Colombier 					return(-1);
811219b2ee8SDavid du Colombier 				} else
812219b2ee8SDavid du Colombier 					continue;
813219b2ee8SDavid du Colombier 			}
814219b2ee8SDavid du Colombier 			if(*p == '\n') {
815219b2ee8SDavid du Colombier 				*p = '\0';
816219b2ee8SDavid du Colombier 				saveq = q;
817219b2ee8SDavid du Colombier 				return(1);
818219b2ee8SDavid du Colombier 			}
819219b2ee8SDavid du Colombier 		}
820219b2ee8SDavid du Colombier 		saveq = 0;
821219b2ee8SDavid du Colombier 		return(1);
822219b2ee8SDavid du Colombier 	}
823219b2ee8SDavid du Colombier 
824219b2ee8SDavid du Colombier 	while((t = getc(fin)) != EOF) {
825219b2ee8SDavid du Colombier 		*++p = t;
826219b2ee8SDavid du Colombier 		if(*p == '\\') {
827219b2ee8SDavid du Colombier 			t = getc(fin);
828219b2ee8SDavid du Colombier 			*++p = t;
829219b2ee8SDavid du Colombier 		}
830219b2ee8SDavid du Colombier 		else if(*p == '\n') {
831219b2ee8SDavid du Colombier 			*p = '\0';
832219b2ee8SDavid du Colombier 			return(1);
833219b2ee8SDavid du Colombier 		}
834219b2ee8SDavid du Colombier 	}
835219b2ee8SDavid du Colombier 	*++p = '\0';
836219b2ee8SDavid du Colombier 	return(-1);
837219b2ee8SDavid du Colombier }
838219b2ee8SDavid du Colombier 
839219b2ee8SDavid du Colombier uchar *
address(uchar * expbuf)840219b2ee8SDavid du Colombier address(uchar *expbuf)
841219b2ee8SDavid du Colombier {
842219b2ee8SDavid du Colombier 	uchar	*rcp;
843219b2ee8SDavid du Colombier 	long	lno;
844219b2ee8SDavid du Colombier 
845219b2ee8SDavid du Colombier 	if(*cp == '$') {
846219b2ee8SDavid du Colombier 		cp++;
847219b2ee8SDavid du Colombier 		*expbuf++ = CEND;
848219b2ee8SDavid du Colombier 		*expbuf++ = CEOF;
849219b2ee8SDavid du Colombier 		return(expbuf);
850219b2ee8SDavid du Colombier 	}
851219b2ee8SDavid du Colombier 
852219b2ee8SDavid du Colombier 	if(*cp == '/') {
853219b2ee8SDavid du Colombier 		seof = '/';
854219b2ee8SDavid du Colombier 		cp++;
855219b2ee8SDavid du Colombier 		return(compile(expbuf));
856219b2ee8SDavid du Colombier 	}
857219b2ee8SDavid du Colombier 
858219b2ee8SDavid du Colombier 	rcp = cp;
859219b2ee8SDavid du Colombier 	lno = 0;
860219b2ee8SDavid du Colombier 
861219b2ee8SDavid du Colombier 	while(*rcp >= '0' && *rcp <= '9')
862219b2ee8SDavid du Colombier 		lno = lno*10 + *rcp++ - '0';
863219b2ee8SDavid du Colombier 
864219b2ee8SDavid du Colombier 	if(rcp > cp) {
865219b2ee8SDavid du Colombier 		if(!lno){
866219b2ee8SDavid du Colombier 			fprintf(stderr, "sed: line number 0 is illegal\n");
867219b2ee8SDavid du Colombier 			exit(2);
868219b2ee8SDavid du Colombier 		}
869219b2ee8SDavid du Colombier 		*expbuf++ = CLNUM;
870219b2ee8SDavid du Colombier 		*expbuf++ = lno;
871219b2ee8SDavid du Colombier 		*expbuf++ = lno >> 8;
872219b2ee8SDavid du Colombier 		*expbuf++ = lno >> 16;
873219b2ee8SDavid du Colombier 		*expbuf++ = lno >> 24;
874219b2ee8SDavid du Colombier 		*expbuf++ = CEOF;
875219b2ee8SDavid du Colombier 		cp = rcp;
876219b2ee8SDavid du Colombier 		return(expbuf);
877219b2ee8SDavid du Colombier 	}
878219b2ee8SDavid du Colombier 	return(0);
879219b2ee8SDavid du Colombier }
880219b2ee8SDavid du Colombier int
cmp(uchar * a,uchar * b)881219b2ee8SDavid du Colombier cmp(uchar *a, uchar *b)
882219b2ee8SDavid du Colombier {
883219b2ee8SDavid du Colombier 	uchar	*ra, *rb;
884219b2ee8SDavid du Colombier 
885219b2ee8SDavid du Colombier 	ra = a - 1;
886219b2ee8SDavid du Colombier 	rb = b - 1;
887219b2ee8SDavid du Colombier 
888219b2ee8SDavid du Colombier 	while(*++ra == *++rb)
889219b2ee8SDavid du Colombier 		if(*ra == '\0')	return(0);
890219b2ee8SDavid du Colombier 	return(1);
891219b2ee8SDavid du Colombier }
892219b2ee8SDavid du Colombier 
893219b2ee8SDavid du Colombier uchar *
text(uchar * textbuf)894219b2ee8SDavid du Colombier text(uchar *textbuf)
895219b2ee8SDavid du Colombier {
896219b2ee8SDavid du Colombier 	uchar	*p, *q;
897219b2ee8SDavid du Colombier 
898219b2ee8SDavid du Colombier 	p = textbuf;
899219b2ee8SDavid du Colombier 	q = cp;
900219b2ee8SDavid du Colombier 	while(*q == '\t' || *q == ' ')	q++;
901219b2ee8SDavid du Colombier 	for(;;) {
902219b2ee8SDavid du Colombier 
903219b2ee8SDavid du Colombier 		if((*p = *q++) == '\\')
904219b2ee8SDavid du Colombier 			*p = *q++;
905219b2ee8SDavid du Colombier 		if(*p == '\0') {
906219b2ee8SDavid du Colombier 			cp = --q;
907219b2ee8SDavid du Colombier 			return(++p);
908219b2ee8SDavid du Colombier 		}
909219b2ee8SDavid du Colombier 		if(*p == '\n') {
910219b2ee8SDavid du Colombier 			while(*q == '\t' || *q == ' ')	q++;
911219b2ee8SDavid du Colombier 		}
912219b2ee8SDavid du Colombier 		p++;
913219b2ee8SDavid du Colombier 	}
914219b2ee8SDavid du Colombier }
915219b2ee8SDavid du Colombier 
916219b2ee8SDavid du Colombier 
917219b2ee8SDavid du Colombier struct label *
search(struct label * ptr)918219b2ee8SDavid du Colombier search(struct label *ptr)
919219b2ee8SDavid du Colombier {
920219b2ee8SDavid du Colombier 	struct label	*rp;
921219b2ee8SDavid du Colombier 
922219b2ee8SDavid du Colombier 	rp = labtab;
923219b2ee8SDavid du Colombier 	while(rp < ptr) {
924219b2ee8SDavid du Colombier 		if(cmp(rp->asc, ptr->asc) == 0)
925219b2ee8SDavid du Colombier 			return(rp);
926219b2ee8SDavid du Colombier 		rp++;
927219b2ee8SDavid du Colombier 	}
928219b2ee8SDavid du Colombier 
929219b2ee8SDavid du Colombier 	return(0);
930219b2ee8SDavid du Colombier }
931219b2ee8SDavid du Colombier 
932219b2ee8SDavid du Colombier void
dechain(void)933219b2ee8SDavid du Colombier dechain(void)
934219b2ee8SDavid du Colombier {
935219b2ee8SDavid du Colombier 	struct label	*lptr;
936219b2ee8SDavid du Colombier 	union reptr	*rptr, *trptr;
937219b2ee8SDavid du Colombier 
938219b2ee8SDavid du Colombier 	for(lptr = labtab; lptr < lab; lptr++) {
939219b2ee8SDavid du Colombier 
940219b2ee8SDavid du Colombier 		if(lptr->address == 0) {
941219b2ee8SDavid du Colombier 			fprintf(stderr, "sed: Undefined label: %s\n", lptr->asc);
942219b2ee8SDavid du Colombier 			exit(2);
943219b2ee8SDavid du Colombier 		}
944219b2ee8SDavid du Colombier 
945219b2ee8SDavid du Colombier 		if(lptr->chain) {
946219b2ee8SDavid du Colombier 			rptr = lptr->chain;
947219b2ee8SDavid du Colombier 			while(trptr = rptr->r2.lb1) {
948219b2ee8SDavid du Colombier 				rptr->r2.lb1 = lptr->address;
949219b2ee8SDavid du Colombier 				rptr = trptr;
950219b2ee8SDavid du Colombier 			}
951219b2ee8SDavid du Colombier 			rptr->r2.lb1 = lptr->address;
952219b2ee8SDavid du Colombier 		}
953219b2ee8SDavid du Colombier 	}
954219b2ee8SDavid du Colombier }
955219b2ee8SDavid du Colombier 
956219b2ee8SDavid du Colombier uchar *
ycomp(uchar * expbuf)957219b2ee8SDavid du Colombier ycomp(uchar *expbuf)
958219b2ee8SDavid du Colombier {
959219b2ee8SDavid du Colombier 	uchar *ep, *tsp;
960219b2ee8SDavid du Colombier 	int c;
961219b2ee8SDavid du Colombier 	uchar	*sp;
962219b2ee8SDavid du Colombier 
963219b2ee8SDavid du Colombier 	ep = expbuf;
964219b2ee8SDavid du Colombier 	sp = cp;
965219b2ee8SDavid du Colombier 	for(tsp = cp; *tsp != seof; tsp++) {
966219b2ee8SDavid du Colombier 		if(*tsp == '\\')
967219b2ee8SDavid du Colombier 			tsp++;
968219b2ee8SDavid du Colombier 		if(*tsp == '\n' || *tsp == '\0')
969219b2ee8SDavid du Colombier 			return(badp);
970219b2ee8SDavid du Colombier 	}
971219b2ee8SDavid du Colombier 	tsp++;
972219b2ee8SDavid du Colombier 
973219b2ee8SDavid du Colombier 	while((c = *sp++) != seof) {
974219b2ee8SDavid du Colombier 		if(c == '\\' && *sp == 'n') {
975219b2ee8SDavid du Colombier 			sp++;
976219b2ee8SDavid du Colombier 			c = '\n';
977219b2ee8SDavid du Colombier 		}
978219b2ee8SDavid du Colombier 		if((ep[c] = *tsp++) == '\\' && *tsp == 'n') {
979219b2ee8SDavid du Colombier 			ep[c] = '\n';
980219b2ee8SDavid du Colombier 			tsp++;
981219b2ee8SDavid du Colombier 		}
982219b2ee8SDavid du Colombier 		if(ep[c] == seof || ep[c] == '\0')
983219b2ee8SDavid du Colombier 			return(badp);
984219b2ee8SDavid du Colombier 	}
985219b2ee8SDavid du Colombier 	if(*tsp != seof)
986219b2ee8SDavid du Colombier 		return(badp);
987219b2ee8SDavid du Colombier 	cp = ++tsp;
988219b2ee8SDavid du Colombier 
989219b2ee8SDavid du Colombier 	for(c = 0; c<0400; c++)
990219b2ee8SDavid du Colombier 		if(ep[c] == 0)
991219b2ee8SDavid du Colombier 			ep[c] = c;
992219b2ee8SDavid du Colombier 
993219b2ee8SDavid du Colombier 	return(ep + 0400);
994219b2ee8SDavid du Colombier }
995219b2ee8SDavid du Colombier 
996