|
|
1.1 ! root 1: #ifndef lint ! 2: static char sccsid[] = "@(#)xec.c 4.3 8/11/83"; ! 3: #endif ! 4: ! 5: # ! 6: /* ! 7: * UNIX shell ! 8: * ! 9: * S. R. Bourne ! 10: * Bell Telephone Laboratories ! 11: * ! 12: */ ! 13: ! 14: #include "defs.h" ! 15: #include "sym.h" ! 16: ! 17: LOCAL INT parent; ! 18: ! 19: SYSTAB commands; ! 20: ! 21: ! 22: ! 23: /* ======== command execution ========*/ ! 24: ! 25: ! 26: execute(argt, execflg, pf1, pf2) ! 27: TREPTR argt; ! 28: INT *pf1, *pf2; ! 29: { ! 30: /* `stakbot' is preserved by this routine */ ! 31: REG TREPTR t; ! 32: STKPTR sav=savstak(); ! 33: ! 34: sigchk(); ! 35: ! 36: IF (t=argt) ANDF execbrk==0 ! 37: THEN REG INT treeflgs; ! 38: INT oldexit, type; ! 39: REG STRING *com; ! 40: ! 41: treeflgs = t->tretyp; type = treeflgs&COMMSK; ! 42: oldexit=exitval; exitval=0; ! 43: ! 44: SWITCH type IN ! 45: ! 46: case TCOM: ! 47: BEGIN ! 48: STRING a1; ! 49: INT argn, internal; ! 50: ARGPTR schain=gchain; ! 51: IOPTR io=t->treio; ! 52: gchain=0; ! 53: argn = getarg(t); ! 54: com=scan(argn); ! 55: a1=com[1]; gchain=schain; ! 56: ! 57: IF argn==0 ORF (internal=syslook(com[0],commands)) ! 58: THEN setlist(t->comset, 0); ! 59: FI ! 60: ! 61: IF argn ANDF (flags&noexec)==0 ! 62: THEN /* print command if execpr */ ! 63: IF flags&execpr ! 64: THEN argn=0; prs(execpmsg); ! 65: WHILE com[argn]!=ENDARGS ! 66: DO prs(com[argn++]); blank() OD ! 67: newline(); ! 68: FI ! 69: ! 70: SWITCH internal IN ! 71: ! 72: case SYSDOT: ! 73: IF a1 ! 74: THEN REG INT f; ! 75: ! 76: IF (f=pathopen(getpath(a1), a1)) < 0 ! 77: THEN failed(a1,notfound); ! 78: ELSE execexp(0,f); ! 79: FI ! 80: FI ! 81: break; ! 82: ! 83: case SYSTIMES: ! 84: { ! 85: L_INT t[4]; times(t); ! 86: prt(t[2]); blank(); prt(t[3]); newline(); ! 87: } ! 88: break; ! 89: ! 90: case SYSEXIT: ! 91: exitsh(a1?stoi(a1):oldexit); ! 92: ! 93: case SYSNULL: ! 94: io=0; ! 95: break; ! 96: ! 97: case SYSCONT: ! 98: execbrk = -loopcnt; break; ! 99: ! 100: case SYSBREAK: ! 101: IF (execbrk=loopcnt) ANDF a1 ! 102: THEN breakcnt=stoi(a1); ! 103: FI ! 104: break; ! 105: ! 106: case SYSTRAP: ! 107: IF a1 ! 108: THEN BOOL clear; ! 109: IF (clear=digit(*a1))==0 ! 110: THEN ++com; ! 111: FI ! 112: WHILE *++com ! 113: DO INT i; ! 114: IF (i=stoi(*com))>=MAXTRAP ORF i<MINTRAP ! 115: THEN failed(*com,badtrap); ! 116: ELIF clear ! 117: THEN clrsig(i); ! 118: ELSE replace(&trapcom[i],a1); ! 119: IF *a1 ! 120: THEN getsig(i); ! 121: ELSE ignsig(i); ! 122: FI ! 123: FI ! 124: OD ! 125: ELSE /* print out current traps */ ! 126: INT i; ! 127: ! 128: FOR i=0; i<MAXTRAP; i++ ! 129: DO IF trapcom[i] ! 130: THEN prn(i); prs(colon); prs(trapcom[i]); newline(); ! 131: FI ! 132: OD ! 133: FI ! 134: break; ! 135: ! 136: case SYSEXEC: ! 137: com++; ! 138: initio(io); ioset=0; io=0; ! 139: IF a1==0 THEN break FI ! 140: ! 141: case SYSLOGIN: ! 142: flags |= forked; ! 143: oldsigs(); execa(com); done(); ! 144: ! 145: case SYSCD: ! 146: IF flags&rshflg ! 147: THEN failed(com[0],restricted); ! 148: ELIF (a1==0 ANDF (a1=homenod.namval)==0) ORF chdir(a1)<0 ! 149: THEN failed(a1,baddir); ! 150: FI ! 151: break; ! 152: ! 153: case SYSSHFT: ! 154: IF dolc<1 ! 155: THEN error(badshift); ! 156: ELSE dolv++; dolc--; ! 157: FI ! 158: assnum(&dolladr, dolc); ! 159: break; ! 160: ! 161: case SYSWAIT: ! 162: await(-1); ! 163: break; ! 164: ! 165: case SYSREAD: ! 166: exitval=readvar(&com[1]); ! 167: break; ! 168: ! 169: /* ! 170: case SYSTST: ! 171: exitval=testcmd(com); ! 172: break; ! 173: */ ! 174: ! 175: case SYSSET: ! 176: IF a1 ! 177: THEN INT argc; ! 178: argc = options(argn,com); ! 179: IF argc>1 ! 180: THEN setargs(com+argn-argc); ! 181: FI ! 182: ELIF t->comset==0 ! 183: THEN /*scan name chain and print*/ ! 184: namscan(printnam); ! 185: FI ! 186: break; ! 187: ! 188: case SYSRDONLY: ! 189: exitval=N_RDONLY; ! 190: case SYSXPORT: ! 191: IF exitval==0 THEN exitval=N_EXPORT; FI ! 192: ! 193: IF a1 ! 194: THEN WHILE *++com ! 195: DO attrib(lookup(*com), exitval) OD ! 196: ELSE namscan(printflg); ! 197: FI ! 198: exitval=0; ! 199: break; ! 200: ! 201: case SYSEVAL: ! 202: IF a1 ! 203: THEN execexp(a1,&com[2]); ! 204: FI ! 205: break; ! 206: ! 207: case SYSUMASK: ! 208: if (a1) { ! 209: int c, i ! 210: i = 0; ! 211: while ((c = *a1++) >= '0' && ! 212: c <= '7') ! 213: i = (i << 3) + c - '0'; ! 214: umask(i); ! 215: } else { ! 216: int i, j; ! 217: umask(i = umask(0)); ! 218: prc('0'); ! 219: for (j = 6; j >= 0; j -= 3) ! 220: prc(((i>>j)&07) + '0'); ! 221: newline(); ! 222: } ! 223: break; ! 224: ! 225: default: ! 226: internal=builtin(argn,com); ! 227: ! 228: ENDSW ! 229: ! 230: IF internal ! 231: THEN IF io THEN error(illegal) FI ! 232: chktrap(); ! 233: break; ! 234: FI ! 235: ELIF t->treio==0 ! 236: THEN break; ! 237: FI ! 238: END ! 239: ! 240: case TFORK: ! 241: IF execflg ANDF (treeflgs&(FAMP|FPOU))==0 ! 242: THEN parent=0; ! 243: ELSE WHILE (parent=fork()) == -1 ! 244: DO sigchk(); alarm(10); pause() OD ! 245: FI ! 246: ! 247: IF parent ! 248: THEN /* This is the parent branch of fork; */ ! 249: /* it may or may not wait for the child. */ ! 250: IF treeflgs&FPRS ANDF flags&ttyflg ! 251: THEN prn(parent); newline(); ! 252: FI ! 253: IF treeflgs&FPCL THEN closepipe(pf1) FI ! 254: IF (treeflgs&(FAMP|FPOU))==0 ! 255: THEN await(parent); ! 256: ELIF (treeflgs&FAMP)==0 ! 257: THEN post(parent); ! 258: ELSE assnum(&pcsadr, parent); ! 259: FI ! 260: ! 261: chktrap(); ! 262: break; ! 263: ! 264: ! 265: ELSE /* this is the forked branch (child) of execute */ ! 266: flags |= forked; iotemp=0; ! 267: postclr(); ! 268: settmp(); ! 269: ! 270: /* Turn off INTR and QUIT if `FINT' */ ! 271: /* Reset ramaining signals to parent */ ! 272: /* except for those `lost' by trap */ ! 273: oldsigs(); ! 274: IF treeflgs&FINT ! 275: THEN signal(INTR,1); signal(QUIT,1); ! 276: FI ! 277: ! 278: /* pipe in or out */ ! 279: IF treeflgs&FPIN ! 280: THEN rename(pf1[INPIPE],0); ! 281: close(pf1[OTPIPE]); ! 282: FI ! 283: IF treeflgs&FPOU ! 284: THEN rename(pf2[OTPIPE],1); ! 285: close(pf2[INPIPE]); ! 286: FI ! 287: ! 288: /* default std input for & */ ! 289: IF treeflgs&FINT ANDF ioset==0 ! 290: THEN rename(chkopen(devnull),0); ! 291: FI ! 292: ! 293: /* io redirection */ ! 294: initio(t->treio); ! 295: IF type!=TCOM ! 296: THEN execute(t->forktre,1); ! 297: ELIF com[0]!=ENDARGS ! 298: THEN setlist(t->comset,N_EXPORT); ! 299: execa(com); ! 300: FI ! 301: done(); ! 302: FI ! 303: ! 304: case TPAR: ! 305: rename(dup(2),output); ! 306: execute(t->partre,execflg); ! 307: done(); ! 308: ! 309: case TFIL: ! 310: BEGIN ! 311: INT pv[2]; chkpipe(pv); ! 312: IF execute(t->lstlef, 0, pf1, pv)==0 ! 313: THEN execute(t->lstrit, execflg, pv, pf2); ! 314: ELSE closepipe(pv); ! 315: FI ! 316: END ! 317: break; ! 318: ! 319: case TLST: ! 320: execute(t->lstlef,0); ! 321: execute(t->lstrit,execflg); ! 322: break; ! 323: ! 324: case TAND: ! 325: IF execute(t->lstlef,0)==0 ! 326: THEN execute(t->lstrit,execflg); ! 327: FI ! 328: break; ! 329: ! 330: case TORF: ! 331: IF execute(t->lstlef,0)!=0 ! 332: THEN execute(t->lstrit,execflg); ! 333: FI ! 334: break; ! 335: ! 336: case TFOR: ! 337: BEGIN ! 338: NAMPTR n = lookup(t->fornam); ! 339: STRING *args; ! 340: DOLPTR argsav=0; ! 341: ! 342: IF t->forlst==0 ! 343: THEN args=dolv+1; ! 344: argsav=useargs(); ! 345: ELSE ARGPTR schain=gchain; ! 346: gchain=0; ! 347: trim((args=scan(getarg(t->forlst)))[0]); ! 348: gchain=schain; ! 349: FI ! 350: loopcnt++; ! 351: WHILE *args!=ENDARGS ANDF execbrk==0 ! 352: DO assign(n,*args++); ! 353: execute(t->fortre,0); ! 354: IF execbrk<0 THEN execbrk=0 FI ! 355: OD ! 356: IF breakcnt THEN breakcnt-- FI ! 357: execbrk=breakcnt; loopcnt--; ! 358: argfor=freeargs(argsav); ! 359: END ! 360: break; ! 361: ! 362: case TWH: ! 363: case TUN: ! 364: BEGIN ! 365: INT i=0; ! 366: ! 367: loopcnt++; ! 368: WHILE execbrk==0 ANDF (execute(t->whtre,0)==0)==(type==TWH) ! 369: DO i=execute(t->dotre,0); ! 370: IF execbrk<0 THEN execbrk=0 FI ! 371: OD ! 372: IF breakcnt THEN breakcnt-- FI ! 373: execbrk=breakcnt; loopcnt--; exitval=i; ! 374: END ! 375: break; ! 376: ! 377: case TIF: ! 378: IF execute(t->iftre,0)==0 ! 379: THEN execute(t->thtre,execflg); ! 380: ELSE execute(t->eltre,execflg); ! 381: FI ! 382: break; ! 383: ! 384: case TSW: ! 385: BEGIN ! 386: REG STRING r = mactrim(t->swarg); ! 387: t=t->swlst; ! 388: WHILE t ! 389: DO ARGPTR rex=t->regptr; ! 390: WHILE rex ! 391: DO REG STRING s; ! 392: IF gmatch(r,s=macro(rex->argval)) ORF (trim(s), eq(r,s)) ! 393: THEN execute(t->regcom,0); ! 394: t=0; break; ! 395: ELSE rex=rex->argnxt; ! 396: FI ! 397: OD ! 398: IF t THEN t=t->regnxt FI ! 399: OD ! 400: END ! 401: break; ! 402: ENDSW ! 403: exitset(); ! 404: FI ! 405: ! 406: sigchk(); ! 407: tdystak(sav); ! 408: return(exitval); ! 409: } ! 410: ! 411: ! 412: execexp(s,f) ! 413: STRING s; ! 414: UFD f; ! 415: { ! 416: FILEBLK fb; ! 417: push(&fb); ! 418: IF s ! 419: THEN estabf(s); fb.feval=f; ! 420: ELIF f>=0 ! 421: THEN initf(f); ! 422: FI ! 423: execute(cmd(NL, NLFLG|MTFLG),0); ! 424: pop(); ! 425: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.