1*2805Swnj static char *sccsid = "@(#)files.c 4.1 (Berkeley) 81/02/28"; 2*2805Swnj /* UNIX DEPENDENT PROCEDURES */ 3*2805Swnj 4*2805Swnj 5*2805Swnj /* DEFAULT RULES FOR UNIX */ 6*2805Swnj 7*2805Swnj char *builtin[] = 8*2805Swnj { 9*2805Swnj #ifdef pwb 10*2805Swnj ".SUFFIXES : .L .out .o .c .f .e .r .y .yr .ye .l .s .z .x .t .h .cl", 11*2805Swnj #else 12*2805Swnj ".SUFFIXES : .out .o .c .f .e .r .y .yr .ye .l .s .cl .p", 13*2805Swnj #endif 14*2805Swnj "YACC=yacc", 15*2805Swnj "YACCR=yacc -r", 16*2805Swnj "YACCE=yacc -e", 17*2805Swnj "YFLAGS=", 18*2805Swnj "LEX=lex", 19*2805Swnj "LFLAGS=", 20*2805Swnj "CC=cc", 21*2805Swnj #ifdef vax 22*2805Swnj "AS=as", 23*2805Swnj #else 24*2805Swnj "AS=as -", 25*2805Swnj #endif 26*2805Swnj "PC=pc", 27*2805Swnj "PFLAGS=", 28*2805Swnj "CFLAGS=", 29*2805Swnj "RC=f77", 30*2805Swnj "RFLAGS=", 31*2805Swnj "EC=f77", 32*2805Swnj "EFLAGS=", 33*2805Swnj "FFLAGS=", 34*2805Swnj "LOADLIBES=", 35*2805Swnj #ifdef pwb 36*2805Swnj "SCOMP=scomp", 37*2805Swnj "SCFLAGS=", 38*2805Swnj "CMDICT=cmdict", 39*2805Swnj "CMFLAGS=", 40*2805Swnj #endif 41*2805Swnj 42*2805Swnj ".c.o :", 43*2805Swnj "\t$(CC) $(CFLAGS) -c $<", 44*2805Swnj 45*2805Swnj ".p.o :", 46*2805Swnj "\t$(PC) $(PFLAGS) -c $<", 47*2805Swnj 48*2805Swnj ".cl.o :", 49*2805Swnj "\tclass -c $<", 50*2805Swnj 51*2805Swnj ".e.o .r.o .f.o :", 52*2805Swnj "\t$(FC) $(RFLAGS) $(EFLAGS) $(FFLAGS) -c $<", 53*2805Swnj 54*2805Swnj ".s.o :", 55*2805Swnj "\t$(AS) -o $@ $<", 56*2805Swnj 57*2805Swnj ".y.o :", 58*2805Swnj "\t$(YACC) $(YFLAGS) $<", 59*2805Swnj "\t$(CC) $(CFLAGS) -c y.tab.c", 60*2805Swnj "\trm y.tab.c", 61*2805Swnj "\tmv y.tab.o $@", 62*2805Swnj 63*2805Swnj ".yr.o:", 64*2805Swnj "\t$(YACCR) $(YFLAGS) $<", 65*2805Swnj "\t$(RC) $(RFLAGS) -c y.tab.r", 66*2805Swnj "\trm y.tab.r", 67*2805Swnj "\tmv y.tab.o $@", 68*2805Swnj 69*2805Swnj ".ye.o :", 70*2805Swnj "\t$(YACCE) $(YFLAGS) $<", 71*2805Swnj "\t$(EC) $(RFLAGS) -c y.tab.e", 72*2805Swnj "\trm y.tab.e", 73*2805Swnj "\tmv y.tab.o $@", 74*2805Swnj 75*2805Swnj ".l.o :", 76*2805Swnj "\t$(LEX) $(LFLAGS) $<", 77*2805Swnj "\t$(CC) $(CFLAGS) -c lex.yy.c", 78*2805Swnj "\trm lex.yy.c", 79*2805Swnj "\tmv lex.yy.o $@", 80*2805Swnj 81*2805Swnj ".y.c :", 82*2805Swnj "\t$(YACC) $(YFLAGS) $<", 83*2805Swnj "\tmv y.tab.c $@", 84*2805Swnj 85*2805Swnj ".l.c :", 86*2805Swnj "\t$(LEX) $(LFLAGS) $<", 87*2805Swnj "\tmv lex.yy.c $@", 88*2805Swnj 89*2805Swnj ".yr.r:", 90*2805Swnj "\t$(YACCR) $(YFLAGS) $<", 91*2805Swnj "\tmv y.tab.r $@", 92*2805Swnj 93*2805Swnj ".ye.e :", 94*2805Swnj "\t$(YACCE) $(YFLAGS) $<", 95*2805Swnj "\tmv y.tab.e $@", 96*2805Swnj 97*2805Swnj #ifdef pwb 98*2805Swnj ".o.L .c.L .t.L:", 99*2805Swnj "\t$(SCOMP) $(SCFLAGS) $<", 100*2805Swnj 101*2805Swnj ".t.o:", 102*2805Swnj "\t$(SCOMP) $(SCFLAGS) -c $<", 103*2805Swnj 104*2805Swnj ".t.c:", 105*2805Swnj "\t$(SCOMP) $(SCFLAGS) -t $<", 106*2805Swnj 107*2805Swnj ".h.z .t.z:", 108*2805Swnj "\t$(CMDICT) $(CMFLAGS) $<", 109*2805Swnj 110*2805Swnj ".h.x .t.x:", 111*2805Swnj "\t$(CMDICT) $(CMFLAGS) -c $<", 112*2805Swnj #endif 113*2805Swnj 114*2805Swnj ".s.out .c.out .o.out :", 115*2805Swnj "\t$(CC) $(CFLAGS) $< $(LOADLIBES) -o $@", 116*2805Swnj 117*2805Swnj ".f.out .r.out .e.out :", 118*2805Swnj "\t$(FC) $(EFLAGS) $(RFLAGS) $(FFLAGS) $< $(LOADLIBES) -o $@", 119*2805Swnj "\t-rm $*.o", 120*2805Swnj 121*2805Swnj ".y.out :", 122*2805Swnj "\t$(YACC) $(YFLAGS) $<", 123*2805Swnj "\t$(CC) $(CFLAGS) y.tab.c $(LOADLIBES) -ly -o $@", 124*2805Swnj "\trm y.tab.c", 125*2805Swnj 126*2805Swnj ".l.out :", 127*2805Swnj "\t$(LEX) $(LFLAGS) $<", 128*2805Swnj "\t$(CC) $(CFLAGS) lex.yy.c $(LOADLIBES) -ll -o $@", 129*2805Swnj "\trm lex.yy.c", 130*2805Swnj 131*2805Swnj 0 }; 132*2805Swnj 133*2805Swnj #include "defs" 134*2805Swnj #include <sys/types.h> 135*2805Swnj 136*2805Swnj 137*2805Swnj TIMETYPE exists(filename) 138*2805Swnj char *filename; 139*2805Swnj { 140*2805Swnj #include <sys/stat.h> 141*2805Swnj struct stat buf; 142*2805Swnj register char *s; 143*2805Swnj TIMETYPE lookarch(); 144*2805Swnj 145*2805Swnj for(s = filename ; *s!='\0' && *s!='(' ; ++s) 146*2805Swnj ; 147*2805Swnj 148*2805Swnj if(*s == '(') 149*2805Swnj return(lookarch(filename)); 150*2805Swnj 151*2805Swnj if(stat(filename,&buf) < 0) 152*2805Swnj return(0); 153*2805Swnj else return(buf.st_mtime); 154*2805Swnj } 155*2805Swnj 156*2805Swnj 157*2805Swnj TIMETYPE prestime() 158*2805Swnj { 159*2805Swnj TIMETYPE t; 160*2805Swnj time(&t); 161*2805Swnj return(t); 162*2805Swnj } 163*2805Swnj 164*2805Swnj 165*2805Swnj 166*2805Swnj #include <sys/dir.h> 167*2805Swnj FSTATIC char n15[15]; 168*2805Swnj FSTATIC char *n15end = &n15[14]; 169*2805Swnj 170*2805Swnj 171*2805Swnj 172*2805Swnj struct depblock *srchdir(pat, mkchain, nextdbl) 173*2805Swnj register char *pat; /* pattern to be matched in directory */ 174*2805Swnj int mkchain; /* nonzero if results to be remembered */ 175*2805Swnj struct depblock *nextdbl; /* final value for chain */ 176*2805Swnj { 177*2805Swnj FILE * dirf; 178*2805Swnj register int i; 179*2805Swnj int nread, cldir; 180*2805Swnj char *dirname, *dirpref, *endir, *filepat, *p, temp[100]; 181*2805Swnj char fullname[100], *p1, *p2; 182*2805Swnj struct nameblock *q; 183*2805Swnj struct depblock *thisdbl; 184*2805Swnj struct opendir *od; 185*2805Swnj struct pattern *patp; 186*2805Swnj 187*2805Swnj struct direct entry[32]; 188*2805Swnj 189*2805Swnj 190*2805Swnj thisdbl = 0; 191*2805Swnj 192*2805Swnj if(mkchain == NO) 193*2805Swnj for(patp=firstpat ; patp ; patp = patp->nxtpattern) 194*2805Swnj if(! unequal(pat, patp->patval)) return(0); 195*2805Swnj 196*2805Swnj patp = ALLOC(pattern); 197*2805Swnj patp->nxtpattern = firstpat; 198*2805Swnj firstpat = patp; 199*2805Swnj patp->patval = copys(pat); 200*2805Swnj 201*2805Swnj endir = 0; 202*2805Swnj 203*2805Swnj for(p=pat; *p!='\0'; ++p) 204*2805Swnj if(*p=='/') endir = p; 205*2805Swnj 206*2805Swnj if(endir==0) 207*2805Swnj { 208*2805Swnj dirname = "."; 209*2805Swnj dirpref = ""; 210*2805Swnj filepat = pat; 211*2805Swnj } 212*2805Swnj else { 213*2805Swnj dirname = pat; 214*2805Swnj *endir = '\0'; 215*2805Swnj dirpref = concat(dirname, "/", temp); 216*2805Swnj filepat = endir+1; 217*2805Swnj } 218*2805Swnj 219*2805Swnj dirf = NULL; 220*2805Swnj cldir = NO; 221*2805Swnj 222*2805Swnj for(od = firstod; od; od = od->nxtopendir) 223*2805Swnj if(! unequal(dirname, od->dirn) ) 224*2805Swnj { 225*2805Swnj dirf = od->dirfc; 226*2805Swnj fseek(dirf, 0L, 0); /* start over at the beginning */ 227*2805Swnj break; 228*2805Swnj } 229*2805Swnj 230*2805Swnj if(dirf == NULL) 231*2805Swnj { 232*2805Swnj dirf = fopen(dirname, "r"); 233*2805Swnj if(nopdir >= MAXDIR) 234*2805Swnj cldir = YES; 235*2805Swnj else { 236*2805Swnj ++nopdir; 237*2805Swnj od = ALLOC(opendir); 238*2805Swnj od->nxtopendir = firstod; 239*2805Swnj firstod = od; 240*2805Swnj od->dirfc = dirf; 241*2805Swnj od->dirn = copys(dirname); 242*2805Swnj } 243*2805Swnj } 244*2805Swnj 245*2805Swnj if(dirf == NULL) 246*2805Swnj { 247*2805Swnj fprintf(stderr, "Directory %s: ", dirname); 248*2805Swnj fatal("Cannot open"); 249*2805Swnj } 250*2805Swnj 251*2805Swnj else do 252*2805Swnj { 253*2805Swnj nread = fread( (char *) &entry[0], sizeof(struct direct), 32, dirf) ; 254*2805Swnj for(i=0; i<nread; ++i) 255*2805Swnj if(entry[i].d_ino!= 0) 256*2805Swnj { 257*2805Swnj p1 = entry[i].d_name; 258*2805Swnj p2 = n15; 259*2805Swnj while( (p2<n15end) && 260*2805Swnj (*p2++ = *p1++)!='\0' ); 261*2805Swnj if( amatch(n15,filepat) ) 262*2805Swnj { 263*2805Swnj concat(dirpref,n15,fullname); 264*2805Swnj if( (q=srchname(fullname)) ==0) 265*2805Swnj q = makename(copys(fullname)); 266*2805Swnj if(mkchain) 267*2805Swnj { 268*2805Swnj thisdbl = ALLOC(depblock); 269*2805Swnj thisdbl->nxtdepblock = nextdbl; 270*2805Swnj thisdbl->depname = q; 271*2805Swnj nextdbl = thisdbl; 272*2805Swnj } 273*2805Swnj } 274*2805Swnj } 275*2805Swnj 276*2805Swnj } while(nread==32); 277*2805Swnj 278*2805Swnj if(endir != 0) *endir = '/'; 279*2805Swnj 280*2805Swnj if(cldir) 281*2805Swnj fclose(dirf); 282*2805Swnj return(thisdbl); 283*2805Swnj } 284*2805Swnj 285*2805Swnj /* stolen from glob through find */ 286*2805Swnj 287*2805Swnj static amatch(s, p) 288*2805Swnj char *s, *p; 289*2805Swnj { 290*2805Swnj register int cc, scc, k; 291*2805Swnj int c, lc; 292*2805Swnj 293*2805Swnj scc = *s; 294*2805Swnj lc = 077777; 295*2805Swnj switch (c = *p) { 296*2805Swnj 297*2805Swnj case '[': 298*2805Swnj k = 0; 299*2805Swnj while (cc = *++p) { 300*2805Swnj switch (cc) { 301*2805Swnj 302*2805Swnj case ']': 303*2805Swnj if (k) 304*2805Swnj return(amatch(++s, ++p)); 305*2805Swnj else 306*2805Swnj return(0); 307*2805Swnj 308*2805Swnj case '-': 309*2805Swnj k |= (lc <= scc) & (scc <= (cc=p[1]) ) ; 310*2805Swnj } 311*2805Swnj if (scc==(lc=cc)) k++; 312*2805Swnj } 313*2805Swnj return(0); 314*2805Swnj 315*2805Swnj case '?': 316*2805Swnj caseq: 317*2805Swnj if(scc) return(amatch(++s, ++p)); 318*2805Swnj return(0); 319*2805Swnj case '*': 320*2805Swnj return(umatch(s, ++p)); 321*2805Swnj case 0: 322*2805Swnj return(!scc); 323*2805Swnj } 324*2805Swnj if (c==scc) goto caseq; 325*2805Swnj return(0); 326*2805Swnj } 327*2805Swnj 328*2805Swnj static umatch(s, p) 329*2805Swnj char *s, *p; 330*2805Swnj { 331*2805Swnj if(*p==0) return(1); 332*2805Swnj while(*s) 333*2805Swnj if (amatch(s++,p)) return(1); 334*2805Swnj return(0); 335*2805Swnj } 336*2805Swnj 337*2805Swnj #ifdef METERFILE 338*2805Swnj #include <pwd.h> 339*2805Swnj int meteron = 0; /* default: metering off */ 340*2805Swnj 341*2805Swnj meter(file) 342*2805Swnj char *file; 343*2805Swnj { 344*2805Swnj TIMETYPE tvec; 345*2805Swnj char *p, *ctime(); 346*2805Swnj FILE * mout; 347*2805Swnj struct passwd *pwd, *getpwuid(); 348*2805Swnj 349*2805Swnj if(file==0 || meteron==0) return; 350*2805Swnj 351*2805Swnj pwd = getpwuid(getuid()); 352*2805Swnj 353*2805Swnj time(&tvec); 354*2805Swnj 355*2805Swnj if( (mout=fopen(file,"a")) != NULL ) 356*2805Swnj { 357*2805Swnj p = ctime(&tvec); 358*2805Swnj p[16] = '\0'; 359*2805Swnj fprintf(mout,"User %s, %s\n",pwd->pw_name,p+4); 360*2805Swnj fclose(mout); 361*2805Swnj } 362*2805Swnj } 363*2805Swnj #endif 364*2805Swnj 365*2805Swnj 366*2805Swnj /* look inside archives for notations a(b) and a((b)) 367*2805Swnj a(b) is file member b in archive a 368*2805Swnj a((b)) is entry point _b in object archive a 369*2805Swnj */ 370*2805Swnj 371*2805Swnj #ifdef ASCARCH 372*2805Swnj # include <ar.h> 373*2805Swnj #else 374*2805Swnj # include <ar.h> 375*2805Swnj #endif 376*2805Swnj #include <a.out.h> 377*2805Swnj 378*2805Swnj static long arflen; 379*2805Swnj static long arfdate; 380*2805Swnj static char arfname[16]; 381*2805Swnj FILE *arfd; 382*2805Swnj long int arpos, arlen; 383*2805Swnj 384*2805Swnj static struct exec objhead; 385*2805Swnj 386*2805Swnj static struct nlist objentry; 387*2805Swnj 388*2805Swnj 389*2805Swnj TIMETYPE lookarch(filename) 390*2805Swnj char *filename; 391*2805Swnj { 392*2805Swnj char *p, *q, *send, s[15]; 393*2805Swnj int i, nc, nsym, objarch; 394*2805Swnj 395*2805Swnj for(p = filename; *p!= '(' ; ++p) 396*2805Swnj ; 397*2805Swnj *p = '\0'; 398*2805Swnj openarch(filename); 399*2805Swnj *p++ = '('; 400*2805Swnj 401*2805Swnj if(*p == '(') 402*2805Swnj { 403*2805Swnj objarch = YES; 404*2805Swnj nc = 8; 405*2805Swnj ++p; 406*2805Swnj } 407*2805Swnj else 408*2805Swnj { 409*2805Swnj objarch = NO; 410*2805Swnj nc = 14; 411*2805Swnj } 412*2805Swnj send = s + nc; 413*2805Swnj 414*2805Swnj for( q = s ; q<send && *p!='\0' && *p!=')' ; *q++ = *p++ ) 415*2805Swnj ; 416*2805Swnj while(q < send) 417*2805Swnj *q++ = '\0'; 418*2805Swnj while(getarch()) 419*2805Swnj { 420*2805Swnj if(objarch) 421*2805Swnj { 422*2805Swnj getobj(); 423*2805Swnj nsym = objhead.a_syms / sizeof(objentry); 424*2805Swnj for(i = 0; i<nsym ; ++i) 425*2805Swnj { 426*2805Swnj fread( (char *) &objentry, sizeof(objentry),1,arfd); 427*2805Swnj if( (objentry.n_type & N_EXT) 428*2805Swnj && ((objentry.n_type & ~N_EXT) || objentry.n_value) 429*2805Swnj && eqstr(objentry.n_un.n_name,s,nc)) 430*2805Swnj { 431*2805Swnj clarch(); 432*2805Swnj return(arfdate); 433*2805Swnj } 434*2805Swnj } 435*2805Swnj } 436*2805Swnj 437*2805Swnj else if( eqstr(arfname, s, nc)) 438*2805Swnj { 439*2805Swnj clarch(); 440*2805Swnj return(arfdate); 441*2805Swnj } 442*2805Swnj } 443*2805Swnj 444*2805Swnj clarch(); 445*2805Swnj return( 0L); 446*2805Swnj } 447*2805Swnj 448*2805Swnj 449*2805Swnj clarch() 450*2805Swnj { 451*2805Swnj fclose( arfd ); 452*2805Swnj } 453*2805Swnj 454*2805Swnj 455*2805Swnj openarch(f) 456*2805Swnj register char *f; 457*2805Swnj { 458*2805Swnj #ifdef ASCARCH 459*2805Swnj char magic[SARMAG]; 460*2805Swnj #endif 461*2805Swnj int word; 462*2805Swnj #include <sys/stat.h> 463*2805Swnj struct stat buf; 464*2805Swnj 465*2805Swnj stat(f, &buf); 466*2805Swnj arlen = buf.st_size; 467*2805Swnj 468*2805Swnj arfd = fopen(f, "r"); 469*2805Swnj if(arfd == NULL) 470*2805Swnj fatal1("cannot open %s", f); 471*2805Swnj 472*2805Swnj fread( (char *) &word, sizeof(word), 1, arfd); 473*2805Swnj #ifdef ASCARCH 474*2805Swnj fseek(arfd, 0L, 0); 475*2805Swnj fread(magic, SARMAG, 1, arfd); 476*2805Swnj arpos = SARMAG; 477*2805Swnj if( ! eqstr(magic, ARMAG, SARMAG) ) 478*2805Swnj #else 479*2805Swnj arpos = sizeof(word); 480*2805Swnj if(word != ARMAG) 481*2805Swnj #endif 482*2805Swnj fatal1("%s is not an archive", f); 483*2805Swnj 484*2805Swnj arflen = 0; 485*2805Swnj } 486*2805Swnj 487*2805Swnj 488*2805Swnj 489*2805Swnj getarch() 490*2805Swnj { 491*2805Swnj struct ar_hdr arhead; 492*2805Swnj long atol(); 493*2805Swnj 494*2805Swnj arpos += (arflen + 1) & ~1L; /* round archived file length up to even */ 495*2805Swnj if(arpos >= arlen) 496*2805Swnj return(0); 497*2805Swnj fseek(arfd, arpos, 0); 498*2805Swnj 499*2805Swnj fread( (char *) &arhead, sizeof(arhead), 1, arfd); 500*2805Swnj arpos += sizeof(arhead); 501*2805Swnj #ifdef ASCARCH 502*2805Swnj arflen = atol(arhead.ar_size); 503*2805Swnj arfdate = atol(arhead.ar_date); 504*2805Swnj #else 505*2805Swnj arflen = arhead.ar_size; 506*2805Swnj arfdate = arhead.ar_date; 507*2805Swnj #endif 508*2805Swnj strncpy(arfname, arhead.ar_name, sizeof(arhead.ar_name)); 509*2805Swnj return(1); 510*2805Swnj } 511*2805Swnj 512*2805Swnj 513*2805Swnj getobj() 514*2805Swnj { 515*2805Swnj long int skip; 516*2805Swnj 517*2805Swnj fread( (char *) &objhead, sizeof(objhead), 1, arfd); 518*2805Swnj if (N_BADMAG(objhead)) 519*2805Swnj fatal1("%s is not an object module", arfname); 520*2805Swnj skip = objhead.a_text + objhead.a_data; 521*2805Swnj #ifdef vax 522*2805Swnj skip += objhead.a_trsize + objhead.a_drsize; 523*2805Swnj #else 524*2805Swnj if(! objhead.a_flag ) 525*2805Swnj skip *= 2; 526*2805Swnj #endif 527*2805Swnj fseek(arfd, skip, 1); 528*2805Swnj } 529*2805Swnj 530*2805Swnj 531*2805Swnj eqstr(a,b,n) 532*2805Swnj register char *a, *b; 533*2805Swnj int n; 534*2805Swnj { 535*2805Swnj register int i; 536*2805Swnj for(i = 0 ; i < n ; ++i) 537*2805Swnj if(*a++ != *b++) 538*2805Swnj return(NO); 539*2805Swnj return(YES); 540*2805Swnj } 541