|
|
1.1 ! root 1: #include <stdio.h> ! 2: #include <sys/types.h> ! 3: #include <sys/stat.h> ! 4: #include <sys/dir.h> ! 5: #include <sys/mtio.h> ! 6: #include <errno.h> ! 7: #include <signal.h> ! 8: ! 9: char *sprintf(); ! 10: char *strcat(); ! 11: daddr_t bsrch(); ! 12: #define TBLOCK 512 ! 13: #define NBLOCK 40 /* maximum blocksize */ ! 14: #define DBLOCK 20 /* default blocksize */ ! 15: #define NAMSIZ 100 ! 16: union hblock { ! 17: char dummy[TBLOCK]; ! 18: struct header { ! 19: char name[NAMSIZ]; ! 20: char mode[8]; ! 21: char uid[8]; ! 22: char gid[8]; ! 23: char size[12]; ! 24: char mtime[12]; ! 25: char chksum[8]; ! 26: char linkflag; ! 27: char linkname[NAMSIZ]; ! 28: } dbuf; ! 29: } dblock, tbuf[NBLOCK]; ! 30: ! 31: struct linkbuf { ! 32: ino_t inum; ! 33: dev_t devnum; ! 34: int count; ! 35: char pathname[NAMSIZ]; ! 36: struct linkbuf *nextp; ! 37: } *ihead; ! 38: ! 39: struct stat stbuf; ! 40: ! 41: int rflag, xflag, vflag, tflag, mt, cflag, mflag, fflag, oflag, pflag; ! 42: int term, chksum, wflag, recno, first, linkerrok, Lflag; ! 43: int freemem = 1; ! 44: int nblock = DBLOCK; ! 45: ! 46: daddr_t low; ! 47: daddr_t high; ! 48: ! 49: FILE *tfile; ! 50: char tname[] = "/tmp/tarXXXXXX"; ! 51: ! 52: ! 53: char *usefile; ! 54: char magtape[] = "/dev/rmt1"; ! 55: ! 56: char *malloc(); ! 57: ! 58: main(argc, argv) ! 59: int argc; ! 60: char *argv[]; ! 61: { ! 62: char *cp; ! 63: int onintr(), onquit(), onhup(), onterm(); ! 64: ! 65: if (argc < 2) ! 66: usage(); ! 67: ! 68: tfile = NULL; ! 69: usefile = magtape; ! 70: argv[argc] = 0; ! 71: argv++; ! 72: for (cp = *argv++; *cp; cp++) ! 73: switch(*cp) { ! 74: case 'f': ! 75: usefile = *argv++; ! 76: fflag++; ! 77: break; ! 78: case 'c': ! 79: cflag++; ! 80: rflag++; ! 81: break; ! 82: case 'o': ! 83: oflag++; ! 84: break; ! 85: case 'p': ! 86: pflag++; ! 87: break; ! 88: case 'u': ! 89: mktemp(tname); ! 90: if ((tfile = fopen(tname, "w")) == NULL) { ! 91: fprintf(stderr, "Tar: cannot create temporary file (%s)\n", tname); ! 92: done(1); ! 93: } ! 94: fprintf(tfile, "!!!!!/!/!/!/!/!/!/! 000\n"); ! 95: /* FALL THROUGH */ ! 96: case 'r': ! 97: rflag++; ! 98: break; ! 99: case 'v': ! 100: vflag++; ! 101: break; ! 102: case 'w': ! 103: wflag++; ! 104: break; ! 105: case 'x': ! 106: xflag++; ! 107: break; ! 108: case 't': ! 109: tflag++; ! 110: break; ! 111: case 'm': ! 112: mflag++; ! 113: break; ! 114: case '-': ! 115: break; ! 116: case '0': ! 117: case '1': ! 118: case '4': ! 119: case '5': ! 120: case '7': ! 121: case '8': ! 122: magtape[8] = *cp; ! 123: usefile = magtape; ! 124: break; ! 125: case 'b': ! 126: nblock = atoi(*argv++); ! 127: if (nblock > NBLOCK || nblock <= 0) { ! 128: fprintf(stderr, "Invalid blocksize. (Max %d)\n", NBLOCK); ! 129: done(1); ! 130: } ! 131: break; ! 132: case 'l': ! 133: linkerrok++; ! 134: break; ! 135: case 'L': ! 136: Lflag++; ! 137: break; ! 138: default: ! 139: fprintf(stderr, "tar: %c: unknown option\n", *cp); ! 140: usage(); ! 141: } ! 142: ! 143: if (rflag) { ! 144: if (cflag && tfile != NULL) { ! 145: usage(); ! 146: done(1); ! 147: } ! 148: if (signal(SIGINT, SIG_IGN) != SIG_IGN) ! 149: signal(SIGINT, onintr); ! 150: if (signal(SIGHUP, SIG_IGN) != SIG_IGN) ! 151: signal(SIGHUP, onhup); ! 152: if (signal(SIGQUIT, SIG_IGN) != SIG_IGN) ! 153: signal(SIGQUIT, onquit); ! 154: /* ! 155: if (signal(SIGTERM, SIG_IGN) != SIG_IGN) ! 156: signal(SIGTERM, onterm); ! 157: */ ! 158: if (strcmp(usefile, "-") == 0) { ! 159: if (cflag == 0) { ! 160: fprintf(stderr, "Can only create standard output archives\n"); ! 161: done(1); ! 162: } ! 163: mt = dup(1); ! 164: nblock = 1; ! 165: } ! 166: else if ((mt = open(usefile, 2)) < 0) { ! 167: if (cflag == 0 || (mt = creat(usefile, 0666)) < 0) { ! 168: fprintf(stderr, "tar: cannot open %s\n", usefile); ! 169: done(1); ! 170: } ! 171: } ! 172: dorep(argv); ! 173: } ! 174: else if (xflag) { ! 175: if (strcmp(usefile, "-") == 0) { ! 176: mt = dup(0); ! 177: nblock = 1; ! 178: } ! 179: else if ((mt = open(usefile, 0)) < 0) { ! 180: fprintf(stderr, "tar: cannot open %s\n", usefile); ! 181: done(1); ! 182: } ! 183: doxtract(argv); ! 184: } ! 185: else if (tflag) { ! 186: if (strcmp(usefile, "-") == 0) { ! 187: mt = dup(0); ! 188: nblock = 1; ! 189: } ! 190: else if ((mt = open(usefile, 0)) < 0) { ! 191: fprintf(stderr, "tar: cannot open %s\n", usefile); ! 192: done(1); ! 193: } ! 194: dotable(); ! 195: } ! 196: else ! 197: usage(); ! 198: done(0); ! 199: } ! 200: ! 201: usage() ! 202: { ! 203: fprintf(stderr, "tar: usage tar -{txru}[cvfblLm] [tapefile] [blocksize] file1 file2...\n"); ! 204: done(1); ! 205: } ! 206: ! 207: dorep(argv) ! 208: char *argv[]; ! 209: { ! 210: register char *cp, *cp2; ! 211: char wdir[60]; ! 212: ! 213: if (!cflag) { ! 214: getdir(); ! 215: do { ! 216: passtape(); ! 217: if (term) ! 218: done(0); ! 219: getdir(); ! 220: } while (!endtape()); ! 221: if (tfile != NULL) { ! 222: char buf[200]; ! 223: ! 224: sprintf(buf, "sort +0 -1 +1nr %s -o %s; awk '$1 != prev {print; prev=$1}' %s >%sX; mv %sX %s", ! 225: tname, tname, tname, tname, tname, tname); ! 226: fflush(tfile); ! 227: system(buf); ! 228: freopen(tname, "r", tfile); ! 229: fstat(fileno(tfile), &stbuf); ! 230: high = stbuf.st_size; ! 231: } ! 232: } ! 233: ! 234: getwdir(wdir); ! 235: while (*argv && ! term) { ! 236: cp2 = *argv; ! 237: if (!strcmp(cp2, "-C") && argv[1]) { ! 238: argv++; ! 239: if (chdir(*argv) < 0) ! 240: perror(*argv); ! 241: else ! 242: getwdir(wdir); ! 243: argv++; ! 244: continue; ! 245: } ! 246: for (cp = *argv; *cp; cp++) ! 247: if (*cp == '/') ! 248: cp2 = cp; ! 249: if (cp2 != *argv) { ! 250: *cp2 = '\0'; ! 251: chdir(*argv); ! 252: *cp2 = '/'; ! 253: cp2++; ! 254: } ! 255: putfile(*argv++, cp2); ! 256: chdir(wdir); ! 257: } ! 258: putempty(); ! 259: putempty(); ! 260: flushtape(); ! 261: if (linkerrok == 1) ! 262: for (; ihead != NULL; ihead = ihead->nextp) ! 263: if (ihead->count != 0) ! 264: fprintf(stderr, "Missing links to %s\n", ihead->pathname); ! 265: } ! 266: ! 267: endtape() ! 268: { ! 269: if (dblock.dbuf.name[0] == '\0') { ! 270: backtape(); ! 271: return(1); ! 272: } ! 273: else ! 274: return(0); ! 275: } ! 276: ! 277: getdir() ! 278: { ! 279: register struct stat *sp; ! 280: int i; ! 281: ! 282: readtape( (char *) &dblock); ! 283: if (dblock.dbuf.name[0] == '\0') ! 284: return; ! 285: sp = &stbuf; ! 286: sscanf(dblock.dbuf.mode, "%o", &i); ! 287: sp->st_mode = i; ! 288: sscanf(dblock.dbuf.uid, "%o", &i); ! 289: sp->st_uid = i; ! 290: sscanf(dblock.dbuf.gid, "%o", &i); ! 291: sp->st_gid = i; ! 292: sscanf(dblock.dbuf.size, "%lo", &sp->st_size); ! 293: sscanf(dblock.dbuf.mtime, "%lo", &sp->st_mtime); ! 294: sscanf(dblock.dbuf.chksum, "%o", &chksum); ! 295: if (chksum != checksum()) { ! 296: fprintf(stderr, "directory checksum error\n"); ! 297: done(2); ! 298: } ! 299: if(xflag){ ! 300: fixname(dblock.dbuf.name); ! 301: fixname(dblock.dbuf.linkname); ! 302: } ! 303: if (tfile != NULL) ! 304: fprintf(tfile, "%s %s\n", dblock.dbuf.name, dblock.dbuf.mtime); ! 305: } ! 306: ! 307: passtape() ! 308: { ! 309: long blocks; ! 310: char buf[TBLOCK]; ! 311: ! 312: if (dblock.dbuf.linkflag == '1' || dblock.dbuf.linkflag == 's') ! 313: return; ! 314: blocks = stbuf.st_size; ! 315: blocks += TBLOCK-1; ! 316: blocks /= TBLOCK; ! 317: ! 318: while (blocks-- > 0) ! 319: readtape(buf); ! 320: } ! 321: ! 322: putfile(longname, shortname) ! 323: char *longname; ! 324: char *shortname; ! 325: { ! 326: int infile; ! 327: long blocks; ! 328: char buf[TBLOCK]; ! 329: register char *cp, *cp2; ! 330: struct direct dbuf; ! 331: int i, j; ! 332: ! 333: if (Lflag && lstat (shortname, &stbuf) == 0 && ! 334: (stbuf.st_mode & S_IFMT) == S_IFLNK) { ! 335: char lname[NAMSIZ+1]; ! 336: int len = readlink (shortname, lname, NAMSIZ+1); ! 337: if (len < 0) { ! 338: perror (longname); ! 339: return; ! 340: } else if (len > NAMSIZ) { ! 341: fprintf (stderr, ! 342: "tar: %s symlink name too long, ignored\n", longname); ! 343: return; ! 344: } ! 345: lname[len] = '\0'; ! 346: ! 347: tomodes(&stbuf); ! 348: ! 349: cp2 = longname; ! 350: for (cp = dblock.dbuf.name, i=0; ! 351: (*cp++ = *cp2++) && i < NAMSIZ; i++); ! 352: if (i >= NAMSIZ) { ! 353: fprintf(stderr, "%s: file name too long\n", longname); ! 354: return; ! 355: } ! 356: strcpy(dblock.dbuf.linkname, lname); ! 357: dblock.dbuf.linkflag = 's'; ! 358: sprintf(dblock.dbuf.chksum, "%6o", checksum()); ! 359: writetape( (char *) &dblock); ! 360: if (vflag) { ! 361: fprintf(stderr, "a %s ", longname); ! 362: fprintf(stderr, "symlink to %s\n", lname); ! 363: } ! 364: return; ! 365: } ! 366: ! 367: infile = open(shortname, 0); ! 368: if (infile < 0) { ! 369: fprintf(stderr, "tar: %s: cannot open file\n", longname); ! 370: return; ! 371: } ! 372: ! 373: fstat(infile, &stbuf); ! 374: ! 375: if (tfile != NULL && checkupdate(longname) == 0) { ! 376: close(infile); ! 377: return; ! 378: } ! 379: if (checkw('r', longname) == 0) { ! 380: close(infile); ! 381: return; ! 382: } ! 383: ! 384: if ((stbuf.st_mode & S_IFMT) == S_IFDIR) { ! 385: for (i = 0, cp = buf; *cp++ = longname[i++];); ! 386: *--cp = '/'; ! 387: *++cp = 0 ; ! 388: i = 0; ! 389: if (!oflag) { ! 390: if( (cp - buf) >= NAMSIZ) { ! 391: fprintf(stderr, "%s: file name too long\n", longname); ! 392: close(infile); ! 393: return; ! 394: } ! 395: stbuf.st_size = 0; ! 396: tomodes(&stbuf); ! 397: strcpy(dblock.dbuf.name,buf); ! 398: sprintf(dblock.dbuf.chksum, "%6o", checksum()); ! 399: writetape( (char *) &dblock); ! 400: } ! 401: chdir(shortname); ! 402: while (read(infile, (char *)&dbuf, sizeof(dbuf)) > 0 && !term) { ! 403: if (dbuf.d_ino == 0) { ! 404: i++; ! 405: continue; ! 406: } ! 407: if (strcmp(".", dbuf.d_name) == 0 || strcmp("..", dbuf.d_name) == 0) { ! 408: i++; ! 409: continue; ! 410: } ! 411: cp2 = cp; ! 412: for (j=0; j < DIRSIZ; j++) ! 413: *cp2++ = dbuf.d_name[j]; ! 414: *cp2 = '\0'; ! 415: close(infile); ! 416: putfile(buf, cp); ! 417: infile = open(".", 0); ! 418: i++; ! 419: lseek(infile, (long) (sizeof(dbuf) * i), 0); ! 420: } ! 421: close(infile); ! 422: chdir(".."); ! 423: return; ! 424: } ! 425: if ((stbuf.st_mode & S_IFMT) != S_IFREG) { ! 426: fprintf(stderr, "tar: %s is not a file. Not dumped\n", longname); ! 427: close(infile); ! 428: return; ! 429: } ! 430: ! 431: tomodes(&stbuf); ! 432: ! 433: cp2 = longname; ! 434: for (cp = dblock.dbuf.name, i=0; (*cp++ = *cp2++) && i < NAMSIZ; i++); ! 435: if (i >= NAMSIZ) { ! 436: fprintf(stderr, "%s: file name too long\n", longname); ! 437: close(infile); ! 438: return; ! 439: } ! 440: ! 441: if (stbuf.st_nlink > 1) { ! 442: struct linkbuf *lp; ! 443: int found = 0; ! 444: ! 445: for (lp = ihead; lp != NULL; lp = lp->nextp) { ! 446: if (lp->inum == stbuf.st_ino && lp->devnum == stbuf.st_dev) { ! 447: found++; ! 448: break; ! 449: } ! 450: } ! 451: if (found) { ! 452: strcpy(dblock.dbuf.linkname, lp->pathname); ! 453: dblock.dbuf.linkflag = '1'; ! 454: sprintf(dblock.dbuf.chksum, "%6o", checksum()); ! 455: writetape( (char *) &dblock); ! 456: if (vflag) { ! 457: fprintf(stderr, "a %s ", longname); ! 458: fprintf(stderr, "link to %s\n", lp->pathname); ! 459: } ! 460: lp->count--; ! 461: close(infile); ! 462: return; ! 463: } ! 464: else { ! 465: lp = (struct linkbuf *) malloc(sizeof(*lp)); ! 466: if (lp == NULL) { ! 467: if (freemem) { ! 468: fprintf(stderr, "Out of memory. Link information lost\n"); ! 469: freemem = 0; ! 470: } ! 471: } ! 472: else { ! 473: lp->nextp = ihead; ! 474: ihead = lp; ! 475: lp->inum = stbuf.st_ino; ! 476: lp->devnum = stbuf.st_dev; ! 477: lp->count = stbuf.st_nlink - 1; ! 478: strcpy(lp->pathname, longname); ! 479: } ! 480: } ! 481: } ! 482: ! 483: blocks = (stbuf.st_size + (TBLOCK-1)) / TBLOCK; ! 484: if (vflag) { ! 485: fprintf(stderr, "a %s ", longname); ! 486: fprintf(stderr, "%ld blocks\n", blocks); ! 487: } ! 488: sprintf(dblock.dbuf.chksum, "%6o", checksum()); ! 489: writetape( (char *) &dblock); ! 490: ! 491: while ((i = read(infile, buf, TBLOCK)) > 0 && blocks > 0) { ! 492: writetape(buf); ! 493: blocks--; ! 494: } ! 495: close(infile); ! 496: if (blocks != 0 || i != 0) ! 497: fprintf(stderr, "%s: file changed size\n", longname); ! 498: while (blocks-- > 0) ! 499: putempty(); ! 500: } ! 501: ! 502: ! 503: ! 504: doxtract(argv) ! 505: char *argv[]; ! 506: { ! 507: long blocks, bytes; ! 508: char buf[TBLOCK]; ! 509: char **cp; ! 510: int ofile; ! 511: ! 512: for (;;) { ! 513: getdir(); ! 514: if (endtape()) ! 515: break; ! 516: ! 517: if (*argv == 0) ! 518: goto gotit; ! 519: ! 520: for (cp = argv; *cp; cp++) ! 521: if (prefix(*cp, dblock.dbuf.name)) ! 522: goto gotit; ! 523: passtape(); ! 524: continue; ! 525: ! 526: gotit: ! 527: if (checkw('x', dblock.dbuf.name) == 0) { ! 528: passtape(); ! 529: continue; ! 530: } ! 531: ! 532: if(checkdir(dblock.dbuf.name)) ! 533: continue; ! 534: ! 535: if (dblock.dbuf.linkflag == '1') { ! 536: unlink(dblock.dbuf.name); ! 537: if (link(dblock.dbuf.linkname, dblock.dbuf.name) < 0) { ! 538: fprintf(stderr, "%s: cannot link\n", dblock.dbuf.name); ! 539: continue; ! 540: } ! 541: if (vflag) ! 542: fprintf(stderr, "%s linked to %s\n", ! 543: dblock.dbuf.name, dblock.dbuf.linkname); ! 544: continue; ! 545: } ! 546: if (dblock.dbuf.linkflag == 's') { ! 547: unlink(dblock.dbuf.name); ! 548: if (symlink(dblock.dbuf.linkname, dblock.dbuf.name) < 0) { ! 549: fprintf(stderr, "%s: cannot symlink\n", dblock.dbuf.name); ! 550: continue; ! 551: } ! 552: if (vflag) ! 553: fprintf(stderr, "%s -> %s\n", ! 554: dblock.dbuf.name, dblock.dbuf.linkname); ! 555: continue; ! 556: } ! 557: if ((ofile = creat(dblock.dbuf.name, stbuf.st_mode & 07777)) < 0) { ! 558: fprintf(stderr, "tar: %s - cannot create\n", dblock.dbuf.name); ! 559: passtape(); ! 560: continue; ! 561: } ! 562: chown(dblock.dbuf.name, stbuf.st_uid, stbuf.st_gid); ! 563: ! 564: blocks = ((bytes = stbuf.st_size) + TBLOCK-1)/TBLOCK; ! 565: if (vflag) ! 566: fprintf(stderr, "x %s, %ld bytes, %ld tape blocks\n", ! 567: dblock.dbuf.name, bytes, blocks); ! 568: while (blocks-- > 0) { ! 569: readtape(buf); ! 570: if (bytes > TBLOCK) { ! 571: if (write(ofile, buf, TBLOCK) < 0) { ! 572: fprintf(stderr, "tar: %s: HELP - extract write error\n", dblock.dbuf.name); ! 573: done(2); ! 574: } ! 575: } else ! 576: if (write(ofile, buf, (int) bytes) < 0) { ! 577: fprintf(stderr, "tar: %s: HELP - extract write error\n", dblock.dbuf.name); ! 578: done(2); ! 579: } ! 580: bytes -= TBLOCK; ! 581: } ! 582: close(ofile); ! 583: if (mflag == 0) { ! 584: time_t timep[2]; ! 585: ! 586: timep[0] = time(NULL); ! 587: timep[1] = stbuf.st_mtime; ! 588: utime(dblock.dbuf.name, timep); ! 589: } ! 590: if (pflag) ! 591: chmod(dblock.dbuf.name, stbuf.st_mode & 07777); ! 592: } ! 593: } ! 594: ! 595: dotable() ! 596: { ! 597: for (;;) { ! 598: getdir(); ! 599: if (endtape()) ! 600: break; ! 601: if (vflag) ! 602: longt(&stbuf); ! 603: printf("%s", dblock.dbuf.name); ! 604: if (dblock.dbuf.linkflag == '1') ! 605: printf(" linked to %s", dblock.dbuf.linkname); ! 606: if (dblock.dbuf.linkflag == 's') ! 607: printf(" -> %s", dblock.dbuf.linkname); ! 608: printf("\n"); ! 609: passtape(); ! 610: } ! 611: } ! 612: ! 613: putempty() ! 614: { ! 615: char buf[TBLOCK]; ! 616: char *cp; ! 617: ! 618: for (cp = buf; cp < &buf[TBLOCK]; ) ! 619: *cp++ = '\0'; ! 620: writetape(buf); ! 621: } ! 622: ! 623: longt(st) ! 624: register struct stat *st; ! 625: { ! 626: register char *cp; ! 627: char *ctime(); ! 628: ! 629: pmode(st); ! 630: printf("%3d/%1d", st->st_uid, st->st_gid); ! 631: printf("%7D", st->st_size); ! 632: cp = ctime(&st->st_mtime); ! 633: printf(" %-12.12s %-4.4s ", cp+4, cp+20); ! 634: } ! 635: ! 636: #define SUID 04000 ! 637: #define SGID 02000 ! 638: #define ROWN 0400 ! 639: #define WOWN 0200 ! 640: #define XOWN 0100 ! 641: #define RGRP 040 ! 642: #define WGRP 020 ! 643: #define XGRP 010 ! 644: #define ROTH 04 ! 645: #define WOTH 02 ! 646: #define XOTH 01 ! 647: #define STXT 01000 ! 648: int m1[] = { 1, ROWN, 'r', '-' }; ! 649: int m2[] = { 1, WOWN, 'w', '-' }; ! 650: int m3[] = { 2, SUID, 's', XOWN, 'x', '-' }; ! 651: int m4[] = { 1, RGRP, 'r', '-' }; ! 652: int m5[] = { 1, WGRP, 'w', '-' }; ! 653: int m6[] = { 2, SGID, 's', XGRP, 'x', '-' }; ! 654: int m7[] = { 1, ROTH, 'r', '-' }; ! 655: int m8[] = { 1, WOTH, 'w', '-' }; ! 656: int m9[] = { 2, STXT, 't', XOTH, 'x', '-' }; ! 657: ! 658: int *m[] = { m1, m2, m3, m4, m5, m6, m7, m8, m9}; ! 659: ! 660: pmode(st) ! 661: register struct stat *st; ! 662: { ! 663: register int **mp; ! 664: ! 665: for (mp = &m[0]; mp < &m[9];) ! 666: select(*mp++, st); ! 667: } ! 668: ! 669: select(pairp, st) ! 670: int *pairp; ! 671: struct stat *st; ! 672: { ! 673: register int n, *ap; ! 674: ! 675: ap = pairp; ! 676: n = *ap++; ! 677: while (--n>=0 && (st->st_mode&*ap++)==0) ! 678: ap++; ! 679: printf("%c", *ap); ! 680: } ! 681: ! 682: checkdir(name) ! 683: register char *name; ! 684: { ! 685: register char *cp; ! 686: int i; ! 687: for (cp = name; *cp; cp++) { ! 688: if (*cp == '/') { ! 689: *cp = '\0'; ! 690: if (access(name, 01) < 0) { ! 691: register int pid, rp; ! 692: ! 693: if ((pid = fork()) == 0) { ! 694: execl("/bin/mkdir", "mkdir", name, 0); ! 695: execl("/usr/bin/mkdir", "mkdir", name, 0); ! 696: fprintf(stderr, "tar: cannot find mkdir!\n"); ! 697: done(0); ! 698: } ! 699: while ((rp = wait(&i)) >= 0 && rp != pid) ! 700: ; ! 701: chown(name, stbuf.st_uid, stbuf.st_gid); ! 702: } ! 703: *cp = '/'; ! 704: } ! 705: } ! 706: return(cp[-1]=='/'); ! 707: } ! 708: ! 709: onintr() ! 710: { ! 711: signal(SIGINT, SIG_IGN); ! 712: term++; ! 713: } ! 714: ! 715: onquit() ! 716: { ! 717: signal(SIGQUIT, SIG_IGN); ! 718: term++; ! 719: } ! 720: ! 721: onhup() ! 722: { ! 723: signal(SIGHUP, SIG_IGN); ! 724: term++; ! 725: } ! 726: ! 727: onterm() ! 728: { ! 729: signal(SIGTERM, SIG_IGN); ! 730: term++; ! 731: } ! 732: ! 733: tomodes(sp) ! 734: register struct stat *sp; ! 735: { ! 736: register char *cp; ! 737: ! 738: for (cp = dblock.dummy; cp < &dblock.dummy[TBLOCK]; cp++) ! 739: *cp = '\0'; ! 740: sprintf(dblock.dbuf.mode, "%6o ", sp->st_mode & 07777); ! 741: sprintf(dblock.dbuf.uid, "%6o ", sp->st_uid); ! 742: sprintf(dblock.dbuf.gid, "%6o ", sp->st_gid); ! 743: sprintf(dblock.dbuf.size, "%11lo ", sp->st_size); ! 744: sprintf(dblock.dbuf.mtime, "%11lo ", sp->st_mtime); ! 745: } ! 746: ! 747: checksum() ! 748: { ! 749: register i; ! 750: register char *cp; ! 751: ! 752: for (cp = dblock.dbuf.chksum; cp < &dblock.dbuf.chksum[sizeof(dblock.dbuf.chksum)]; cp++) ! 753: *cp = ' '; ! 754: i = 0; ! 755: for (cp = dblock.dummy; cp < &dblock.dummy[TBLOCK]; cp++) ! 756: i += *cp; ! 757: return(i); ! 758: } ! 759: ! 760: checkw(c, name) ! 761: char *name; ! 762: { ! 763: if (wflag) { ! 764: printf("%c ", c); ! 765: if (vflag) ! 766: longt(&stbuf); ! 767: printf("%s: ", name); ! 768: if (response() == 'y'){ ! 769: return(1); ! 770: } ! 771: return(0); ! 772: } ! 773: return(1); ! 774: } ! 775: ! 776: response() ! 777: { ! 778: char c; ! 779: ! 780: c = getchar(); ! 781: if (c != '\n') ! 782: while (getchar() != '\n'); ! 783: else c = 'n'; ! 784: return(c); ! 785: } ! 786: ! 787: checkupdate(arg) ! 788: char *arg; ! 789: { ! 790: char name[100]; ! 791: long mtime; ! 792: daddr_t seekp; ! 793: daddr_t lookup(); ! 794: ! 795: rewind(tfile); ! 796: for (;;) { ! 797: if ((seekp = lookup(arg)) < 0) ! 798: return(1); ! 799: fseek(tfile, seekp, 0); ! 800: fscanf(tfile, "%s %lo", name, &mtime); ! 801: if (stbuf.st_mtime > mtime) ! 802: return(1); ! 803: else ! 804: return(0); ! 805: } ! 806: } ! 807: ! 808: done(n) ! 809: { ! 810: unlink(tname); ! 811: exit(n); ! 812: } ! 813: ! 814: prefix(s1, s2) ! 815: register char *s1, *s2; ! 816: { ! 817: while (*s1) ! 818: if (*s1++ != *s2++) ! 819: return(0); ! 820: if (*s2) ! 821: return(*s2 == '/'); ! 822: return(1); ! 823: } ! 824: ! 825: getwdir(s) ! 826: char *s; ! 827: { ! 828: int i; ! 829: int pipdes[2]; ! 830: ! 831: pipe(pipdes); ! 832: if ((i = fork()) == 0) { ! 833: close(1); ! 834: dup(pipdes[1]); ! 835: execl("/bin/pwd", "pwd", 0); ! 836: execl("/usr/bin/pwd", "pwd", 0); ! 837: fprintf(stderr, "pwd failed!\n"); ! 838: printf("/\n"); ! 839: exit(1); ! 840: } ! 841: while (wait((int *)NULL) != -1) ! 842: ; ! 843: read(pipdes[0], s, 50); ! 844: while(*s != '\n') ! 845: s++; ! 846: *s = '\0'; ! 847: close(pipdes[0]); ! 848: close(pipdes[1]); ! 849: } ! 850: ! 851: #define N 200 ! 852: int njab; ! 853: daddr_t ! 854: lookup(s) ! 855: char *s; ! 856: { ! 857: register i; ! 858: daddr_t a; ! 859: ! 860: for(i=0; s[i]; i++) ! 861: if(s[i] == ' ') ! 862: break; ! 863: a = bsrch(s, i, low, high); ! 864: return(a); ! 865: } ! 866: ! 867: daddr_t ! 868: bsrch(s, n, l, h) ! 869: daddr_t l, h; ! 870: char *s; ! 871: { ! 872: register i, j; ! 873: char b[N]; ! 874: daddr_t m, m1; ! 875: ! 876: njab = 0; ! 877: ! 878: loop: ! 879: if(l >= h) ! 880: return(-1L); ! 881: m = l + (h-l)/2 - N/2; ! 882: if(m < l) ! 883: m = l; ! 884: fseek(tfile, m, 0); ! 885: fread(b, 1, N, tfile); ! 886: njab++; ! 887: for(i=0; i<N; i++) { ! 888: if(b[i] == '\n') ! 889: break; ! 890: m++; ! 891: } ! 892: if(m >= h) ! 893: return(-1L); ! 894: m1 = m; ! 895: j = i; ! 896: for(i++; i<N; i++) { ! 897: m1++; ! 898: if(b[i] == '\n') ! 899: break; ! 900: } ! 901: i = cmp(b+j, s, n); ! 902: if(i < 0) { ! 903: h = m; ! 904: goto loop; ! 905: } ! 906: if(i > 0) { ! 907: l = m1; ! 908: goto loop; ! 909: } ! 910: return(m); ! 911: } ! 912: ! 913: cmp(b, s, n) ! 914: char *b, *s; ! 915: { ! 916: register i; ! 917: ! 918: if(b[0] != '\n') ! 919: exit(2); ! 920: for(i=0; i<n; i++) { ! 921: if(b[i+1] > s[i]) ! 922: return(-1); ! 923: if(b[i+1] < s[i]) ! 924: return(1); ! 925: } ! 926: return(b[i+1] == ' '? 0 : -1); ! 927: } ! 928: ! 929: readtape(buffer) ! 930: char *buffer; ! 931: { ! 932: register int i; ! 933: ! 934: if (recno >= nblock || first == 0) { ! 935: if ((i = read(mt, tbuf, TBLOCK*nblock)) < 0) { ! 936: fprintf(stderr, "Tar: tape read error\n"); ! 937: done(3); ! 938: } ! 939: if (first == 0) { ! 940: if ((i % TBLOCK) != 0) { ! 941: fprintf(stderr, "Tar: tape blocksize error\n"); ! 942: done(3); ! 943: } ! 944: i /= TBLOCK; ! 945: if (i != nblock) { ! 946: fprintf(stderr, "Tar: blocksize = %d\n", i); ! 947: nblock = i; ! 948: } ! 949: } ! 950: recno = 0; ! 951: } ! 952: first = 1; ! 953: copy(buffer, &tbuf[recno++]); ! 954: return(TBLOCK); ! 955: } ! 956: ! 957: writetape(buffer) ! 958: char *buffer; ! 959: { ! 960: first = 1; ! 961: if (recno >= nblock) { ! 962: if (write(mt, tbuf, TBLOCK*nblock) < 0) { ! 963: fprintf(stderr, "Tar: tape write error\n"); ! 964: done(2); ! 965: } ! 966: recno = 0; ! 967: } ! 968: copy(&tbuf[recno++], buffer); ! 969: if (recno >= nblock) { ! 970: if (write(mt, tbuf, TBLOCK*nblock) < 0) { ! 971: fprintf(stderr, "Tar: tape write error\n"); ! 972: done(2); ! 973: } ! 974: recno = 0; ! 975: } ! 976: return(TBLOCK); ! 977: } ! 978: ! 979: /* ! 980: * backup over last `tape' block ! 981: * hack: if it's a raw magtape, do the ioctl ! 982: */ ! 983: backtape() ! 984: { ! 985: static int isatape = 1; ! 986: static struct mtop mtop = {MTBSR, 1}; ! 987: ! 988: lseek(mt, (long) -TBLOCK*nblock, 1); ! 989: recno--; ! 990: if (isatape == 1 && ioctl(mt, MTIOCTOP, &mtop) < 0) { ! 991: if (errno != ENOTTY) { ! 992: perror("tar: tape backspace error"); ! 993: done(4); ! 994: } ! 995: isatape = 0; ! 996: return; ! 997: } ! 998: } ! 999: ! 1000: flushtape() ! 1001: { ! 1002: write(mt, tbuf, TBLOCK*nblock); ! 1003: } ! 1004: ! 1005: copy(to, from) ! 1006: register char *to, *from; ! 1007: { ! 1008: register i; ! 1009: ! 1010: i = TBLOCK; ! 1011: do { ! 1012: *to++ = *from++; ! 1013: } while (--i); ! 1014: } ! 1015: #define MAXFILENAME 14 ! 1016: FILE *longnamefd; ! 1017: ! 1018: affix(n,ptr) ! 1019: int n; ! 1020: char *ptr; ! 1021: { ! 1022: int i=0,m; ! 1023: char ext[5]; ! 1024: ! 1025: while(1) { ! 1026: if((m=n%52)<26) ext[i++] = m + 'a'; ! 1027: else ext[i++] = m + 'A' - 26; ! 1028: if(n < 52)break; ! 1029: n = n/52 - 1; /* so we have Z,aa not Z,ba */ ! 1030: } ! 1031: ! 1032: while(--i >= 0)*ptr++ = ext[i]; ! 1033: *ptr = '\0'; ! 1034: } ! 1035: ! 1036: #define MAXOVER 1000 ! 1037: struct { ! 1038: char *longname, ! 1039: *shortname; ! 1040: } pairs[MAXOVER]; ! 1041: int npairs = 0; /* no. of tabulated pairs */ ! 1042: ! 1043: int ntoolong = 0; /* no. of overlong pathnames */ ! 1044: ! 1045: char * ! 1046: findname(key) ! 1047: char *key; ! 1048: { ! 1049: int i, nprevious = 0, nprefix; ! 1050: char *longptr, *shortptr, *malloc(), *endbit, *strrchr(); ! 1051: ! 1052: endbit = strrchr(key,'/'); ! 1053: if(endbit == 0)endbit = key; ! 1054: else endbit++; ! 1055: nprefix = endbit - key; ! 1056: ! 1057: for(i=0;i<npairs;i++){ ! 1058: if(strcmp(key,pairs[i].longname) == 0) ! 1059: return(pairs[i].shortname); ! 1060: if(strncmp(key,pairs[i].longname,nprefix+MAXFILENAME-4) == 0) ! 1061: nprevious++; ! 1062: } ! 1063: longptr = pairs[npairs].longname = malloc(strlen(key)+1); ! 1064: shortptr = pairs[npairs].shortname = malloc(MAXFILENAME+1); ! 1065: strcpy(longptr,key); ! 1066: strncpy(shortptr,endbit,MAXFILENAME-4); ! 1067: sprintf(shortptr+MAXFILENAME-4,".."); ! 1068: affix(nprevious,shortptr+MAXFILENAME-2); ! 1069: npairs++; ! 1070: return(shortptr); ! 1071: } ! 1072: ! 1073: fixname(original) ! 1074: char *original; ! 1075: { ! 1076: int length; ! 1077: char newname[100]; ! 1078: register char *inend, *outptr=newname, *instart=original, ! 1079: *outstart; ! 1080: int changed = 0; ! 1081: ! 1082: while(1){ ! 1083: if(*instart == '\0')break; ! 1084: if(*instart == '/')*outptr++ = *instart++; ! 1085: outstart = outptr; ! 1086: for(inend=instart;*inend != '\0' && *inend != '/';) ! 1087: *outptr++ = *inend++; ! 1088: *outptr = '\0'; ! 1089: length = strlen(outstart); ! 1090: if(length > MAXFILENAME){ ! 1091: changed++; ! 1092: strcpy(outstart,findname(newname)); ! 1093: } ! 1094: outptr = outstart + strlen(outstart); ! 1095: instart = inend; ! 1096: } ! 1097: ! 1098: if(changed){ ! 1099: if(ntoolong == 0) { ! 1100: longnamefd = fopen("longnamelist","w"); ! 1101: if(longnamefd == NULL){ ! 1102: fprintf(stderr, ! 1103: "can't create longnamelist file\n"); ! 1104: exit(1); ! 1105: } ! 1106: fprintf(stderr,"check out file 'longnamelist'\n"); ! 1107: } ! 1108: printf("%s changed to %s\n",original,newname); ! 1109: fprintf(longnamefd,"%s\t%s\n",original, newname); ! 1110: fflush(longnamefd); ! 1111: strcpy(original,newname); ! 1112: ntoolong++; ! 1113: } ! 1114: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.