xref: /titanic_53/usr/src/cmd/csh/sh.err.c (revision 7c478bd95313f5f23a4c958a745db2134aa03244)
1*7c478bd9Sstevel@tonic-gate /*
2*7c478bd9Sstevel@tonic-gate  * Copyright 1997 Sun Microsystems, Inc.  All rights reserved.
3*7c478bd9Sstevel@tonic-gate  * Use is subject to license terms.
4*7c478bd9Sstevel@tonic-gate  */
5*7c478bd9Sstevel@tonic-gate 
6*7c478bd9Sstevel@tonic-gate /*	Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T	*/
7*7c478bd9Sstevel@tonic-gate /*	  All Rights Reserved  	*/
8*7c478bd9Sstevel@tonic-gate 
9*7c478bd9Sstevel@tonic-gate /*
10*7c478bd9Sstevel@tonic-gate  * Copyright (c) 1980 Regents of the University of California.
11*7c478bd9Sstevel@tonic-gate  * All rights reserved.  The Berkeley Software License Agreement
12*7c478bd9Sstevel@tonic-gate  * specifies the terms and conditions for redistribution.
13*7c478bd9Sstevel@tonic-gate  */
14*7c478bd9Sstevel@tonic-gate 
15*7c478bd9Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
16*7c478bd9Sstevel@tonic-gate 
17*7c478bd9Sstevel@tonic-gate #include "sh.h"
18*7c478bd9Sstevel@tonic-gate #include <locale.h>
19*7c478bd9Sstevel@tonic-gate #include <dirent.h>
20*7c478bd9Sstevel@tonic-gate /*
21*7c478bd9Sstevel@tonic-gate  * #include <sys/ioctl.h>
22*7c478bd9Sstevel@tonic-gate  * #include <stdlib.h>
23*7c478bd9Sstevel@tonic-gate  */
24*7c478bd9Sstevel@tonic-gate #include "sh.tconst.h"
25*7c478bd9Sstevel@tonic-gate /*
26*7c478bd9Sstevel@tonic-gate  * C Shell
27*7c478bd9Sstevel@tonic-gate  */
28*7c478bd9Sstevel@tonic-gate 
29*7c478bd9Sstevel@tonic-gate 
30*7c478bd9Sstevel@tonic-gate bool	errspl;			/* Argument to error was spliced by seterr2 */
31*7c478bd9Sstevel@tonic-gate tchar one[2] = { '1', 0 };
32*7c478bd9Sstevel@tonic-gate tchar *onev[2] = { one, NOSTR };
33*7c478bd9Sstevel@tonic-gate /*
34*7c478bd9Sstevel@tonic-gate  *    contains DIR * for last opendir_(), its left open if an error
35*7c478bd9Sstevel@tonic-gate  *    longjmp (reset) occurs before it gets closed via closedir.
36*7c478bd9Sstevel@tonic-gate  *    if its not null in the error handler, then closedir it.
37*7c478bd9Sstevel@tonic-gate  */
38*7c478bd9Sstevel@tonic-gate DIR *Dirp = NULL;
39*7c478bd9Sstevel@tonic-gate 
40*7c478bd9Sstevel@tonic-gate /*
41*7c478bd9Sstevel@tonic-gate  * Print error string s with optional argument arg.
42*7c478bd9Sstevel@tonic-gate  * This routine always resets or exits.  The flag haderr
43*7c478bd9Sstevel@tonic-gate  * is set so the routine who catches the unwind can propogate
44*7c478bd9Sstevel@tonic-gate  * it if they want.
45*7c478bd9Sstevel@tonic-gate  *
46*7c478bd9Sstevel@tonic-gate  * Note that any open files at the point of error will eventually
47*7c478bd9Sstevel@tonic-gate  * be closed in the routine process in sh.c which is the only
48*7c478bd9Sstevel@tonic-gate  * place error unwinds are ever caught.
49*7c478bd9Sstevel@tonic-gate  */
50*7c478bd9Sstevel@tonic-gate /*VARARGS1*/
51*7c478bd9Sstevel@tonic-gate error(s, a1, a2)
52*7c478bd9Sstevel@tonic-gate      char	*s;
53*7c478bd9Sstevel@tonic-gate {
54*7c478bd9Sstevel@tonic-gate 	register	tchar **v;
55*7c478bd9Sstevel@tonic-gate 	register	char *ep;
56*7c478bd9Sstevel@tonic-gate 
57*7c478bd9Sstevel@tonic-gate 	/*
58*7c478bd9Sstevel@tonic-gate 	 * Must flush before we print as we wish output before the error
59*7c478bd9Sstevel@tonic-gate 	 * to go on (some form of) standard output, while output after
60*7c478bd9Sstevel@tonic-gate 	 * goes on (some form of) diagnostic output.
61*7c478bd9Sstevel@tonic-gate 	 * If didfds then output will go to 1/2 else to FSHOUT/FSHDIAG.
62*7c478bd9Sstevel@tonic-gate 	 * See flush in sh.print.c.
63*7c478bd9Sstevel@tonic-gate 	 */
64*7c478bd9Sstevel@tonic-gate 	flush();
65*7c478bd9Sstevel@tonic-gate 	haderr = 1;		/* Now to diagnostic output */
66*7c478bd9Sstevel@tonic-gate 	timflg = 0;		/* This isn't otherwise reset */
67*7c478bd9Sstevel@tonic-gate 	if (v = pargv)
68*7c478bd9Sstevel@tonic-gate 		pargv = 0, blkfree(v);
69*7c478bd9Sstevel@tonic-gate 	if (v = gargv)
70*7c478bd9Sstevel@tonic-gate 		gargv = 0, blkfree(v);
71*7c478bd9Sstevel@tonic-gate 
72*7c478bd9Sstevel@tonic-gate 	/*
73*7c478bd9Sstevel@tonic-gate 	 * A zero arguments causes no printing, else print
74*7c478bd9Sstevel@tonic-gate 	 * an error diagnostic here.
75*7c478bd9Sstevel@tonic-gate 	 */
76*7c478bd9Sstevel@tonic-gate 	if (s) {
77*7c478bd9Sstevel@tonic-gate 			printf(s, a1, a2), printf("\n");
78*7c478bd9Sstevel@tonic-gate 	}
79*7c478bd9Sstevel@tonic-gate 
80*7c478bd9Sstevel@tonic-gate 
81*7c478bd9Sstevel@tonic-gate 	didfds = 0;		/* Forget about 0,1,2 */
82*7c478bd9Sstevel@tonic-gate 	if ((ep = err) && errspl) {
83*7c478bd9Sstevel@tonic-gate 		errspl = 0;
84*7c478bd9Sstevel@tonic-gate 		xfree(ep);
85*7c478bd9Sstevel@tonic-gate 	}
86*7c478bd9Sstevel@tonic-gate 	errspl = 0;
87*7c478bd9Sstevel@tonic-gate 
88*7c478bd9Sstevel@tonic-gate 	if ( Dirp ){
89*7c478bd9Sstevel@tonic-gate 		closedir(Dirp);
90*7c478bd9Sstevel@tonic-gate 		Dirp = NULL;
91*7c478bd9Sstevel@tonic-gate 	}
92*7c478bd9Sstevel@tonic-gate 
93*7c478bd9Sstevel@tonic-gate 	/*
94*7c478bd9Sstevel@tonic-gate 	 * Go away if -e or we are a child shell
95*7c478bd9Sstevel@tonic-gate 	 */
96*7c478bd9Sstevel@tonic-gate 	if (exiterr || child) {
97*7c478bd9Sstevel@tonic-gate 		exit(1);
98*7c478bd9Sstevel@tonic-gate 	}
99*7c478bd9Sstevel@tonic-gate 
100*7c478bd9Sstevel@tonic-gate 	/*
101*7c478bd9Sstevel@tonic-gate 	 * Reset the state of the input.
102*7c478bd9Sstevel@tonic-gate 	 * This buffered seek to end of file will also
103*7c478bd9Sstevel@tonic-gate 	 * clear the while/foreach stack.
104*7c478bd9Sstevel@tonic-gate 	 */
105*7c478bd9Sstevel@tonic-gate 	btoeof();
106*7c478bd9Sstevel@tonic-gate 
107*7c478bd9Sstevel@tonic-gate 	setq(S_status, onev, &shvhed);
108*7c478bd9Sstevel@tonic-gate 	if (tpgrp > 0)
109*7c478bd9Sstevel@tonic-gate 		(void) ioctl(FSHTTY, TIOCSPGRP,  (char *)&tpgrp);
110*7c478bd9Sstevel@tonic-gate 	reset();		/* Unwind */
111*7c478bd9Sstevel@tonic-gate }
112*7c478bd9Sstevel@tonic-gate 
113*7c478bd9Sstevel@tonic-gate /*
114*7c478bd9Sstevel@tonic-gate  * Perror is the shells version of perror which should otherwise
115*7c478bd9Sstevel@tonic-gate  * never be called.
116*7c478bd9Sstevel@tonic-gate  */
117*7c478bd9Sstevel@tonic-gate Perror(s)
118*7c478bd9Sstevel@tonic-gate      tchar *s;
119*7c478bd9Sstevel@tonic-gate {
120*7c478bd9Sstevel@tonic-gate 	char	chbuf[BUFSIZ];
121*7c478bd9Sstevel@tonic-gate 
122*7c478bd9Sstevel@tonic-gate 	/*
123*7c478bd9Sstevel@tonic-gate 	 * Perror uses unit 2, thus if we didn't set up the fd's
124*7c478bd9Sstevel@tonic-gate 	 * we must set up unit 2 now else the diagnostic will disappear
125*7c478bd9Sstevel@tonic-gate 	 */
126*7c478bd9Sstevel@tonic-gate 	if (!didfds) {
127*7c478bd9Sstevel@tonic-gate 		register int oerrno = errno;
128*7c478bd9Sstevel@tonic-gate 
129*7c478bd9Sstevel@tonic-gate 		(void) dcopy(SHDIAG, 2);
130*7c478bd9Sstevel@tonic-gate 		errno = oerrno;
131*7c478bd9Sstevel@tonic-gate 	}
132*7c478bd9Sstevel@tonic-gate 	tstostr(chbuf, s);
133*7c478bd9Sstevel@tonic-gate 	perror(chbuf);
134*7c478bd9Sstevel@tonic-gate 	error(NULL);		/* To exit or unwind */
135*7c478bd9Sstevel@tonic-gate }
136*7c478bd9Sstevel@tonic-gate 
137*7c478bd9Sstevel@tonic-gate bferr(cp)
138*7c478bd9Sstevel@tonic-gate      char *cp;
139*7c478bd9Sstevel@tonic-gate {
140*7c478bd9Sstevel@tonic-gate 
141*7c478bd9Sstevel@tonic-gate 	flush();
142*7c478bd9Sstevel@tonic-gate 	haderr = 1;
143*7c478bd9Sstevel@tonic-gate 	if( bname) printf("%t: ", bname);
144*7c478bd9Sstevel@tonic-gate 	error("%s", gettext(cp));
145*7c478bd9Sstevel@tonic-gate }
146*7c478bd9Sstevel@tonic-gate 
147*7c478bd9Sstevel@tonic-gate /*
148*7c478bd9Sstevel@tonic-gate  * The parser and scanner set up errors for later by calling seterr,
149*7c478bd9Sstevel@tonic-gate  * which sets the variable err as a side effect; later to be tested,
150*7c478bd9Sstevel@tonic-gate  * e.g. in process.
151*7c478bd9Sstevel@tonic-gate  */
152*7c478bd9Sstevel@tonic-gate seterr(s)
153*7c478bd9Sstevel@tonic-gate      char *s;
154*7c478bd9Sstevel@tonic-gate {
155*7c478bd9Sstevel@tonic-gate 
156*7c478bd9Sstevel@tonic-gate 	if (err == 0)
157*7c478bd9Sstevel@tonic-gate 		err = s, errspl = 0;
158*7c478bd9Sstevel@tonic-gate }
159*7c478bd9Sstevel@tonic-gate 
160*7c478bd9Sstevel@tonic-gate /* Set err to a splice of cp and dp, to be freed later in error() */
161*7c478bd9Sstevel@tonic-gate seterr2(cp, dp)
162*7c478bd9Sstevel@tonic-gate      tchar *cp;
163*7c478bd9Sstevel@tonic-gate      char *dp;
164*7c478bd9Sstevel@tonic-gate {
165*7c478bd9Sstevel@tonic-gate 	char	chbuf[BUFSIZ];
166*7c478bd9Sstevel@tonic-gate 	char	*gdp;
167*7c478bd9Sstevel@tonic-gate 
168*7c478bd9Sstevel@tonic-gate 	if (err)
169*7c478bd9Sstevel@tonic-gate 		return;
170*7c478bd9Sstevel@tonic-gate 
171*7c478bd9Sstevel@tonic-gate 	/* Concatinate cp and dp in the allocated space. */
172*7c478bd9Sstevel@tonic-gate 	tstostr(chbuf, cp);
173*7c478bd9Sstevel@tonic-gate 	gdp = gettext(dp);
174*7c478bd9Sstevel@tonic-gate 	err = (char *)xalloc(strlen(chbuf)+strlen(gdp)+1);
175*7c478bd9Sstevel@tonic-gate 	strcpy(err, chbuf);
176*7c478bd9Sstevel@tonic-gate 	strcat(err, gdp);
177*7c478bd9Sstevel@tonic-gate 
178*7c478bd9Sstevel@tonic-gate 	errspl++;/* Remember to xfree(err). */
179*7c478bd9Sstevel@tonic-gate }
180*7c478bd9Sstevel@tonic-gate 
181*7c478bd9Sstevel@tonic-gate /* Set err to a splice of cp with a string form of character d */
182*7c478bd9Sstevel@tonic-gate seterrc(cp, d)
183*7c478bd9Sstevel@tonic-gate      char	*cp;
184*7c478bd9Sstevel@tonic-gate      tchar	 d;
185*7c478bd9Sstevel@tonic-gate {
186*7c478bd9Sstevel@tonic-gate 	char	chbuf[MB_LEN_MAX+1];
187*7c478bd9Sstevel@tonic-gate 
188*7c478bd9Sstevel@tonic-gate 	/* don't overwrite an existing error message */
189*7c478bd9Sstevel@tonic-gate 	if (err)
190*7c478bd9Sstevel@tonic-gate 		return;
191*7c478bd9Sstevel@tonic-gate 
192*7c478bd9Sstevel@tonic-gate #ifdef MBCHAR
193*7c478bd9Sstevel@tonic-gate 	{
194*7c478bd9Sstevel@tonic-gate 	wchar_t	wcd=(wchar_t)(d&TRIM);
195*7c478bd9Sstevel@tonic-gate 	int	i;
196*7c478bd9Sstevel@tonic-gate 
197*7c478bd9Sstevel@tonic-gate 	i = wctomb(chbuf, wcd); /* chbuf holds d in multibyte representation. */
198*7c478bd9Sstevel@tonic-gate 	chbuf[(i>0)?i:0] = (char) 0;
199*7c478bd9Sstevel@tonic-gate 	}
200*7c478bd9Sstevel@tonic-gate #else
201*7c478bd9Sstevel@tonic-gate 	chbuf[0]=(char)(d&TRIM); chbuf[1]=(char)0;
202*7c478bd9Sstevel@tonic-gate #endif
203*7c478bd9Sstevel@tonic-gate 
204*7c478bd9Sstevel@tonic-gate 
205*7c478bd9Sstevel@tonic-gate 	/* Concatinate cp and d in the allocated space. */
206*7c478bd9Sstevel@tonic-gate 	err = (char *)xalloc(strlen(cp)+strlen(chbuf)+1);
207*7c478bd9Sstevel@tonic-gate 	strcpy(err, cp);
208*7c478bd9Sstevel@tonic-gate 	strcat(err, chbuf);
209*7c478bd9Sstevel@tonic-gate 
210*7c478bd9Sstevel@tonic-gate 	errspl++; /* Remember to xfree(err). */
211*7c478bd9Sstevel@tonic-gate }
212