+static read_method_decl(pack_non_delta)
+{
+ size_t total_read = 0;
+
+ switch (st->z_state) {
+ case z_unused:
+ memset(&st->z, 0, sizeof(st->z));
+ git_inflate_init(&st->z);
+ st->z_state = z_used;
+ break;
+ case z_done:
+ return 0;
+ case z_error:
+ return -1;
+ case z_used:
+ break;
+ }
+
+ while (total_read < sz) {
+ int status;
+ struct pack_window *window = NULL;
+ unsigned char *mapped;
+
+ mapped = use_pack(st->u.in_pack.pack, &window,
+ st->u.in_pack.pos, &st->z.avail_in);
+
+ st->z.next_out = (unsigned char *)buf + total_read;
+ st->z.avail_out = sz - total_read;
+ st->z.next_in = mapped;
+ status = git_inflate(&st->z, Z_FINISH);
+
+ st->u.in_pack.pos += st->z.next_in - mapped;
+ total_read = st->z.next_out - (unsigned char *)buf;
+ unuse_pack(&window);
+
+ if (status == Z_STREAM_END) {
+ git_inflate_end(&st->z);
+ st->z_state = z_done;
+ break;
+ }
+ if (status != Z_OK && status != Z_BUF_ERROR) {
+ git_inflate_end(&st->z);
+ st->z_state = z_error;
+ return -1;
+ }
+ }
+ return total_read;
+}
+
+static close_method_decl(pack_non_delta)
+{
+ close_deflated_stream(st);
+ return 0;
+}
+
+static struct stream_vtbl pack_non_delta_vtbl = {
+ close_istream_pack_non_delta,
+ read_istream_pack_non_delta,
+};
+