|
|
1.1 root 1: static char *sccsid = "@(#)sh.set.c 4.1 10/9/80";
2:
3: #include "sh.h"
4:
5: /*
6: * C Shell
7: */
8:
9: doset(v)
10: register char **v;
11: {
12: register char *p;
13: char *vp, op;
14: char **vecp;
15: bool hadsub;
16: int subscr;
17:
18: v++;
19: p = *v++;
20: if (p == 0) {
21: prvars();
22: return;
23: }
24: do {
25: hadsub = 0;
26: for (vp = p; alnum(*p); p++)
27: continue;
28: if (vp == p)
29: goto setsyn;
30: if (*p == '[') {
31: hadsub++;
32: p = getinx(p, &subscr);
33: }
34: if (op = *p) {
35: *p++ = 0;
36: if (*p == 0 && *v && **v == '(')
37: p = *v++;
38: } else if (*v && eq(*v, "=")) {
39: op = '=', v++;
40: if (*v)
41: p = *v++;
42: }
43: if (op && op != '=')
44: setsyn:
45: bferr("Syntax error");
46: if (eq(p, "(")) {
47: register char **e = v;
48:
49: if (hadsub)
50: goto setsyn;
51: for (;;) {
52: if (!*e)
53: bferr("Missing )");
54: if (**e == ')')
55: break;
56: e++;
57: }
58: p = *e;
59: *e = 0;
60: vecp = saveblk(v);
61: set1(vp, vecp, &shvhed);
62: *e = p;
63: v = e + 1;
64: } else if (hadsub)
65: asx(vp, subscr, savestr(p));
66: else
67: set(vp, savestr(p));
68: if (eq(vp, "path")) {
69: exportpath(adrof("path")->vec);
70: dohash();
71: } else if (eq(vp, "histchars")) {
72: register char *p = value("histchars");
73:
74: HIST = *p++;
75: HISTSUB = *p;
76: } else if (eq(vp, "user"))
77: setenv("USER", value(vp));
78: else if (eq(vp, "term"))
79: setenv("TERM", value(vp));
80: else if (eq(vp, "home"))
81: setenv("HOME", value(vp));
82: } while (p = *v++);
83: }
84:
85: char *
86: getinx(cp, ip)
87: register char *cp;
88: register int *ip;
89: {
90:
91: *ip = 0;
92: *cp++ = 0;
93: while (*cp && digit(*cp))
94: *ip = *ip * 10 + *cp++ - '0';
95: if (*cp++ != ']')
96: bferr("Subscript error");
97: return (cp);
98: }
99:
100: asx(vp, subscr, p)
101: char *vp;
102: int subscr;
103: char *p;
104: {
105: register struct varent *v = getvx(vp, subscr);
106:
107: xfree(v->vec[subscr - 1]);
108: v->vec[subscr - 1] = globone(p);
109: }
110:
111: struct varent *
112: getvx(vp, subscr)
113: {
114: register struct varent *v = adrof(vp);
115:
116: if (v == 0)
117: udvar(vp);
118: if (subscr < 1 || subscr > blklen(v->vec))
119: bferr("Subscript out of range");
120: return (v);
121: }
122:
123: char plusplus[2] = { '1', 0 };
124:
125:
126: dolet(v)
127: char **v;
128: {
129: register char *p;
130: char *vp, c, op;
131: bool hadsub;
132: int subscr;
133:
134: v++;
135: p = *v++;
136: if (p == 0) {
137: prvars();
138: return;
139: }
140: do {
141: hadsub = 0;
142: for (vp = p; letter(*p); p++)
143: continue;
144: if (vp == p)
145: goto letsyn;
146: if (*p == '[') {
147: hadsub++;
148: p = getinx(p, &subscr);
149: }
150: if (*p == 0 && *v)
151: p = *v++;
152: if (op = *p)
153: *p++ = 0;
154: else
155: goto letsyn;
156: vp = savestr(vp);
157: if (op == '=') {
158: c = '=';
159: p = xset(p, &v);
160: } else {
161: c = *p++;
162: if (any(c, "+-")) {
163: if (c != op || *p)
164: goto letsyn;
165: p = plusplus;
166: } else {
167: if (any(op, "<>")) {
168: if (c != op)
169: goto letsyn;
170: c = *p++;
171: letsyn:
172: bferr("Syntax error");
173: }
174: if (c != '=')
175: goto letsyn;
176: p = xset(p, &v);
177: }
178: }
179: if (op == '=')
180: if (hadsub)
181: asx(vp, subscr, p);
182: else
183: set(vp, p);
184: else
185: if (hadsub)
186: #ifndef V6
187: /* avoid bug in vax CC */
188: {
189: struct varent *gv = getvx(vp, subscr);
190:
191: asx(vp, subscr, operate(op, gv->vec[subscr - 1], p));
192: }
193: #else
194: asx(vp, subscr, operate(op, getvx(vp, subscr)->vec[subscr - 1], p));
195: #endif
196: else
197: set(vp, operate(op, value(vp), p));
198: if (strcmp(vp, "path") == 0)
199: dohash();
200: xfree(vp);
201: if (c != '=')
202: xfree(p);
203: } while (p = *v++);
204: }
205:
206: char *
207: xset(cp, vp)
208: char *cp, ***vp;
209: {
210: register char *dp;
211:
212: if (*cp) {
213: dp = savestr(cp);
214: --(*vp);
215: xfree(**vp);
216: **vp = dp;
217: }
218: return (putn(exp(vp)));
219: }
220:
221: char *
222: operate(op, vp, p)
223: char op, *vp, *p;
224: {
225: char opr[2];
226: char *vec[5];
227: register char **v = vec;
228: char **vecp = v;
229: register int i;
230:
231: if (op != '=') {
232: if (*vp)
233: *v++ = vp;
234: opr[0] = op;
235: opr[1] = 0;
236: *v++ = opr;
237: if (op == '<' || op == '>')
238: *v++ = opr;
239: }
240: *v++ = p;
241: *v++ = 0;
242: i = exp(&vecp);
243: if (*vecp)
244: bferr("Expression syntax");
245: return (putn(i));
246: }
247:
248: onlyread(cp)
249: char *cp;
250: {
251: extern char end[];
252:
253: return (cp < end);
254: }
255:
256: xfree(cp)
257: char *cp;
258: {
259: extern char end[];
260:
261: if (cp >= end && cp < (char *) &cp)
262: cfree(cp);
263: }
264:
265: char *
266: savestr(s)
267: register char *s;
268: {
269: register char *n;
270:
271: if (s == 0)
272: s = "";
273: strcpy(n = calloc(1, strlen(s) + 1), s);
274: return (n);
275: }
276:
277: static char *putp;
278:
279: char *
280: putn(n)
281: register int n;
282: {
283: static char number[15];
284:
285: putp = number;
286: if (n < 0) {
287: n = -n;
288: *putp++ = '-';
289: }
290: if (sizeof (int) == 2 && n == -32768) {
291: *putp++ = '3';
292: n = 2768;
293: #ifdef pdp11
294: }
295: #else
296: } else if (sizeof (int) == 4 && n == -2147483648) {
297: *putp++ = '2';
298: n = 147483648;
299: }
300: #endif
301: putn1(n);
302: *putp = 0;
303: return (savestr(number));
304: }
305:
306: putn1(n)
307: register int n;
308: {
309: if (n > 9)
310: putn1(n / 10);
311: *putp++ = n % 10 + '0';
312: }
313:
314: getn(cp)
315: register char *cp;
316: {
317: register int n;
318: int sign;
319:
320: sign = 0;
321: if (cp[0] == '+' && cp[1])
322: cp++;
323: if (*cp == '-') {
324: sign++;
325: cp++;
326: if (!digit(*cp))
327: goto badnum;
328: }
329: n = 0;
330: while (digit(*cp))
331: n = n * 10 + *cp++ - '0';
332: if (*cp)
333: goto badnum;
334: return (sign ? -n : n);
335: badnum:
336: bferr("Badly formed number");
337: return (0);
338: }
339:
340: char *
341: value(var)
342: char *var;
343: {
344:
345: return (value1(var, &shvhed));
346: }
347:
348: char *
349: value1(var, head)
350: char *var;
351: struct varent *head;
352: {
353: register struct varent *vp;
354:
355: vp = adrof1(var, head);
356: return (vp == 0 || vp->vec[0] == 0 ? "" : vp->vec[0]);
357: }
358:
359: static struct varent *shprev;
360:
361: struct varent *
362: adrof(var)
363: char *var;
364: {
365:
366: return (adrof1(var, &shvhed));
367: }
368:
369: struct varent *
370: madrof(pat, head)
371: char *pat;
372: struct varent *head;
373: {
374: register struct varent *vp;
375:
376: shprev = head;
377: for (vp = shprev->link; vp != 0; vp = vp->link) {
378: if (Gmatch(vp->name, pat))
379: return (vp);
380: shprev = vp;
381: }
382: return (0);
383: }
384:
385: struct varent *
386: adrof1(var, head)
387: char *var;
388: struct varent *head;
389: {
390: register struct varent *vp;
391: int cmp;
392:
393: shprev = head;
394: for (vp = shprev->link; vp != 0; vp = vp->link) {
395: cmp = strcmp(vp->name, var);
396: if (cmp == 0)
397: return (vp);
398: else if (cmp > 0)
399: return (0);
400: shprev = vp;
401: }
402: return (0);
403: }
404:
405: /*
406: * The caller is responsible for putting value in a safe place
407: */
408: set(var, value)
409: char *var, *value;
410: {
411: register char **vec = (char **) calloc(2, sizeof (char **));
412:
413: vec[0] = onlyread(value) ? savestr(value) : value;
414: set1(var, vec, &shvhed);
415: }
416:
417: set1(var, vec, head)
418: char *var, **vec;
419: struct varent *head;
420: {
421:
422: register char **oldv = vec;
423:
424: gflag = 0; rscan(oldv, tglob);
425: if (gflag) {
426: vec = glob(oldv);
427: if (vec == 0) {
428: bferr("No match");
429: blkfree(oldv);
430: return;
431: }
432: blkfree(oldv);
433: gargv = 0;
434: }
435: setq(var, vec, head);
436: }
437:
438: setq(var, vec, head)
439: char *var, **vec;
440: struct varent *head;
441: {
442: register struct varent *vp;
443:
444: vp = adrof1(var, head);
445: if (vp == 0) {
446: vp = (struct varent *) calloc(1, sizeof *vp);
447: vp->name = savestr(var);
448: vp->link = shprev->link;
449: shprev->link = vp;
450: }
451: if (vp->vec)
452: blkfree(vp->vec);
453: scan(vec, trim);
454: vp->vec = vec;
455: }
456:
457: unset(v)
458: register char *v[];
459: {
460:
461: unset1(v, &shvhed);
462: if (adrof("histchars") == 0) {
463: HIST = '!';
464: HISTSUB = '^';
465: }
466: }
467:
468: unset1(v, head)
469: register char *v[];
470: struct varent *head;
471: {
472: register char *var;
473: register struct varent *vp;
474: register int cnt;
475:
476: v++;
477: while (var = *v++) {
478: cnt = 0;
479: while (vp = madrof(var, head))
480: unsetv1(vp->name, head), cnt++;
481: if (cnt == 0)
482: setname(var);
483: }
484: }
485:
486: unsetv(var)
487: char *var;
488: {
489:
490: unsetv1(var, &shvhed);
491: }
492:
493: unsetv1(var, head)
494: char *var;
495: struct varent *head;
496: {
497: register struct varent *vp;
498:
499: vp = adrof1(var, head);
500: if (vp == 0)
501: udvar(var);
502: vp = shprev->link;
503: shprev->link = vp->link;
504: blkfree(vp->vec);
505: xfree(vp->name);
506: xfree((char *)vp);
507: }
508:
509: setNS(cp)
510: char *cp;
511: {
512:
513: set(cp, "");
514: }
515:
516: shift(v)
517: register char **v;
518: {
519: register struct varent *argv;
520: register char *name;
521:
522: v++;
523: name = *v;
524: if (name == 0)
525: name = "argv";
526: else
527: strip(name);
528: argv = adrof(name);
529: if (argv == 0)
530: udvar(name);
531: if (argv->vec[0] == 0)
532: bferr("No more words");
533: lshift(argv->vec, 1);
534: }
535:
536: exportpath(val)
537: char **val;
538: {
539: char exppath[BUFSIZ];
540: register char *dir;
541:
542: exppath[0] = 0;
543: if (val)
544: while (*val) {
545: if (strlen(*val) + strlen(exppath) + 2 > BUFSIZ) {
546: printf("Warning: ridiculously long PATH truncated\n");
547: break;
548: }
549: strcat(exppath, *val++);
550: if (*val == 0 || eq(*val, ")"))
551: break;
552: strcat(exppath, ":");
553: }
554: setenv("PATH", exppath);
555: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.