home *** CD-ROM | disk | FTP | other *** search
/ minnie.tuhs.org / unixen.tar / unixen / PDP-11 / Distributions / ucb / spencer_2bsd.tar.gz / 2bsd.tar / src / ckdir.c < prev    next >
C/C++ Source or Header  |  1980-02-17  |  3KB  |  194 lines

  1. /* Copyright (c) 1979 Regents of the University of California */
  2. #include <retrofit.h>
  3. #include <sys/types.h>
  4. #include <sys/dir.h>
  5. #include <sys/stat.h>
  6. #include <stdio.h>
  7.  
  8. /*
  9.  * Checksum the indicated directory, creating the file "check.sum"
  10.  * with names and int sums stored inside, one per line.  The -c
  11.  * option causes the directory checksums to be verified.
  12.  */
  13.  
  14. #define    equal(a, b)    (strcmp(a, b) == 0)
  15.  
  16. int    cflag = 1;            /* Flag to verify */
  17. char    cname[]    = "check.sum";        /* Name of checksum files */
  18. int    errs;                /* Error count */
  19.  
  20. main(argc, argv)
  21.     char **argv;
  22. {
  23.     register char *cp;
  24.  
  25.     if (argc == 2 && equal(argv[1], "-c")) {
  26.         cflag = 0;
  27.         argc--, argv++;
  28.     }
  29.     if (argc < 2) {
  30.         checkout(".");
  31.         exit(errs);
  32.     }
  33.     while (--argc) {
  34.         cp = *++argv;
  35.         if (equal(cp, "-c")) {
  36.             cflag++;
  37.             continue;
  38.         }
  39.         checkout(cp);
  40.     }
  41.     exit(errs);
  42. }
  43.  
  44. /*
  45.  * Checkout a directory.
  46.  * The fork is necessary to preserve the current directory.
  47.  */
  48.  
  49. checkout(dir)
  50.     char dir[];
  51. {
  52.     int s, pid;
  53.     char ename[DIRSIZ+1], linebuf[BUFSIZ];
  54.     FILE *cf, *df, *ef;
  55.     register int sum, c;
  56.     struct direct dirent;
  57.     register char *cp, *cp2;
  58.  
  59.     pid = fork();
  60.     if (pid == -1) {
  61.         perror("fork");
  62.         errs++;
  63.         return;
  64.     }
  65.     if (pid > 0) {
  66.         while (wait(&s) != pid)
  67.             ;
  68.         if (s != 0)
  69.             errs++;
  70.         return;
  71.     }
  72.     errs = 0;
  73.     fprintf(stderr, "%s:\n", dir);
  74.     if (chdir(dir) < 0) {
  75.         perror(dir);
  76.         exit(1);
  77.     }
  78.     if (cflag) {
  79.         if ((cf = fopen(cname, "r")) == NULL) {
  80.             perror(cname);
  81.             exit(1);
  82.         }
  83.         while (fgets(linebuf, BUFSIZ, cf) != NULL) {
  84.             for (cp = linebuf, cp2 = ename; *cp != ' ';
  85.                 *cp2++ = *cp++)
  86.                 ;
  87.             *cp2 = '\0';
  88.             if (equal(ename, cname))
  89.                 continue;
  90.             if ((ef = fopen(ename, "r")) == NULL) {
  91.                 perror(ename);
  92.                 errs++;
  93.                 continue;
  94.             }
  95.             c = cksum(ef);
  96.             fclose(ef);
  97.             sum = atoi(cp);
  98.             if (sum != c) {
  99.                 printf("Checksum error: \"%s\" is %d not %d\n",
  100.                     ename, c, sum);
  101.                 errs++;
  102.             }
  103.         }
  104.         exit(errs);
  105.     }
  106.     if ((cf = fopen(cname, "w")) == NULL) {
  107.         perror(cname);
  108.         exit(1);
  109.     }
  110.     if ((df = fopen("", "r")) == NULL) {
  111.         perror(dir);
  112.         exit(1);
  113.     }
  114.     while (fread((char *) &dirent, sizeof dirent, 1, df) == 1) {
  115.         struct stat stb;
  116.         if (dirent.d_ino == 0)
  117.             continue;
  118.         for (cp = dirent.d_name, cp2 = ename; *cp &&
  119.             cp-dirent.d_name < DIRSIZ; *cp2++ = *cp++)
  120.             ;
  121.         *cp2 = '\0';
  122.         if (equal(ename, cname))
  123.             continue;
  124.         if ((ef = fopen(ename, "r")) == NULL) {
  125.             perror(ename);
  126.             errs++;
  127.             continue;
  128.         }
  129.         fstat(fileno(ef), &stb);
  130.         if ((stb.st_mode & S_IFMT) != S_IFREG) {
  131.             fclose(ef);
  132.             continue;
  133.         }
  134.         sum = cksum(ef);
  135.         fclose(ef);
  136.         fprintf(cf, "%s %d\n", ename, sum);
  137.     }
  138.     exit(errs);
  139. }
  140.  
  141. /*
  142.  * Checksum the passed file.  Return the sum of all of its bytes.
  143.  */
  144.  
  145. cksum(f)
  146.     FILE *f;
  147. {
  148.     register int sum, c;
  149.  
  150.     sum = 0;
  151.     while ((c = getc(f)) != EOF)
  152.         sum += c;
  153.     if (sum < 0)
  154.         sum = -sum;
  155.     if (sum < 0)
  156.         sum = 0;
  157.     return(sum);
  158. }
  159.  
  160. /*
  161.  * Convert the passed string to decimal.
  162.  */
  163.  
  164. atoi(cp)
  165.     register char *cp;
  166. {
  167.     register int sum, sign;
  168.  
  169.     while (any(*cp, " \t"))
  170.         cp++;
  171.     if (*cp == '-')
  172.         sign = -1;
  173.     else
  174.         sign = 1;
  175.     sum = 0;
  176.     while (any(*cp, "0123456789"))
  177.         sum = sum*10 + *cp++ - '0';
  178.     return(sign*sum);
  179. }
  180.  
  181. /*
  182.  * Is c any of *cp ?
  183.  */
  184.  
  185. any(c, cp)
  186.     register int c;
  187.     register char *cp;
  188. {
  189.     while (*cp)
  190.         if (c == *cp++)
  191.             return(1);
  192.     return(0);
  193. }
  194.