xref: /original-bsd/bin/csh/misc.c (revision 703f6d5d)
1 /*-
2  * Copyright (c) 1980, 1991 The Regents of the University of California.
3  * All rights reserved.
4  *
5  * %sccs.include.redist.c%
6  */
7 
8 #ifndef lint
9 static char sccsid[] = "@(#)misc.c	5.13 (Berkeley) 06/27/91";
10 #endif /* not lint */
11 
12 #include <sys/param.h>
13 #include <stdlib.h>
14 #include <unistd.h>
15 #if __STDC__
16 # include <stdarg.h>
17 #else
18 # include <varargs.h>
19 #endif
20 
21 #include "csh.h"
22 #include "extern.h"
23 
24 static int	renum __P((int, int));
25 
26 int
27 any(s, c)
28     register char *s;
29     register int c;
30 {
31     if (!s)
32 	return (0);		/* Check for nil pointer */
33     while (*s)
34 	if (*s++ == c)
35 	    return (1);
36     return (0);
37 }
38 
39 void
40 setzero(cp, i)
41     char   *cp;
42     int     i;
43 {
44     if (i != 0)
45 	do
46 	    *cp++ = 0;
47 	while (--i);
48 }
49 
50 char   *
51 strsave(s)
52     register char *s;
53 {
54     char   *n;
55     register char *p;
56 
57     if (s == NULL)
58 	s = "";
59     for (p = s; *p++;);
60     n = p = (char *) xmalloc((size_t) ((p - s) * sizeof(char)));
61     while (*p++ = *s++);
62     return (n);
63 }
64 
65 Char  **
66 blkend(up)
67     register Char **up;
68 {
69 
70     while (*up)
71 	up++;
72     return (up);
73 }
74 
75 
76 void
77 blkpr(av)
78     register Char **av;
79 {
80 
81     for (; *av; av++) {
82 	xprintf("%s", short2str(*av));
83 	if (av[1])
84 	    xprintf(" ");
85     }
86 }
87 
88 int
89 blklen(av)
90     register Char **av;
91 {
92     register int i = 0;
93 
94     while (*av++)
95 	i++;
96     return (i);
97 }
98 
99 Char  **
100 blkcpy(oav, bv)
101     Char  **oav;
102     register Char **bv;
103 {
104     register Char **av = oav;
105 
106     while (*av++ = *bv++)
107 	continue;
108     return (oav);
109 }
110 
111 Char  **
112 blkcat(up, vp)
113     Char  **up, **vp;
114 {
115 
116     (void) blkcpy(blkend(up), vp);
117     return (up);
118 }
119 
120 void
121 blkfree(av0)
122     Char  **av0;
123 {
124     register Char **av = av0;
125 
126     if (!av0)
127 	return;
128     for (; *av; av++)
129 	xfree((ptr_t) * av);
130     xfree((ptr_t) av0);
131 }
132 
133 Char  **
134 saveblk(v)
135     register Char **v;
136 {
137     register Char **newv =
138     (Char **) xcalloc((size_t) (blklen(v) + 1), sizeof(Char **));
139     Char  **onewv = newv;
140 
141     while (*v)
142 	*newv++ = Strsave(*v++);
143     return (onewv);
144 }
145 
146 #ifdef NOTUSED
147 char   *
148 strstr(s, t)
149     register char *s, *t;
150 {
151     do {
152 	register char *ss = s;
153 	register char *tt = t;
154 
155 	do
156 	    if (*tt == '\0')
157 		return (s);
158 	while (*ss++ == *tt++);
159     } while (*s++ != '\0');
160     return (NULL);
161 }
162 
163 #endif /* NOTUSED */
164 
165 #ifndef SHORT_STRINGS
166 char   *
167 strspl(cp, dp)
168     char   *cp, *dp;
169 {
170     char   *ep;
171     register char *p, *q;
172 
173     if (!cp)
174 	cp = "";
175     if (!dp)
176 	dp = "";
177     for (p = cp; *p++;);
178     for (q = dp; *q++;);
179     ep = (char *) xmalloc((size_t) (((p - cp) + (q - dp) - 1) * sizeof(char)));
180     for (p = ep, q = cp; *p++ = *q++;);
181     for (p--, q = dp; *p++ = *q++;);
182     return (ep);
183 }
184 
185 #endif
186 
187 Char  **
188 blkspl(up, vp)
189     register Char **up, **vp;
190 {
191     register Char **wp =
192     (Char **) xcalloc((size_t) (blklen(up) + blklen(vp) + 1),
193 		      sizeof(Char **));
194 
195     (void) blkcpy(wp, up);
196     return (blkcat(wp, vp));
197 }
198 
199 Char
200 lastchr(cp)
201     register Char *cp;
202 {
203 
204     if (!cp)
205 	return (0);
206     if (!*cp)
207 	return (0);
208     while (cp[1])
209 	cp++;
210     return (*cp);
211 }
212 
213 /*
214  * This routine is called after an error to close up
215  * any units which may have been left open accidentally.
216  */
217 void
218 closem()
219 {
220     register int f;
221 
222     for (f = 0; f < NOFILE; f++)
223 	if (f != SHIN && f != SHOUT && f != SHDIAG && f != OLDSTD &&
224 	    f != FSHTTY)
225 	    (void) close(f);
226 }
227 
228 void
229 donefds()
230 {
231 
232     (void) close(0);
233     (void) close(1);
234     (void) close(2);
235     didfds = 0;
236 }
237 
238 /*
239  * Move descriptor i to j.
240  * If j is -1 then we just want to get i to a safe place,
241  * i.e. to a unit > 2.  This also happens in dcopy.
242  */
243 int
244 dmove(i, j)
245     register int i, j;
246 {
247 
248     if (i == j || i < 0)
249 	return (i);
250     if (j >= 0) {
251 	(void) dup2(i, j);
252 	if (j != i)
253 	    (void) close(i);
254 	return (j);
255     }
256     j = dcopy(i, j);
257     if (j != i)
258 	(void) close(i);
259     return (j);
260 }
261 
262 int
263 dcopy(i, j)
264     register int i, j;
265 {
266 
267     if (i == j || i < 0 || j < 0 && i > 2)
268 	return (i);
269     if (j >= 0) {
270 	(void) dup2(i, j);
271 	return (j);
272     }
273     (void) close(j);
274     return (renum(i, j));
275 }
276 
277 static int
278 renum(i, j)
279     register int i, j;
280 {
281     register int k = dup(i);
282 
283     if (k < 0)
284 	return (-1);
285     if (j == -1 && k > 2)
286 	return (k);
287     if (k != j) {
288 	j = renum(k, j);
289 	(void) close(k);
290 	return (j);
291     }
292     return (k);
293 }
294 
295 /*
296  * Left shift a command argument list, discarding
297  * the first c arguments.  Used in "shift" commands
298  * as well as by commands like "repeat".
299  */
300 void
301 lshift(v, c)
302     register Char **v;
303     register int c;
304 {
305     register Char **u = v;
306 
307     while (*u && --c >= 0)
308 	xfree((ptr_t) * u++);
309     (void) blkcpy(v, u);
310 }
311 
312 int
313 number(cp)
314     Char   *cp;
315 {
316     if (!cp)
317 	return(0);
318     if (*cp == '-') {
319 	cp++;
320 	if (!Isdigit(*cp))
321 	    return (0);
322 	cp++;
323     }
324     while (*cp && Isdigit(*cp))
325 	cp++;
326     return (*cp == 0);
327 }
328 
329 Char  **
330 copyblk(v)
331     register Char **v;
332 {
333     Char  **nv = (Char **) xcalloc((size_t) (blklen(v) + 1), sizeof(Char **));
334 
335     return (blkcpy(nv, v));
336 }
337 
338 #ifndef SHORT_STRINGS
339 char   *
340 strend(cp)
341     register char *cp;
342 {
343     if (!cp)
344 	return (cp);
345     while (*cp)
346 	cp++;
347     return (cp);
348 }
349 
350 #endif				/* SHORT_STRINGS */
351 
352 Char   *
353 strip(cp)
354     Char   *cp;
355 {
356     register Char *dp = cp;
357 
358     if (!cp)
359 	return (cp);
360     while (*dp++ &= TRIM)
361 	continue;
362     return (cp);
363 }
364 
365 void
366 udvar(name)
367     Char   *name;
368 {
369 
370     setname(short2str(name));
371     stderror(ERR_NAME | ERR_UNDVAR);
372 }
373 
374 int
375 prefix(sub, str)
376     register Char *sub, *str;
377 {
378 
379     for (;;) {
380 	if (*sub == 0)
381 	    return (1);
382 	if (*str == 0)
383 	    return (0);
384 	if (*sub++ != *str++)
385 	    return (0);
386     }
387 }
388