1: /* $Header: util.c,v 4.3.1.2 85/05/15 14:44:27 lwall Exp $
   2:  *
   3:  * $Log:	util.c,v $
   4:  * Revision 4.3.1.2  85/05/15  14:44:27  lwall
   5:  * Last arg of execl changed from 0 to Nullch [(char*)0].
   6:  *
   7:  * Revision 4.3.1.1  85/05/10  11:41:30  lwall
   8:  * Branch for patches.
   9:  *
  10:  * Revision 4.3  85/05/01  11:51:44  lwall
  11:  * Baseline for release with 4.3bsd.
  12:  *
  13:  */
  14: 
  15: #include "EXTERN.h"
  16: #include "common.h"
  17: #include "final.h"
  18: #include "ndir.h"
  19: #include "INTERN.h"
  20: #include "util.h"
  21: 
  22: void
  23: util_init()
  24: {
  25:     ;
  26: }
  27: 
  28: /* fork and exec a shell command */
  29: 
  30: int
  31: doshell(shl,s)
  32: char *s, *shl;
  33: {
  34:     int status, pid, w;
  35:     register int (*istat)(), (*qstat)();
  36:     int (*signal())();
  37:     char *shell;
  38: 
  39: #ifdef SIGTSTP
  40:     sigset(SIGTSTP,SIG_DFL);
  41:     sigset(SIGCONT,SIG_DFL);
  42: #endif
  43:     if (shl != Nullch)
  44:     shell = shl;
  45:     else if ((shell = getenv("SHELL")) == Nullch || !*shell)
  46:     shell = PREFSHELL;
  47:     if ((pid = fork()) == 0) {
  48:     if (*s) {
  49:         if (execl(shell, shell, "-c", s, Nullch) < 0)
  50:         perror("execl");
  51:     }
  52:     else {
  53:         if (execl(shell, shell, Nullch, Nullch, Nullch) < 0)
  54:         perror("execl");
  55:     }
  56:     _exit(127);
  57:     }
  58: #ifndef lint
  59:     istat = signal(SIGINT, SIG_IGN);
  60:     qstat = signal(SIGQUIT, SIG_IGN);
  61: #else
  62:     istat = Null(int (*)());
  63:     qstat = Null(int (*)());
  64: #endif lint
  65:     waiting = TRUE;
  66:     while ((w = wait(&status)) != pid && w != -1)
  67:     ;
  68:     if (w == -1)
  69:     status = -1;
  70:     waiting = FALSE;
  71:     signal(SIGINT, istat);
  72:     signal(SIGQUIT, qstat);
  73: #ifdef SIGTSTP
  74:     sigset(SIGTSTP,stop_catcher);
  75:     sigset(SIGCONT,cont_catcher);
  76: #endif
  77:     return status;
  78: }
  79: 
  80: static char nomem[] = "rn: out of memory!\n";
  81: 
  82: /* paranoid version of malloc */
  83: 
  84: char *
  85: safemalloc(size)
  86: MEM_SIZE size;
  87: {
  88:     char *ptr;
  89:     char *malloc();
  90: 
  91:     ptr = malloc(size?size:1);  /* malloc(0) is NASTY on our system */
  92:     if (ptr != Nullch)
  93:     return ptr;
  94:     else {
  95:     fputs(nomem,stdout) FLUSH;
  96:     sig_catcher(0);
  97:     }
  98:     /*NOTREACHED*/
  99: }
 100: 
 101: /* paranoid version of realloc */
 102: 
 103: char *
 104: saferealloc(where,size)
 105: char *where;
 106: MEM_SIZE size;
 107: {
 108:     char *ptr;
 109:     char *realloc();
 110: 
 111:     ptr = realloc(where,size?size:1);   /* realloc(0) is NASTY on our system */
 112:     if (ptr != Nullch)
 113:     return ptr;
 114:     else {
 115:     fputs(nomem,stdout) FLUSH;
 116:     sig_catcher(0);
 117:     }
 118:     /*NOTREACHED*/
 119: }
 120: 
 121: /* safe version of string copy */
 122: 
 123: char *
 124: safecpy(to,from,len)
 125: char *to;
 126: register char *from;
 127: register int len;
 128: {
 129:     register char *dest = to;
 130: 
 131:     if (from != Nullch)
 132:     for (len--; len && (*dest++ = *from++); len--) ;
 133:     *dest = '\0';
 134:     return to;
 135: }
 136: 
 137: /* safe version of string concatenate, with \n deletion and space padding */
 138: 
 139: char *
 140: safecat(to,from,len)
 141: char *to;
 142: register char *from;
 143: register int len;
 144: {
 145:     register char *dest = to;
 146: 
 147:     len--;              /* leave room for null */
 148:     if (*dest) {
 149:     while (len && *dest++) len--;
 150:     if (len) {
 151:         len--;
 152:         *(dest-1) = ' ';
 153:     }
 154:     }
 155:     if (from != Nullch)
 156:     while (len && (*dest++ = *from++)) len--;
 157:     if (len)
 158:     dest--;
 159:     if (*(dest-1) == '\n')
 160:     dest--;
 161:     *dest = '\0';
 162:     return to;
 163: }
 164: 
 165: /* copy a string up to some (non-backslashed) delimiter, if any */
 166: 
 167: char *
 168: cpytill(to,from,delim)
 169: register char *to, *from;
 170: register int delim;
 171: {
 172:     for (; *from; from++,to++) {
 173:     if (*from == '\\' && from[1] == delim)
 174:         from++;
 175:     else if (*from == delim)
 176:         break;
 177:     *to = *from;
 178:     }
 179:     *to = '\0';
 180:     return from;
 181: }
 182: 
 183: /* return ptr to little string in big string, NULL if not found */
 184: 
 185: char *
 186: instr(big, little)
 187: char *big, *little;
 188: 
 189: {
 190:     register char *t, *s, *x;
 191: 
 192:     for (t = big; *t; t++) {
 193:     for (x=t,s=little; *s; x++,s++) {
 194:         if (!*x)
 195:         return Nullch;
 196:         if (*s != *x)
 197:         break;
 198:     }
 199:     if (!*s)
 200:         return t;
 201:     }
 202:     return Nullch;
 203: }
 204: 
 205: /* effective access */
 206: 
 207: #ifdef SETUIDGID
 208: int
 209: eaccess(filename, mod)
 210: char *filename;
 211: int mod;
 212: {
 213:     int protection, euid;
 214: 
 215:     mod &= 7;               /* remove extraneous garbage */
 216:     if (stat(filename, &filestat) < 0)
 217:     return -1;
 218:     euid = geteuid();
 219:     if (euid == ROOTID)
 220:     return 0;
 221:     protection = 7 & (filestat.st_mode >>
 222:       (filestat.st_uid == euid ? 6 :
 223:         (filestat.st_gid == getegid() ? 3 : 0)
 224:       ));
 225:     if ((mod & protection) == mod)
 226:     return 0;
 227:     errno = EACCES;
 228:     return -1;
 229: }
 230: #endif
 231: 
 232: /*
 233:  * Get working directory
 234:  */
 235: 
 236: #ifdef GETWD
 237: #define dot "."
 238: #define dotdot  ".."
 239: 
 240: static  char    *name;
 241: 
 242: static  DIR *dirp;
 243: static  int off;
 244: static  struct  stat    d, dd;
 245: static  struct  direct  *dir;
 246: 
 247: char *
 248: getwd(np)
 249: char *np;
 250: {
 251:     long rdev, rino;
 252: 
 253:     *np++ = '/';
 254:     *np = 0;
 255:     name = np;
 256:     off = -1;
 257:     stat("/", &d);
 258:     rdev = d.st_dev;
 259:     rino = d.st_ino;
 260:     for (;;) {
 261:         stat(dot, &d);
 262:         if (d.st_ino==rino && d.st_dev==rdev)
 263:             goto done;
 264:         if ((dirp = opendir(dotdot)) == Null(DIR *))
 265:             prexit("getwd: cannot open ..\n");
 266:         stat(dotdot, &dd);
 267:         chdir(dotdot);
 268:         if(d.st_dev == dd.st_dev) {
 269:             if(d.st_ino == dd.st_ino)
 270:                 goto done;
 271:             do
 272:                 if ((dir = readdir(dirp)) == Null(struct direct *))
 273:                     prexit("getwd: read error in ..\n");
 274:             while (dir->d_ino != d.st_ino);
 275:         }
 276:         else do {
 277:                 if ((dir = readdir(dirp)) == Null(struct direct *))
 278:                     prexit("getwd: read error in ..\n");
 279:                 stat(dir->d_name, &dd);
 280:             } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev);
 281:         cat();
 282:         closedir(dirp);
 283:     }
 284: done:
 285:     name--;
 286:     if (chdir(name) < 0) {
 287:         printf("getwd: can't cd back to %s\n",name) FLUSH;
 288:         sig_catcher(0);
 289:     }
 290:     return (name);
 291: }
 292: 
 293: void
 294: cat()
 295: {
 296:     register i, j;
 297: 
 298:     i = -1;
 299:     while (dir->d_name[++i] != 0);
 300:     if ((off+i+2) > 1024-1)
 301:         return;
 302:     for(j=off+1; j>=0; --j)
 303:         name[j+i+1] = name[j];
 304:     if (off >= 0)
 305:         name[i] = '/';
 306:     off=i+off+1;
 307:     name[off] = 0;
 308:     for(--i; i>=0; --i)
 309:         name[i] = dir->d_name[i];
 310: }
 311: 
 312: void
 313: prexit(cp)
 314: char *cp;
 315: {
 316:     write(2, cp, strlen(cp));
 317:     sig_catcher(0);
 318: }
 319: #else
 320: char *
 321: getwd(np)           /* shorter but slower */
 322: char *np;
 323: {
 324:     FILE *popen();
 325:     FILE *pipefp = popen("/bin/pwd","r");
 326: 
 327:     if (pipefd == Nullfp) {
 328:     printf("Can't run /bin/pwd\n") FLUSH;
 329:     finalize(1);
 330:     }
 331:     fgets(np,512,pipefp);
 332:     np[strlen(np)-1] = '\0';    /* wipe out newline */
 333:     pclose(pipefp);
 334:     return np;
 335: }
 336: #endif
 337: 
 338: /* just like fgets but will make bigger buffer as necessary */
 339: 
 340: char *
 341: get_a_line(original_buffer,buffer_length,fp)
 342: char *original_buffer;
 343: register int buffer_length;
 344: FILE *fp;
 345: {
 346:     register int bufix = 0;
 347:     register int nextch;
 348:     register char *some_buffer_or_other = original_buffer;
 349: 
 350:     do {
 351:     if (bufix >= buffer_length) {
 352:         buffer_length *= 2;
 353:         if (some_buffer_or_other == original_buffer) {
 354:                     /* currently static? */
 355:         some_buffer_or_other = safemalloc((MEM_SIZE)buffer_length+1);
 356:         strncpy(some_buffer_or_other,original_buffer,buffer_length/2);
 357:                     /* so we must copy it */
 358:         }
 359:         else {          /* just grow in place, if possible */
 360:         some_buffer_or_other = saferealloc(some_buffer_or_other,
 361:             (MEM_SIZE)buffer_length+1);
 362:         }
 363:     }
 364:     if ((nextch = getc(fp)) == EOF)
 365:         return Nullch;
 366:     some_buffer_or_other[bufix++] = (char) nextch;
 367:     } while (nextch && nextch != '\n');
 368:     some_buffer_or_other[bufix] = '\0';
 369:     len_last_line_got = bufix;
 370:     return some_buffer_or_other;
 371: }
 372: 
 373: /* copy a string to a safe spot */
 374: 
 375: char *
 376: savestr(str)
 377: char *str;
 378: {
 379:     register char *newaddr = safemalloc((MEM_SIZE)(strlen(str)+1));
 380: 
 381:     strcpy(newaddr,str);
 382:     return newaddr;
 383: }
 384: 
 385: int
 386: makedir(dirname,nametype)
 387: register char *dirname;
 388: int nametype;
 389: {
 390: #ifdef MAKEDIR
 391:     register char *end;
 392:     register char *s;
 393:     char tmpbuf[1024];
 394:     register char *tbptr = tmpbuf+5;
 395: 
 396:     for (end = dirname; *end; end++) ;  /* find the end */
 397:     if (nametype == MD_FILE) {      /* not to create last component? */
 398:     for (--end; end != dirname && *end != '/'; --end) ;
 399:     if (*end != '/')
 400:         return 0;           /* nothing to make */
 401:     *end = '\0';            /* isolate file name */
 402:     }
 403:     strcpy(tmpbuf,"mkdir");
 404: 
 405:     s = end;
 406:     for (;;) {
 407:     if (stat(dirname,&filestat) >= 0) {
 408:                     /* does this much exist? */
 409:         *s = '/';           /* mark this as existing */
 410:         break;
 411:     }
 412:     s = rindex(dirname,'/');    /* shorten name */
 413:     if (!s)             /* relative path! */
 414:         break;          /* hope they know what they are doing */
 415:     *s = '\0';          /* mark as not existing */
 416:     }
 417: 
 418:     for (s=dirname; s <= end; s++) {    /* this is grody but efficient */
 419:     if (!*s) {          /* something to make? */
 420:         sprintf(tbptr," %s",dirname);
 421:         tbptr += strlen(tbptr); /* make it, sort of */
 422:         *s = '/';           /* mark it made */
 423:     }
 424:     }
 425:     if (nametype == MD_DIR)     /* don't need final slash unless */
 426:     *end = '\0';            /*  a filename follows the dir name */
 427: 
 428:     return (tbptr==tmpbuf+5 ? 0 : doshell(sh,tmpbuf));
 429:                     /* exercise our faith */
 430: #else
 431:     sprintf(cmd_buf,"%s %s %d", filexp(DIRMAKER), dirname, nametype);
 432:     return doshell(sh,cmd_buf);
 433: #endif
 434: }
 435: 
 436: #ifdef SETENV
 437: static bool firstsetenv = TRUE;
 438: extern char **environ;
 439: 
 440: void
 441: setenv(nam,val)
 442: char *nam, *val;
 443: {
 444:     register int i=envix(nam);      /* where does it go? */
 445: 
 446:     if (!environ[i]) {          /* does not exist yet */
 447:     if (firstsetenv) {      /* need we copy environment? */
 448:         int j;
 449: #ifndef lint
 450:         char **tmpenv = (char**)    /* point our wand at memory */
 451:         safemalloc((MEM_SIZE) (i+2) * sizeof(char*));
 452: #else
 453:         char **tmpenv = Null(char **);
 454: #endif lint
 455: 
 456:         firstsetenv = FALSE;
 457:         for (j=0; j<i; j++)     /* copy environment */
 458:         tmpenv[j] = environ[j];
 459:         environ = tmpenv;       /* tell exec where it is now */
 460:     }
 461: #ifndef lint
 462:     else
 463:         environ = (char**) saferealloc((char*) environ,
 464:         (MEM_SIZE) (i+2) * sizeof(char*));
 465:                     /* just expand it a bit */
 466: #endif lint
 467:     environ[i+1] = Nullch;  /* make sure it's null terminated */
 468:     }
 469:     environ[i] = safemalloc((MEM_SIZE) strlen(nam) + strlen(val) + 2);
 470:                     /* this may or may not be in */
 471:                     /* the old environ structure */
 472:     sprintf(environ[i],"%s=%s",nam,val);/* all that work just for this */
 473: }
 474: 
 475: int
 476: envix(nam)
 477: char *nam;
 478: {
 479:     register int i, len = strlen(nam);
 480: 
 481:     for (i = 0; environ[i]; i++) {
 482:     if (strnEQ(environ[i],nam,len) && environ[i][len] == '=')
 483:         break;          /* strnEQ must come first to avoid */
 484:     }                   /* potential SEGV's */
 485:     return i;
 486: }
 487: #endif
 488: 
 489: void
 490: notincl(feature)
 491: char *feature;
 492: {
 493:     printf("\nNo room for feature \"%s\" on this machine.\n",feature) FLUSH;
 494: }
 495: 
 496: char *
 497: getval(nam,def)
 498: char *nam,*def;
 499: {
 500:     char *val;
 501: 
 502:     if ((val = getenv(nam)) == Nullch || !*val)
 503:     val = def;
 504:     return val;
 505: }
 506: 
 507: /* grow a static string to at least a certain length */
 508: 
 509: void
 510: growstr(strptr,curlen,newlen)
 511: char **strptr;
 512: int *curlen;
 513: int newlen;
 514: {
 515:     if (newlen > *curlen) {     /* need more room? */
 516:     if (*curlen)
 517:         *strptr = saferealloc(*strptr,(MEM_SIZE)newlen);
 518:     else
 519:         *strptr = safemalloc((MEM_SIZE)newlen);
 520:     *curlen = newlen;
 521:     }
 522: }
 523: 
 524: void
 525: setdef(buffer,dflt)
 526: char *buffer,*dflt;
 527: {
 528: #ifdef STRICTCR
 529:     if (*buffer == ' ')
 530: #else
 531:     if (*buffer == ' ' || *buffer == '\n')
 532: #endif
 533:     {
 534:     if (*dflt == '^' && isupper(dflt[1]))
 535:         *buffer = Ctl(dflt[1]);
 536:     else
 537:         *buffer = *dflt;
 538:     }
 539: }

Defined functions

cat defined in line 293; used 2 times
eaccess defined in line 208; used 1 times
envix defined in line 475; used 2 times
get_a_line defined in line 340; used 2 times
prexit defined in line 312; used 4 times
setenv defined in line 440; used 5 times
util_init defined in line 22; used 2 times

Defined variables

d defined in line 244; used 11 times
dd defined in line 244; used 6 times
dir defined in line 245; used 6 times
dirp defined in line 242; used 4 times
name defined in line 240; used 10 times
nomem defined in line 80; used 2 times
off defined in line 243; used 7 times

Defined macros

dot defined in line 237; used 1 times
dotdot defined in line 238; used 3 times
Last modified: 1986-03-21
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 2699
Valid CSS Valid XHTML 1.0 Strict