2 * zlib wrappers to make sure we don't silently miss errors
7 static const char *zerr_to_string(int status)
11 return "out of memory";
13 return "wrong version";
15 return "needs dictionary";
17 return "data stream error";
19 return "stream consistency error";
21 return "unknown error";
26 * avail_in and avail_out in zlib are counted in uInt, which typically
27 * limits the size of the buffer we can use to 4GB when interacting
28 * with zlib in a single call to inflate/deflate.
30 #define ZLIB_BUF_MAX ((uInt)-1)
31 static inline uInt zlib_buf_cap(unsigned long len)
33 if (ZLIB_BUF_MAX < len)
34 die("working buffer for zlib too large");
38 static void zlib_pre_call(git_zstream *s)
40 s->z.next_in = s->next_in;
41 s->z.next_out = s->next_out;
42 s->z.total_in = s->total_in;
43 s->z.total_out = s->total_out;
44 s->z.avail_in = zlib_buf_cap(s->avail_in);
45 s->z.avail_out = zlib_buf_cap(s->avail_out);
48 static void zlib_post_call(git_zstream *s)
50 s->next_in = s->z.next_in;
51 s->next_out = s->z.next_out;
52 s->total_in = s->z.total_in;
53 s->total_out = s->z.total_out;
54 s->avail_in = s->z.avail_in;
55 s->avail_out = s->z.avail_out;
58 void git_inflate_init(git_zstream *strm)
63 status = inflateInit(&strm->z);
67 die("inflateInit: %s (%s)", zerr_to_string(status),
68 strm->z.msg ? strm->z.msg : "no message");
71 void git_inflate_init_gzip_only(git_zstream *strm)
74 * Use default 15 bits, +16 is to accept only gzip and to
75 * yield Z_DATA_ERROR when fed zlib format.
77 const int windowBits = 15 + 16;
81 status = inflateInit2(&strm->z, windowBits);
85 die("inflateInit2: %s (%s)", zerr_to_string(status),
86 strm->z.msg ? strm->z.msg : "no message");
89 void git_inflate_end(git_zstream *strm)
94 status = inflateEnd(&strm->z);
98 error("inflateEnd: %s (%s)", zerr_to_string(status),
99 strm->z.msg ? strm->z.msg : "no message");
102 int git_inflate(git_zstream *strm, int flush)
107 status = inflate(&strm->z, flush);
108 zlib_post_call(strm);
110 /* Z_BUF_ERROR: normal, needs more space in the output buffer */
117 die("inflate: out of memory");
121 error("inflate: %s (%s)", zerr_to_string(status),
122 strm->z.msg ? strm->z.msg : "no message");
126 #if defined(NO_DEFLATE_BOUND) || ZLIB_VERNUM < 0x1200
127 #define deflateBound(c,s) ((s) + (((s) + 7) >> 3) + (((s) + 63) >> 6) + 11)
130 unsigned long git_deflate_bound(git_zstream *strm, unsigned long size)
132 return deflateBound(&strm->z, size);
135 void git_deflate_init(git_zstream *strm, int level)
140 status = deflateInit(&strm->z, level);
141 zlib_post_call(strm);
144 die("deflateInit: %s (%s)", zerr_to_string(status),
145 strm->z.msg ? strm->z.msg : "no message");
148 void git_deflate_init_gzip(git_zstream *strm, int level)
151 * Use default 15 bits, +16 is to generate gzip header/trailer
152 * instead of the zlib wrapper.
154 const int windowBits = 15 + 16;
158 status = deflateInit2(&strm->z, level,
159 Z_DEFLATED, windowBits,
160 8, Z_DEFAULT_STRATEGY);
161 zlib_post_call(strm);
164 die("deflateInit2: %s (%s)", zerr_to_string(status),
165 strm->z.msg ? strm->z.msg : "no message");
168 void git_deflate_end(git_zstream *strm)
173 status = deflateEnd(&strm->z);
174 zlib_post_call(strm);
177 error("deflateEnd: %s (%s)", zerr_to_string(status),
178 strm->z.msg ? strm->z.msg : "no message");
181 int git_deflate_end_gently(git_zstream *strm)
186 status = deflateEnd(&strm->z);
187 zlib_post_call(strm);
191 int git_deflate(git_zstream *strm, int flush)
196 status = deflate(&strm->z, flush);
197 zlib_post_call(strm);
199 /* Z_BUF_ERROR: normal, needs more space in the output buffer */
206 die("deflate: out of memory");
210 error("deflate: %s (%s)", zerr_to_string(status),
211 strm->z.msg ? strm->z.msg : "no message");