xref: /freebsd/contrib/tcsh/sh.glob.c (revision 17d6c636720d00f77e5d098daf4c278f89d84f7b)
1 /* $Header: /src/pub/tcsh/sh.glob.c,v 3.48 2001/01/04 18:51:57 christos Exp $ */
2 /*
3  * sh.glob.c: Regular expression expansion
4  */
5 /*-
6  * Copyright (c) 1980, 1991 The Regents of the University of California.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  * 3. All advertising materials mentioning features or use of this software
18  *    must display the following acknowledgement:
19  *	This product includes software developed by the University of
20  *	California, Berkeley and its contributors.
21  * 4. Neither the name of the University nor the names of its contributors
22  *    may be used to endorse or promote products derived from this software
23  *    without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
26  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
29  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35  * SUCH DAMAGE.
36  */
37 #include "sh.h"
38 
39 RCSID("$Id: sh.glob.c,v 3.48 2001/01/04 18:51:57 christos Exp $")
40 
41 #include "tc.h"
42 
43 #include "glob.h"
44 
45 static int noglob;
46 static int pargsiz, gargsiz;
47 
48 /*
49  * Values for gflag
50  */
51 #define	G_NONE	0		/* No globbing needed			*/
52 #define	G_GLOB	1		/* string contains *?[] characters	*/
53 #define	G_CSH	2		/* string contains ~`{ characters	*/
54 
55 #define	GLOBSPACE	100	/* Alloc increment			*/
56 #define LONGBSIZE	10240	/* Backquote expansion buffer size	*/
57 
58 
59 #define LBRC '{'
60 #define RBRC '}'
61 #define LBRK '['
62 #define RBRK ']'
63 #define EOS '\0'
64 
65 Char  **gargv = NULL;
66 int     gargc = 0;
67 Char  **pargv = NULL;
68 static int pargc = 0;
69 
70 /*
71  * globbing is now done in two stages. In the first pass we expand
72  * csh globbing idioms ~`{ and then we proceed doing the normal
73  * globbing if needed ?*[
74  *
75  * Csh type globbing is handled in globexpand() and the rest is
76  * handled in glob() which is part of the 4.4BSD libc.
77  *
78  */
79 static	Char	 *globtilde	__P((Char **, Char *));
80 static	Char     *handleone	__P((Char *, Char **, int));
81 static	Char	**libglob	__P((Char **));
82 static	Char	**globexpand	__P((Char **));
83 static	int	  globbrace	__P((Char *, Char *, Char ***));
84 static  void	  expbrace	__P((Char ***, Char ***, int));
85 static  int	  pmatch	__P((Char *, Char *, Char **));
86 static	void	  pword		__P((int));
87 static	void	  psave		__P((int));
88 static	void	  backeval	__P((Char *, bool));
89 
90 static Char *
91 globtilde(nv, s)
92     Char  **nv, *s;
93 {
94     Char    gbuf[BUFSIZE], *gstart, *b, *u, *e;
95 #ifdef apollo
96     int slash;
97 #endif
98 
99     gstart = gbuf;
100     *gstart++ = *s++;
101     u = s;
102     for (b = gstart, e = &gbuf[BUFSIZE - 1];
103 	 *s && *s != '/' && *s != ':' && b < e;
104 	 *b++ = *s++)
105 	continue;
106     *b = EOS;
107     if (gethdir(gstart)) {
108 	if (adrof(STRnonomatch))
109 	    return (--u);
110 	blkfree(nv);
111 	if (*gstart)
112 	    stderror(ERR_UNKUSER, short2str(gstart));
113 	else
114 	    stderror(ERR_NOHOME);
115     }
116     b = &gstart[Strlen(gstart)];
117 #ifdef apollo
118     slash = gstart[0] == '/' && gstart[1] == '\0';
119 #endif
120     while (*s)
121 	*b++ = *s++;
122     *b = EOS;
123     --u;
124     xfree((ptr_t) u);
125 #ifdef apollo
126     if (slash && gstart[1] == '/')
127 	gstart++;
128 #endif
129     return (Strsave(gstart));
130 }
131 
132 Char *
133 globequal(new, old)
134     Char *new, *old;
135 {
136     int     dig;
137     Char    *b, *d;
138 
139     /*
140      * kfk - 17 Jan 1984 - stack hack allows user to get at arbitrary dir names
141      * in stack. PWP: let =foobar pass through (for X windows)
142      */
143     if (old[1] == '-' && (old[2] == '\0' || old[2] == '/')) {
144 	/* =- */
145 	dig = -1;
146 	b = &old[2];
147     }
148     else if (Isdigit(old[1])) {
149 	/* =<number> */
150 	dig = old[1] - '0';
151 	for (b = &old[2]; Isdigit(*b); b++)
152 	    dig = dig * 10 + (*b - '0');
153 	if (*b != '\0' && *b != '/')
154 	    /* =<number>foobar */
155 	    return old;
156     }
157     else
158 	/* =foobar */
159 	return old;
160 
161     if (!getstakd(new, dig))
162 	return NULL;
163 
164     /* Copy the rest of the string */
165     for (d = &new[Strlen(new)];
166 	 d < &new[BUFSIZE - 1] && (*d++ = *b++) != '\0';)
167 	continue;
168     *d = '\0';
169 
170     return new;
171 }
172 
173 static int
174 globbrace(s, p, bl)
175     Char   *s, *p, ***bl;
176 {
177     int     i, len;
178     Char   *pm, *pe, *lm, *pl;
179     Char  **nv, **vl;
180     Char    gbuf[BUFSIZE];
181     int     size = GLOBSPACE;
182 
183     nv = vl = (Char **) xmalloc((size_t) (sizeof(Char *) * size));
184     *vl = NULL;
185 
186     len = 0;
187     /* copy part up to the brace */
188     for (lm = gbuf, p = s; *p != LBRC; *lm++ = *p++)
189 	continue;
190 
191     /* check for balanced braces */
192     for (i = 0, pe = ++p; *pe; pe++)
193 #ifdef DSPMBYTE
194 	if (Ismbyte1(*pe) && *(pe + 1) != EOS)
195 	    pe ++;
196 	else
197 #endif /* DSPMBYTE */
198 	if (*pe == LBRK) {
199 	    /* Ignore everything between [] */
200 	    for (++pe; *pe != RBRK && *pe != EOS; pe++)
201 #ifdef DSPMBYTE
202 	      if (Ismbyte1(*pe) && *(pe + 1) != EOS)
203 		pe ++;
204 	      else
205 #endif /* DSPMBYTE */
206 		continue;
207 	    if (*pe == EOS) {
208 		blkfree(nv);
209 		return (-RBRK);
210 	    }
211 	}
212 	else if (*pe == LBRC)
213 	    i++;
214 	else if (*pe == RBRC) {
215 	    if (i == 0)
216 		break;
217 	    i--;
218 	}
219 
220     if (i != 0 || *pe == '\0') {
221 	blkfree(nv);
222 	return (-RBRC);
223     }
224 
225     for (i = 0, pl = pm = p; pm <= pe; pm++)
226 #ifdef DSPMBYTE
227 	if (Ismbyte1(*pm) && pm + 1 <= pe)
228 	    pm ++;
229 	else
230 #endif /* DSPMBYTE */
231 	switch (*pm) {
232 	case LBRK:
233 	    for (++pm; *pm != RBRK && *pm != EOS; pm++)
234 #ifdef DSPMBYTE
235 	      if (Ismbyte1(*pm) && *(pm + 1) != EOS)
236 		pm ++;
237 	      else
238 #endif /* DSPMBYTE */
239 		continue;
240 	    if (*pm == EOS) {
241 		*vl = NULL;
242 		blkfree(nv);
243 		return (-RBRK);
244 	    }
245 	    break;
246 	case LBRC:
247 	    i++;
248 	    break;
249 	case RBRC:
250 	    if (i) {
251 		i--;
252 		break;
253 	    }
254 	    /* FALLTHROUGH */
255 	case ',':
256 	    if (i && *pm == ',')
257 		break;
258 	    else {
259 		Char    savec = *pm;
260 
261 		*pm = EOS;
262 		(void) Strcpy(lm, pl);
263 		(void) Strcat(gbuf, pe + 1);
264 		*pm = savec;
265 		*vl++ = Strsave(gbuf);
266 		len++;
267 		pl = pm + 1;
268 		if (vl == &nv[size]) {
269 		    size += GLOBSPACE;
270 		    nv = (Char **) xrealloc((ptr_t) nv,
271 					    (size_t) (size * sizeof(Char *)));
272 		    vl = &nv[size - GLOBSPACE];
273 		}
274 	    }
275 	    break;
276 	default:
277 	    break;
278 	}
279     *vl = NULL;
280     *bl = nv;
281     return (len);
282 }
283 
284 
285 static void
286 expbrace(nvp, elp, size)
287     Char ***nvp, ***elp;
288     int size;
289 {
290     Char **vl, **el, **nv, *s;
291 
292     vl = nv = *nvp;
293     if (elp != NULL)
294 	el = *elp;
295     else
296 	for (el = vl; *el; el++)
297 	    continue;
298 
299     for (s = *vl; s; s = *++vl) {
300 	Char   *b;
301 	Char  **vp, **bp;
302 
303 	/* leave {} untouched for find */
304 	if (s[0] == '{' && (s[1] == '\0' || (s[1] == '}' && s[2] == '\0')))
305 	    continue;
306 	if ((b = Strchr(s, '{')) != NULL) {
307 	    Char  **bl;
308 	    int     len;
309 
310 #if defined (DSPMBYTE)
311 	    if (b != s && Ismbyte2(*b) && Ismbyte1(*(b-1))) {
312 		/* The "{" is the 2nd byte of a MB character */
313 		continue;
314 	    }
315 #endif /* DSPMBYTE */
316 	    if ((len = globbrace(s, b, &bl)) < 0) {
317 		xfree((ptr_t) nv);
318 		stderror(ERR_MISSING, -len);
319 	    }
320 	    xfree((ptr_t) s);
321 	    if (len == 1) {
322 		*vl-- = *bl;
323 		xfree((ptr_t) bl);
324 		continue;
325 	    }
326 	    if (&el[len] >= &nv[size]) {
327 		int     l, e;
328 		l = (int) (&el[len] - &nv[size]);
329 		size += GLOBSPACE > l ? GLOBSPACE : l;
330 		l = (int) (vl - nv);
331 		e = (int) (el - nv);
332 		nv = (Char **) xrealloc((ptr_t) nv,
333 					(size_t) (size * sizeof(Char *)));
334 		vl = nv + l;
335 		el = nv + e;
336 	    }
337 	    /* nv vl   el     bl
338 	     * |  |    |      |
339 	     * -.--..--	      x--
340 	     *   |            len
341 	     *   vp
342 	     */
343 	    vp = vl--;
344 	    *vp = *bl;
345 	    len--;
346 	    for (bp = el; bp != vp; bp--)
347 		bp[len] = *bp;
348 	    el += len;
349 	    /* nv vl    el bl
350 	     * |  |     |  |
351 	     * -.-x  ---    --
352 	     *   |len
353 	     *   vp
354 	     */
355 	    vp++;
356 	    for (bp = bl + 1; *bp; *vp++ = *bp++)
357 		continue;
358 	    xfree((ptr_t) bl);
359 	}
360 
361     }
362     if (elp != NULL)
363 	*elp = el;
364     *nvp = nv;
365 }
366 
367 static Char **
368 globexpand(v)
369     Char  **v;
370 {
371     Char   *s;
372     Char  **nv, **vl, **el;
373     int     size = GLOBSPACE;
374 
375 
376     nv = vl = (Char **) xmalloc((size_t) (sizeof(Char *) * size));
377     *vl = NULL;
378 
379     /*
380      * Step 1: expand backquotes.
381      */
382     while ((s = *v++) != '\0') {
383 	if (Strchr(s, '`')) {
384 	    int     i;
385 
386 	    (void) dobackp(s, 0);
387 	    for (i = 0; i < pargc; i++) {
388 		*vl++ = pargv[i];
389 		if (vl == &nv[size]) {
390 		    size += GLOBSPACE;
391 		    nv = (Char **) xrealloc((ptr_t) nv,
392 					    (size_t) (size * sizeof(Char *)));
393 		    vl = &nv[size - GLOBSPACE];
394 		}
395 	    }
396 	    xfree((ptr_t) pargv);
397 	    pargv = NULL;
398 	}
399 	else {
400 	    *vl++ = Strsave(s);
401 	    if (vl == &nv[size]) {
402 		size += GLOBSPACE;
403 		nv = (Char **) xrealloc((ptr_t) nv,
404 					(size_t) (size * sizeof(Char *)));
405 		vl = &nv[size - GLOBSPACE];
406 	    }
407 	}
408     }
409     *vl = NULL;
410 
411     if (noglob)
412 	return (nv);
413 
414     /*
415      * Step 2: expand braces
416      */
417     el = vl;
418     expbrace(&nv, &el, size);
419 
420 
421     /*
422      * Step 3: expand ~ =
423      */
424     vl = nv;
425     for (s = *vl; s; s = *++vl)
426 	switch (*s) {
427 	    Char gp[BUFSIZE], *ns;
428 	case '~':
429 	    *vl = globtilde(nv, s);
430 	    break;
431 	case '=':
432 	    if ((ns = globequal(gp, s)) == NULL) {
433 		if (!adrof(STRnonomatch)) {
434 		    /* Error */
435 		    blkfree(nv);
436 		    stderror(ERR_DEEP);
437 		}
438 	    }
439 	    if (ns && ns != s) {
440 		/* Expansion succeeded */
441 		xfree((ptr_t) s);
442 		*vl = Strsave(gp);
443 	    }
444 	    break;
445 	default:
446 	    break;
447 	}
448     vl = nv;
449 
450     /*
451      * Step 4: expand .. if the variable symlinks==expand is set
452      */
453     if (symlinks == SYM_EXPAND) {
454 	for (s = *vl; s; s = *++vl) {
455 	    *vl = dnormalize(s, 1);
456 	    xfree((ptr_t) s);
457 	}
458     }
459     vl = nv;
460 
461     return (vl);
462 }
463 
464 static Char *
465 handleone(str, vl, action)
466     Char   *str, **vl;
467     int     action;
468 {
469 
470     Char   **vlp = vl;
471     int chars;
472     Char **t, *p, *strp;
473 
474     switch (action) {
475     case G_ERROR:
476 	setname(short2str(str));
477 	blkfree(vl);
478 	stderror(ERR_NAME | ERR_AMBIG);
479 	break;
480     case G_APPEND:
481 	chars = 0;
482 	for (t = vlp; (p = *t++) != '\0'; chars++)
483 	    while (*p++)
484 		chars++;
485 	str = (Char *)xmalloc((size_t)(chars * sizeof(Char)));
486 	for (t = vlp, strp = str; (p = *t++) != '\0'; chars++) {
487 	    while (*p)
488 		 *strp++ = *p++ & TRIM;
489 	    *strp++ = ' ';
490 	}
491 	*--strp = '\0';
492 	blkfree(vl);
493 	break;
494     case G_IGNORE:
495 	str = Strsave(strip(*vlp));
496 	blkfree(vl);
497 	break;
498     default:
499 	break;
500     }
501     return (str);
502 }
503 
504 static Char **
505 libglob(vl)
506     Char  **vl;
507 {
508     int     gflgs = GLOB_QUOTE | GLOB_NOMAGIC | GLOB_ALTNOT;
509     glob_t  globv;
510     char   *ptr;
511     int     nonomatch = adrof(STRnonomatch) != 0, magic = 0, match = 0;
512 
513     if (!vl || !vl[0])
514 	return(vl);
515 
516     globv.gl_offs = 0;
517     globv.gl_pathv = 0;
518     globv.gl_pathc = 0;
519 
520     if (nonomatch)
521 	gflgs |= GLOB_NOCHECK;
522 
523     do {
524 	ptr = short2qstr(*vl);
525 	switch (glob(ptr, gflgs, 0, &globv)) {
526 	case GLOB_ABEND:
527 	    globfree(&globv);
528 	    setname(ptr);
529 	    stderror(ERR_NAME | ERR_GLOB);
530 	    /* NOTREACHED */
531 	case GLOB_NOSPACE:
532 	    globfree(&globv);
533 	    stderror(ERR_NOMEM);
534 	    /* NOTREACHED */
535 	default:
536 	    break;
537 	}
538 	if (globv.gl_flags & GLOB_MAGCHAR) {
539 	    match |= (globv.gl_matchc != 0);
540 	    magic = 1;
541 	}
542 	gflgs |= GLOB_APPEND;
543     }
544     while (*++vl);
545     vl = (globv.gl_pathc == 0 || (magic && !match && !nonomatch)) ?
546 	NULL : blk2short(globv.gl_pathv);
547     globfree(&globv);
548     return (vl);
549 }
550 
551 Char   *
552 globone(str, action)
553     Char   *str;
554     int     action;
555 {
556 
557     Char   *v[2], **vl, **vo;
558     int gflg;
559 
560     noglob = adrof(STRnoglob) != 0;
561     gflag = 0;
562     v[0] = str;
563     v[1] = 0;
564     tglob(v);
565     gflg = gflag;
566     if (gflg == G_NONE)
567 	return (strip(Strsave(str)));
568 
569     if (gflg & G_CSH) {
570 	/*
571 	 * Expand back-quote, tilde and brace
572 	 */
573 	vo = globexpand(v);
574 	if (noglob || (gflg & G_GLOB) == 0) {
575 	    if (vo[0] == NULL) {
576 		xfree((ptr_t) vo);
577 		return (Strsave(STRNULL));
578 	    }
579 	    if (vo[1] != NULL)
580 		return (handleone(str, vo, action));
581 	    else {
582 		str = strip(vo[0]);
583 		xfree((ptr_t) vo);
584 		return (str);
585 	    }
586 	}
587     }
588     else if (noglob || (gflg & G_GLOB) == 0)
589 	return (strip(Strsave(str)));
590     else
591 	vo = v;
592 
593     vl = libglob(vo);
594     if ((gflg & G_CSH) && vl != vo)
595 	blkfree(vo);
596     if (vl == NULL) {
597 	setname(short2str(str));
598 	stderror(ERR_NAME | ERR_NOMATCH);
599     }
600     if (vl[0] == NULL) {
601 	xfree((ptr_t) vl);
602 	return (Strsave(STRNULL));
603     }
604     if (vl[1])
605 	return (handleone(str, vl, action));
606     else {
607 	str = strip(*vl);
608 	xfree((ptr_t) vl);
609 	return (str);
610     }
611 }
612 
613 Char  **
614 globall(v)
615     Char  **v;
616 {
617     Char  **vl, **vo;
618     int gflg = gflag;
619 
620     if (!v || !v[0]) {
621 	gargv = saveblk(v);
622 	gargc = blklen(gargv);
623 	return (gargv);
624     }
625 
626     noglob = adrof(STRnoglob) != 0;
627 
628     if (gflg & G_CSH)
629 	/*
630 	 * Expand back-quote, tilde and brace
631 	 */
632 	vl = vo = globexpand(v);
633     else
634 	vl = vo = saveblk(v);
635 
636     if (!noglob && (gflg & G_GLOB)) {
637 	vl = libglob(vo);
638 	if (vl != vo)
639 	    blkfree(vo);
640     }
641     else
642 	trim(vl);
643 
644     gargc = vl ? blklen(vl) : 0;
645     return (gargv = vl);
646 }
647 
648 void
649 ginit()
650 {
651     gargsiz = GLOBSPACE;
652     gargv = (Char **) xmalloc((size_t) (sizeof(Char *) * gargsiz));
653     gargv[0] = 0;
654     gargc = 0;
655 }
656 
657 void
658 rscan(t, f)
659     register Char **t;
660     void    (*f) __P((int));
661 {
662     register Char *p;
663 
664     while ((p = *t++) != '\0')
665 	while (*p)
666 	    (*f) (*p++);
667 }
668 
669 void
670 trim(t)
671     register Char **t;
672 {
673     register Char *p;
674 
675     while ((p = *t++) != '\0')
676 	while (*p)
677 	    *p++ &= TRIM;
678 }
679 
680 void
681 tglob(t)
682     register Char **t;
683 {
684     register Char *p, *c;
685 
686     while ((p = *t++) != '\0') {
687 	if (*p == '~' || *p == '=')
688 	    gflag |= G_CSH;
689 	else if (*p == '{' &&
690 		 (p[1] == '\0' || (p[1] == '}' && p[2] == '\0')))
691 	    continue;
692 	/*
693 	 * The following line used to be *(c = p++), but hp broke their
694 	 * optimizer in 9.01, so we break the assignment into two pieces
695 	 * The careful reader here will note that *most* compiler workarounds
696 	 * in tcsh are either for apollo/DomainOS or hpux. Is it a coincidence?
697 	 */
698 	while ( *(c = p) != '\0') {
699 	    p++;
700 	    if (*c == '`') {
701 		gflag |= G_CSH;
702 #ifdef notdef
703 		/*
704 		 * We do want to expand echo `echo '*'`, so we don't\
705 		 * use this piece of code anymore.
706 		 */
707 		while (*p && *p != '`')
708 		    if (*p++ == '\\') {
709 			if (*p)		/* Quoted chars */
710 			    p++;
711 			else
712 			    break;
713 		    }
714 		if (*p)			/* The matching ` */
715 		    p++;
716 		else
717 		    break;
718 #endif
719 	    }
720 	    else if (*c == '{')
721 		gflag |= G_CSH;
722 	    else if (isglob(*c))
723 		gflag |= G_GLOB;
724 	    else if (symlinks == SYM_EXPAND &&
725 		*p && ISDOTDOT(c) && (c == *(t-1) || *(c-1) == '/') )
726 	    	gflag |= G_CSH;
727 	}
728     }
729 }
730 
731 /*
732  * Command substitute cp.  If literal, then this is a substitution from a
733  * << redirection, and so we should not crunch blanks and tabs, separating
734  * words only at newlines.
735  */
736 Char  **
737 dobackp(cp, literal)
738     Char   *cp;
739     bool    literal;
740 {
741     register Char *lp, *rp;
742     Char   *ep, word[LONGBSIZE];
743 
744     if (pargv) {
745 #ifdef notdef
746 	abort();
747 #endif
748 	blkfree(pargv);
749     }
750     pargsiz = GLOBSPACE;
751     pargv = (Char **) xmalloc((size_t) (sizeof(Char *) * pargsiz));
752     pargv[0] = NULL;
753     pargcp = pargs = word;
754     pargc = 0;
755     pnleft = LONGBSIZE - 4;
756     for (;;) {
757 #if defined(DSPMBYTE)
758 	for (lp = cp;; lp++) {
759 	    if (*lp == '`' &&
760 		(lp-1 < cp || !Ismbyte2(*lp) || !Ismbyte1(*(lp-1)))) {
761 		break;
762 	    }
763 #else /* DSPMBYTE */
764 	for (lp = cp; *lp != '`'; lp++) {
765 #endif /* DSPMBYTE */
766 	    if (*lp == 0) {
767 		if (pargcp != pargs)
768 		    pword(LONGBSIZE);
769 		return (pargv);
770 	    }
771 	    psave(*lp);
772 	}
773 	lp++;
774 	for (rp = lp; *rp && *rp != '`'; rp++)
775 	    if (*rp == '\\') {
776 		rp++;
777 		if (!*rp)
778 		    goto oops;
779 	    }
780 	if (!*rp)
781     oops:  stderror(ERR_UNMATCHED, '`');
782 	ep = Strsave(lp);
783 	ep[rp - lp] = 0;
784 	backeval(ep, literal);
785 	cp = rp + 1;
786     }
787 }
788 
789 
790 static void
791 backeval(cp, literal)
792     Char   *cp;
793     bool    literal;
794 {
795     register int icnt, c;
796     register Char *ip;
797     struct command faket;
798     bool    hadnl;
799     int     pvec[2], quoted;
800     Char   *fakecom[2], ibuf[BUFSIZE];
801     char    tibuf[BUFSIZE];
802 
803     hadnl = 0;
804     icnt = 0;
805     quoted = (literal || (cp[0] & QUOTE)) ? QUOTE : 0;
806     faket.t_dtyp = NODE_COMMAND;
807     faket.t_dflg = F_BACKQ;
808     faket.t_dlef = 0;
809     faket.t_drit = 0;
810     faket.t_dspr = 0;
811     faket.t_dcom = fakecom;
812     fakecom[0] = STRfakecom1;
813     fakecom[1] = 0;
814 
815     /*
816      * We do the psave job to temporarily change the current job so that the
817      * following fork is considered a separate job.  This is so that when
818      * backquotes are used in a builtin function that calls glob the "current
819      * job" is not corrupted.  We only need one level of pushed jobs as long as
820      * we are sure to fork here.
821      */
822     psavejob();
823 
824     /*
825      * It would be nicer if we could integrate this redirection more with the
826      * routines in sh.sem.c by doing a fake execute on a builtin function that
827      * was piped out.
828      */
829     mypipe(pvec);
830     if (pfork(&faket, -1) == 0) {
831 	struct command *t;
832 
833 	(void) close(pvec[0]);
834 	(void) dmove(pvec[1], 1);
835 	(void) dmove(SHDIAG,  2);
836 	initdesc();
837 	/*
838 	 * Bugfix for nested backquotes by Michael Greim <greim@sbsvax.UUCP>,
839 	 * posted to comp.bugs.4bsd 12 Sep. 1989.
840 	 */
841 	if (pargv)		/* mg, 21.dec.88 */
842 	    blkfree(pargv), pargv = 0, pargsiz = 0;
843 	/* mg, 21.dec.88 */
844 	arginp = cp;
845 	while (*cp)
846 	    *cp++ &= TRIM;
847 
848         /*
849 	 * In the child ``forget'' everything about current aliases or
850 	 * eval vectors.
851 	 */
852 	alvec = NULL;
853 	evalvec = NULL;
854 	alvecp = NULL;
855 	evalp = NULL;
856 	(void) lex(&paraml);
857 	if (seterr)
858 	    stderror(ERR_OLD);
859 	alias(&paraml);
860 	t = syntax(paraml.next, &paraml, 0);
861 	if (seterr)
862 	    stderror(ERR_OLD);
863 	if (t)
864 	    t->t_dflg |= F_NOFORK;
865 #ifdef SIGTSTP
866 	(void) sigignore(SIGTSTP);
867 #endif
868 #ifdef SIGTTIN
869 	(void) sigignore(SIGTTIN);
870 #endif
871 #ifdef SIGTTOU
872 	(void) sigignore(SIGTTOU);
873 #endif
874 	execute(t, -1, NULL, NULL);
875 	exitstat();
876     }
877     xfree((ptr_t) cp);
878     (void) close(pvec[1]);
879     c = 0;
880     ip = NULL;
881     do {
882 	int     cnt = 0;
883 
884 	for (;;) {
885 	    if (icnt == 0) {
886 		int     i;
887 
888 		ip = ibuf;
889 		do
890 		    icnt = read(pvec[0], tibuf, BUFSIZE);
891 		while (icnt == -1 && errno == EINTR);
892 		if (icnt <= 0) {
893 		    c = -1;
894 		    break;
895 		}
896 		for (i = 0; i < icnt; i++)
897 		    ip[i] = (unsigned char) tibuf[i];
898 	    }
899 	    if (hadnl)
900 		break;
901 	    --icnt;
902 	    c = (*ip++ & TRIM);
903 	    if (c == 0)
904 		break;
905 #ifdef WINNT_NATIVE
906 	    if (c == '\r')
907 	    	c = ' ';
908 #endif /* WINNT_NATIVE */
909 	    if (c == '\n') {
910 		/*
911 		 * Continue around the loop one more time, so that we can eat
912 		 * the last newline without terminating this word.
913 		 */
914 		hadnl = 1;
915 		continue;
916 	    }
917 	    if (!quoted && (c == ' ' || c == '\t'))
918 		break;
919 	    cnt++;
920 	    psave(c | quoted);
921 	}
922 	/*
923 	 * Unless at end-of-file, we will form a new word here if there were
924 	 * characters in the word, or in any case when we take text literally.
925 	 * If we didn't make empty words here when literal was set then we
926 	 * would lose blank lines.
927 	 */
928 	if (c != -1 && (cnt || literal))
929 	    pword(BUFSIZE);
930 	hadnl = 0;
931     } while (c >= 0);
932     (void) close(pvec[0]);
933     pwait();
934     prestjob();
935 }
936 
937 static void
938 psave(c)
939     int    c;
940 {
941     if (--pnleft <= 0)
942 	stderror(ERR_WTOOLONG);
943     *pargcp++ = (Char) c;
944 }
945 
946 static void
947 pword(bufsiz)
948     int    bufsiz;
949 {
950     psave(0);
951     if (pargc == pargsiz - 1) {
952 	pargsiz += GLOBSPACE;
953 	pargv = (Char **) xrealloc((ptr_t) pargv,
954 				   (size_t) (pargsiz * sizeof(Char *)));
955     }
956     pargv[pargc++] = Strsave(pargs);
957     pargv[pargc] = NULL;
958     pargcp = pargs;
959     pnleft = bufsiz - 4;
960 }
961 
962 int
963 Gmatch(string, pattern)
964     Char *string, *pattern;
965 {
966     return Gnmatch(string, pattern, NULL);
967 }
968 
969 int
970 Gnmatch(string, pattern, endstr)
971     Char *string, *pattern, **endstr;
972 {
973     Char **blk, **p, *tstring = string;
974     int	   gpol = 1, gres = 0;
975 
976     if (*pattern == '^') {
977 	gpol = 0;
978 	pattern++;
979     }
980 
981     blk = (Char **) xmalloc((size_t) (GLOBSPACE * sizeof(Char *)));
982     blk[0] = Strsave(pattern);
983     blk[1] = NULL;
984 
985     expbrace(&blk, NULL, GLOBSPACE);
986 
987     if (endstr == NULL)
988 	/* Exact matches only */
989 	for (p = blk; *p; p++)
990 	    gres |= pmatch(string, *p, &tstring) == 2 ? 1 : 0;
991     else {
992 	/* partial matches */
993 	int minc = 0x7fffffff;
994 	for (p = blk; *p; p++)
995 	    if (pmatch(string, *p, &tstring) != 0) {
996 		int t = (int) (tstring - string);
997 		gres |= 1;
998 		if (minc == -1 || minc > t)
999 		    minc = t;
1000 	    }
1001 	*endstr = string + minc;
1002     }
1003 
1004     blkfree(blk);
1005     return(gres == gpol);
1006 }
1007 
1008 /* pmatch():
1009  *	Return 2 on exact match,
1010  *	Return 1 on substring match.
1011  *	Return 0 on no match.
1012  *	*estr will point to the end of the longest exact or substring match.
1013  */
1014 static int
1015 pmatch(string, pattern, estr)
1016     register Char *string, *pattern, **estr;
1017 {
1018     register Char stringc, patternc;
1019     int     match, negate_range;
1020     Char    rangec, *oestr, *pestr;
1021 
1022     for (;; ++string) {
1023 	stringc = *string & TRIM;
1024 	/*
1025 	 * apollo compiler bug: switch (patternc = *pattern++) dies
1026 	 */
1027 	patternc = *pattern++;
1028 	switch (patternc) {
1029 	case 0:
1030 	    *estr = string;
1031 	    return (stringc == 0 ? 2 : 1);
1032 	case '?':
1033 	    if (stringc == 0)
1034 		return (0);
1035 	    *estr = string;
1036 	    break;
1037 	case '*':
1038 	    if (!*pattern) {
1039 		while (*string) string++;
1040 		*estr = string;
1041 		return (2);
1042 	    }
1043 	    oestr = *estr;
1044 	    pestr = NULL;
1045 
1046 	    do {
1047 		switch(pmatch(string, pattern, estr)) {
1048 		case 0:
1049 		    break;
1050 		case 1:
1051 		    pestr = *estr;
1052 		    break;
1053 		case 2:
1054 		    return 2;
1055 		default:
1056 		    abort();	/* Cannot happen */
1057 		}
1058 		*estr = string;
1059 	    }
1060 	    while (*string++);
1061 
1062 	    if (pestr) {
1063 		*estr = pestr;
1064 		return 1;
1065 	    }
1066 	    else {
1067 		*estr = oestr;
1068 		return 0;
1069 	    }
1070 
1071 	case '[':
1072 	    match = 0;
1073 	    if ((negate_range = (*pattern == '^')) != 0)
1074 		pattern++;
1075 	    while ((rangec = *pattern++) != '\0') {
1076 		if (rangec == ']')
1077 		    break;
1078 		if (match)
1079 		    continue;
1080 		if (rangec == '-' && *(pattern-2) != '[' && *pattern  != ']') {
1081 		    match = (globcharcoll(stringc, *pattern & TRIM) <= 0 &&
1082 		    globcharcoll(*(pattern-2) & TRIM, stringc) <= 0);
1083 		    pattern++;
1084 		}
1085 		else
1086 		    match = (stringc == (rangec & TRIM));
1087 	    }
1088 	    if (rangec == 0)
1089 		stderror(ERR_NAME | ERR_MISSING, ']');
1090 	    if (match == negate_range)
1091 		return (0);
1092 	    *estr = string;
1093 	    break;
1094 	default:
1095 	    if ((patternc & TRIM) != stringc)
1096 		return (0);
1097 	    *estr = string;
1098 	    break;
1099 	}
1100     }
1101 }
1102 
1103 void
1104 Gcat(s1, s2)
1105     Char   *s1, *s2;
1106 {
1107     register Char *p, *q;
1108     int     n;
1109 
1110     for (p = s1; *p++;)
1111 	continue;
1112     for (q = s2; *q++;)
1113 	continue;
1114     n = (int) ((p - s1) + (q - s2) - 1);
1115     if (++gargc >= gargsiz) {
1116 	gargsiz += GLOBSPACE;
1117 	gargv = (Char **) xrealloc((ptr_t) gargv,
1118 				   (size_t) (gargsiz * sizeof(Char *)));
1119     }
1120     gargv[gargc] = 0;
1121     p = gargv[gargc - 1] = (Char *) xmalloc((size_t) (n * sizeof(Char)));
1122     for (q = s1; (*p++ = *q++) != '\0';)
1123 	continue;
1124     for (p--, q = s2; (*p++ = *q++) != '\0';)
1125 	continue;
1126 }
1127 
1128 #ifdef FILEC
1129 int
1130 sortscmp(a, b)
1131     register Char **a, **b;
1132 {
1133     if (!a)			/* check for NULL */
1134 	return (b ? 1 : 0);
1135     if (!b)
1136 	return (-1);
1137 
1138     if (!*a)			/* check for NULL */
1139 	return (*b ? 1 : 0);
1140     if (!*b)
1141 	return (-1);
1142 
1143     return (int) collate(*a, *b);
1144 }
1145 
1146 #endif
1147