Write out all of the available bits when using Z_BLOCK.
authorMark Adler <madler@alumni.caltech.edu>
Thu, 29 Dec 2011 21:19:27 +0000 (13:19 -0800)
committerMark Adler <madler@alumni.caltech.edu>
Sat, 7 Jan 2012 22:08:02 +0000 (14:08 -0800)
Previously, the bit buffer would hold 1 to 16 bits after "all" of the
output is provided after a Z_BLOCK deflate() call.  Now at most seven
bits remain in the output buffer after Z_BLOCK.  flush_pending() now
flushes the bit buffer before copying out the byte buffer, in order
for it to really flush as much as possible.

deflate.c
deflate.h
trees.c

index 12fbd5a..3c04f5d 100644 (file)
--- a/deflate.c
+++ b/deflate.c
@@ -638,19 +638,22 @@ local void putShortMSB (s, b)
 local void flush_pending(strm)
     z_streamp strm;
 {
-    unsigned len = strm->state->pending;
+    unsigned len;
+    deflate_state *s = strm->state;
 
+    _tr_flush_bits(s);
+    len = s->pending;
     if (len > strm->avail_out) len = strm->avail_out;
     if (len == 0) return;
 
-    zmemcpy(strm->next_out, strm->state->pending_out, len);
+    zmemcpy(strm->next_out, s->pending_out, len);
     strm->next_out  += len;
-    strm->state->pending_out  += len;
+    s->pending_out  += len;
     strm->total_out += len;
     strm->avail_out  -= len;
-    strm->state->pending -= len;
-    if (strm->state->pending == 0) {
-        strm->state->pending_out = strm->state->pending_buf;
+    s->pending -= len;
+    if (s->pending == 0) {
+        s->pending_out = s->pending_buf;
     }
 }
 
index 3590e4d..d605fc6 100644 (file)
--- a/deflate.h
+++ b/deflate.h
@@ -296,6 +296,7 @@ void ZLIB_INTERNAL _tr_init OF((deflate_state *s));
 int ZLIB_INTERNAL _tr_tally OF((deflate_state *s, unsigned dist, unsigned lc));
 void ZLIB_INTERNAL _tr_flush_block OF((deflate_state *s, charf *buf,
                         ulg stored_len, int last));
+void ZLIB_INTERNAL _tr_flush_bits OF((deflate_state *s));
 void ZLIB_INTERNAL _tr_align OF((deflate_state *s));
 void ZLIB_INTERNAL _tr_stored_block OF((deflate_state *s, charf *buf,
                         ulg stored_len, int last));
diff --git a/trees.c b/trees.c
index d5e1a56..8c32b21 100644 (file)
--- a/trees.c
+++ b/trees.c
@@ -877,6 +877,15 @@ void ZLIB_INTERNAL _tr_stored_block(s, buf, stored_len, last)
 }
 
 /* ===========================================================================
+ * Flush the bits in the bit buffer to pending output (leaves at most 7 bits)
+ */
+void ZLIB_INTERNAL _tr_flush_bits(s)
+    deflate_state *s;
+{
+    bi_flush(s);
+}
+
+/* ===========================================================================
  * Send one empty static block to give enough lookahead for inflate.
  * This takes 10 bits, of which 7 may remain in the bit buffer.
  */