1: static char *sccsid = "@(#)sh.misc.c 4.1 10/9/80"; 2: 3: #include "sh.h" 4: 5: /* 6: * C Shell 7: */ 8: 9: letter(c) 10: register char c; 11: { 12: 13: return (c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z' || c == '_'); 14: } 15: 16: digit(c) 17: register char c; 18: { 19: 20: return (c >= '0' && c <= '9'); 21: } 22: 23: alnum(c) 24: register char c; 25: { 26: return (letter(c) || digit(c)); 27: } 28: 29: any(c, s) 30: register int c; 31: register char *s; 32: { 33: 34: while (*s) 35: if (*s++ == c) 36: return(1); 37: return(0); 38: } 39: 40: char * 41: calloc(i, j) 42: register unsigned i; 43: unsigned j; 44: { 45: register char *cp, *dp; 46: #ifdef debug 47: static char *av[2] = {0, 0}; 48: #endif 49: 50: i *= j; 51: cp = (char *) malloc(i); 52: if (cp == 0) { 53: child++; 54: #ifndef debug 55: error("Out of memory"); 56: #else 57: showall(av); 58: printf("i=%d, j=%d: ", i/j, j); 59: printf("Out of memory\n"); 60: chdir("/usr/bill/cshcore"); 61: abort(); 62: #endif 63: } 64: dp = cp; 65: if (i != 0) 66: do 67: *dp++ = 0; 68: while (--i); 69: return (cp); 70: } 71: 72: cfree(p) 73: char *p; 74: { 75: 76: free(p); 77: } 78: 79: char ** 80: blkend(up) 81: register char **up; 82: { 83: 84: while (*up) 85: up++; 86: return (up); 87: } 88: 89: blkpr(av) 90: register char **av; 91: { 92: 93: for (; *av; av++) { 94: printf("%s", *av); 95: if (av[1]) 96: printf(" "); 97: } 98: } 99: 100: blklen(av) 101: register char **av; 102: { 103: register int i = 0; 104: 105: while (*av++) 106: i++; 107: return (i); 108: } 109: 110: char ** 111: blkcpy(oav, bv) 112: char **oav; 113: register char **bv; 114: { 115: register char **av = oav; 116: 117: while (*av++ = *bv++) 118: continue; 119: return (oav); 120: } 121: 122: char ** 123: blkcat(up, vp) 124: char **up, **vp; 125: { 126: 127: blkcpy(blkend(up), vp); 128: return (up); 129: } 130: 131: blkfree(av0) 132: char **av0; 133: { 134: register char **av = av0; 135: 136: while (*av) 137: xfree(*av++); 138: xfree((char *)av0); 139: } 140: 141: char ** 142: saveblk(v) 143: register char **v; 144: { 145: register int len = blklen(v) + 1; 146: register char **newv = (char **) calloc(len, sizeof (char **)); 147: char **onewv = newv; 148: 149: while (*v) 150: *newv++ = savestr(*v++); 151: return (onewv); 152: } 153: 154: char * 155: strspl(cp, dp) 156: register char *cp, *dp; 157: { 158: register char *ep = calloc(1, strlen(cp) + strlen(dp) + 1); 159: 160: strcpy(ep, cp); 161: strcat(ep, dp); 162: return (ep); 163: } 164: 165: char ** 166: blkspl(up, vp) 167: register char **up, **vp; 168: { 169: register char **wp = (char **) calloc(blklen(up) + blklen(vp) + 1, sizeof (char **)); 170: 171: blkcpy(wp, up); 172: return (blkcat(wp, vp)); 173: } 174: 175: lastchr(cp) 176: register char *cp; 177: { 178: 179: if (!*cp) 180: return (0); 181: while (cp[1]) 182: cp++; 183: return (*cp); 184: } 185: 186: /* 187: * This routine is called after an error to close up 188: * any units which may have been left open accidentally. 189: */ 190: closem() 191: { 192: register int f; 193: 194: for (f = 0; f < NOFILE; f++) 195: if (f != SHIN && f != SHOUT && f != SHDIAG && f != OLDSTD && 196: f != FSHTTY) 197: close(f); 198: } 199: 200: /* 201: * Close files before executing a file. 202: * We could be MUCH more intelligent, since (on a version 7 system) 203: * we need only close files here during a source, the other 204: * shell fd's being in units 16-19 which are closed automatically! 205: */ 206: closech() 207: { 208: register int f; 209: 210: if (didcch) 211: return; 212: didcch = 1; 213: SHIN = 0; SHOUT = 1; SHDIAG = 2; OLDSTD = 0; 214: for (f = 3; f < NOFILE; f++) 215: close(f); 216: } 217: 218: donefds() 219: { 220: 221: close(0), close(1), close(2); 222: didfds = 0; 223: } 224: 225: /* 226: * Move descriptor i to j. 227: * If j is -1 then we just want to get i to a safe place, 228: * i.e. to a unit > 2. This also happens in dcopy. 229: */ 230: dmove(i, j) 231: register int i, j; 232: { 233: 234: if (i == j || i < 0) 235: return (i); 236: #ifdef V7 237: if (j >= 0) { 238: dup2(i, j); 239: return (j); 240: } else 241: #endif 242: j = dcopy(i, j); 243: if (j != i) 244: close(i); 245: return (j); 246: } 247: 248: dcopy(i, j) 249: register int i, j; 250: { 251: 252: if (i == j || i < 0 || j < 0 && i > 2) 253: return (i); 254: #ifdef V7 255: if (j >= 0) { 256: dup2(i, j); 257: return (j); 258: } 259: #endif 260: close(j); 261: return (renum(i, j)); 262: } 263: 264: renum(i, j) 265: register int i, j; 266: { 267: register int k = dup(i); 268: 269: if (k < 0) 270: return (-1); 271: if (j == -1 && k > 2) 272: return (k); 273: if (k != j) { 274: j = renum(k, j); 275: close(k); 276: return (j); 277: } 278: return (k); 279: } 280: 281: copy(to, from, size) 282: register char *to, *from; 283: register int size; 284: { 285: 286: if (size) 287: do 288: *to++ = *from++; 289: while (--size != 0); 290: } 291: 292: /* 293: * Left shift a command argument list, discarding 294: * the first c arguments. Used in "shift" commands 295: * as well as by commands like "repeat". 296: */ 297: lshift(v, c) 298: register char **v; 299: register int c; 300: { 301: register char **u = v; 302: 303: while (*u && --c >= 0) 304: xfree(*u++); 305: blkcpy(v, u); 306: } 307: 308: number(cp) 309: char *cp; 310: { 311: 312: if (*cp == '-') { 313: cp++; 314: if (!digit(*cp++)) 315: return (0); 316: } 317: while (*cp && digit(*cp)) 318: cp++; 319: return (*cp == 0); 320: } 321: 322: char ** 323: copyblk(v) 324: register char **v; 325: { 326: register char **nv = (char **) calloc(blklen(v) + 1, sizeof (char **)); 327: 328: return (blkcpy(nv, v)); 329: } 330: 331: char * 332: strend(cp) 333: register char *cp; 334: { 335: 336: while (*cp) 337: cp++; 338: return (cp); 339: } 340: 341: char * 342: strip(cp) 343: char *cp; 344: { 345: register char *dp = cp; 346: 347: while (*dp++ &= TRIM) 348: continue; 349: return (cp); 350: } 351: 352: udvar(name) 353: char *name; 354: { 355: 356: setname(name); 357: bferr("Undefined variable"); 358: } 359: 360: prefix(sub, str) 361: register char *sub, *str; 362: { 363: 364: for (;;) { 365: if (*sub == 0) 366: return (1); 367: if (*str == 0) 368: return (0); 369: if (*sub++ != *str++) 370: return (0); 371: } 372: }