]> git.lizzy.rs Git - plan9front.git/blob - sys/src/cmd/crc32.c
libtags, zuke: add *.mod support (thanks kemal)
[plan9front.git] / sys / src / cmd / crc32.c
1 #include <u.h>
2 #include <libc.h>
3 #include <libsec.h>
4
5 u32int table[256];
6 u32int xor = -1, init, poly = 0xedb88320;
7 char *error;
8
9 static void
10 dotable(void)
11 {
12         u32int c;
13         int n, k;
14
15         for(n = 0; n < 256; n++){
16                 c = n;
17                 for(k = 0; k < 8; k++)
18                         if((c & 1) != 0)
19                                 c = poly ^ c >> 1;
20                         else
21                                 c >>= 1;
22                 table[n] = c;
23         }
24 }
25
26 static u32int
27 calc(u32int init, uchar *buf, ulong len)
28 {
29         u32int c;
30         
31         c = init;
32         while(len-- != 0)
33                 c = table[(*buf++ ^ c) & 0xff] ^ c >> 8;
34         return c;
35 }
36
37 static void
38 sum(int fd, char *name)
39 {
40         int n;
41         uchar buf[8192];
42         u32int crc;
43
44         crc = init ^ xor;
45         while((n = read(fd, buf, sizeof buf)) > 0)
46                 crc = calc(crc, buf, n);
47         if(n < 0){
48                 fprint(2, "reading %s: %r\n", name ? name : "stdin");
49                 error = "read";
50                 return;
51         }
52         crc ^= xor;
53         if(name == nil)
54                 print("%ux\n", crc);
55         else
56                 print("%ux\t%s\n", crc, name);
57 }
58
59 void
60 usage(void)
61 {
62         fprint(2, "usage: %s [-x xorval] [-i initial] [-p poly] [file...]\n", argv0);
63         exits("usage");
64 }
65
66 void
67 main(int argc, char *argv[])
68 {
69         int i, fd;
70
71         ARGBEGIN{
72         case 'x':
73                 xor = strtol(EARGF(usage()), 0, 0);
74                 break;
75         case 'i':
76                 init = strtol(EARGF(usage()), 0, 0);
77                 break;
78         case 'p':
79                 poly = strtol(EARGF(usage()), 0, 0);
80                 break;
81         default:
82                 usage();
83         }ARGEND
84
85         dotable();
86         if(argc == 0)
87                 sum(0, nil);
88         else for(i = 0; i < argc; i++){
89                 fd = open(argv[i], OREAD);
90                 if(fd < 0){
91                         fprint(2, "crc32: can't open %s: %r\n", argv[i]);
92                         error = "open";
93                         continue;
94                 }
95                 sum(fd, argv[i]);
96                 close(fd);
97         }
98         exits(error);
99 }