1 /* $Id: inflate.c,v 1.7 2002/01/31 18:28:24 ukai Exp $ */
2 #include <stdio.h>
3 #include <stdlib.h>
4 #include <zlib.h>
5
6 #undef BUFSIZE
7 #define BUFSIZE 4096
8
9 static char dummy_head[1 + 1] = {
10 0x8 + 0x7 * 0x10,
11 (((0x8 + 0x7 * 0x10) * 0x100 + 30) / 31 * 31) & 0xFF,
12 };
13
14 int
main(int argc,char ** argv)15 main(int argc, char **argv)
16 {
17 z_stream s;
18 FILE *f;
19 char inbuf[BUFSIZE], outbuf[BUFSIZE];
20 int status, flush, retry = 0, len = 0;
21
22 if (argc > 1) {
23 f = fopen(argv[1], "rb");
24 if (!f) {
25 fprintf(stderr, "%s: cannot open %s\n", argv[0], argv[1]);
26 exit(1);
27 }
28 }
29 else
30 f = stdin;
31
32 s.zalloc = Z_NULL;
33 s.zfree = Z_NULL;
34 s.opaque = Z_NULL;
35 status = inflateInit(&s);
36 if (status != Z_OK) {
37 fprintf(stderr, "%s: inflateInit() %s\n", argv[0], zError(status));
38 exit(1);
39 }
40 s.avail_in = 0;
41 s.next_out = (Bytef *) outbuf;
42 s.avail_out = sizeof(outbuf);
43 flush = Z_NO_FLUSH;
44 while (1) {
45 if (s.avail_in == 0) {
46 s.next_in = (Bytef *) inbuf;
47 len = s.avail_in = fread(inbuf, 1, sizeof(inbuf), f);
48 }
49 status = inflate(&s, flush);
50 if (status == Z_STREAM_END || status == Z_BUF_ERROR) {
51 if (sizeof(outbuf) - s.avail_out)
52 fwrite(outbuf, 1, sizeof(outbuf) - s.avail_out, stdout);
53 break;
54 }
55 if (status == Z_DATA_ERROR && !retry++) {
56 status = inflateReset(&s);
57 if (status != Z_OK) {
58 fprintf(stderr, "%s: inflateReset() %s\n", argv[0],
59 zError(status));
60 exit(1);
61 }
62 s.next_in = (Bytef *) dummy_head;
63 s.avail_in = sizeof(dummy_head);
64 status = inflate(&s, flush);
65 s.next_in = (Bytef *) inbuf;
66 s.avail_in = len;
67 continue;
68 }
69 if (status != Z_OK) {
70 fprintf(stderr, "%s: inflate() %s\n", argv[0], zError(status));
71 exit(1);
72 }
73 if (s.avail_out == 0) {
74 fwrite(outbuf, 1, sizeof(outbuf), stdout);
75 s.next_out = (Bytef *) outbuf;
76 s.avail_out = sizeof(outbuf);
77 }
78 retry = 1;
79 }
80 inflateEnd(&s);
81 fclose(f);
82 return 0;
83 }
84