diff options
author | Alexis La Goutte <alexis.lagoutte@gmail.com> | 2015-01-07 21:32:47 +0100 |
---|---|---|
committer | Alexis La Goutte <alexis.lagoutte@gmail.com> | 2015-01-15 08:34:38 +0000 |
commit | adaa661b74b1b407341e67052fb430914cba127d (patch) | |
tree | 3b19913b04f10c369e5ea166c6e0130958070d96 /epan/nghttp2/nghttp2_hd_huffman.c | |
parent | 5b92ab9f97a4d1644218059e3b17097a02421bc4 (diff) |
Update to libnghttp2 0.7.1
Change-Id: Ib8d40586a3b95674447819f77eaaa69376dce6fd
Reviewed-on: https://code.wireshark.org/review/6411
Reviewed-by: Alexis La Goutte <alexis.lagoutte@gmail.com>
Diffstat (limited to 'epan/nghttp2/nghttp2_hd_huffman.c')
-rw-r--r-- | epan/nghttp2/nghttp2_hd_huffman.c | 107 |
1 files changed, 59 insertions, 48 deletions
diff --git a/epan/nghttp2/nghttp2_hd_huffman.c b/epan/nghttp2/nghttp2_hd_huffman.c index 1f5388c79b..6c4b2b64ce 100644 --- a/epan/nghttp2/nghttp2_hd_huffman.c +++ b/epan/nghttp2/nghttp2_hd_huffman.c @@ -44,56 +44,72 @@ static ssize_t huff_encode_sym(nghttp2_bufs *bufs, size_t *avail_ptr, size_t rembits, const nghttp2_huff_sym *sym) { int rv; size_t nbits = sym->nbits; + uint32_t code = sym->code; - for (;;) { - if (rembits > nbits) { - if (*avail_ptr) { - nghttp2_bufs_fast_orb_hold(bufs, sym->code << (rembits - nbits)); - } else { - rv = nghttp2_bufs_orb_hold(bufs, sym->code << (rembits - nbits)); - if (rv != 0) { - return rv; - } - - *avail_ptr = nghttp2_bufs_cur_avail(bufs); - } + /* We assume that sym->nbits <= 32 */ + if (rembits > nbits) { + nghttp2_bufs_fast_orb_hold(bufs, code << (rembits - nbits)); + return (ssize_t)(rembits - nbits); + } - rembits -= nbits; + if (rembits == nbits) { + nghttp2_bufs_fast_orb(bufs, code); + --*avail_ptr; + return 8; + } - break; - } + nghttp2_bufs_fast_orb(bufs, code >> (nbits - rembits)); + --*avail_ptr; - if (*avail_ptr) { - nghttp2_bufs_fast_orb(bufs, sym->code >> (nbits - rembits)); - --*avail_ptr; - } else { - rv = nghttp2_bufs_orb(bufs, sym->code >> (nbits - rembits)); - if (rv != 0) { - return rv; - } + nbits -= rembits; + if (nbits & 0x7) { + /* align code to MSB byte boundary */ + code <<= 8 - (nbits & 0x7); + } - *avail_ptr = nghttp2_bufs_cur_avail(bufs); + /* we lose at most 3 bytes, but it is not critical in practice */ + if (*avail_ptr < (nbits + 7) / 8) { + rv = nghttp2_bufs_advance(bufs); + if (rv != 0) { + return rv; } + *avail_ptr = nghttp2_bufs_cur_avail(bufs); + /* we assume that we at least 3 buffer space available */ + assert(*avail_ptr >= 3); + } - nbits -= rembits; - rembits = 8; + /* fast path, since most code is less than 8 */ + if (nbits < 8) { + nghttp2_bufs_fast_addb_hold(bufs, code); + *avail_ptr = nghttp2_bufs_cur_avail(bufs); + return (ssize_t)(8 - nbits); + } - if (nbits == 0) { - break; - } + /* handle longer code path */ + if (nbits > 24) { + nghttp2_bufs_fast_addb(bufs, code >> 24); + nbits -= 8; + } - if (*avail_ptr) { - nghttp2_bufs_fast_addb_hold(bufs, 0); - } else { - rv = nghttp2_bufs_addb_hold(bufs, 0); - if (rv != 0) { - return rv; - } + if (nbits > 16) { + nghttp2_bufs_fast_addb(bufs, code >> 16); + nbits -= 8; + } - *avail_ptr = nghttp2_bufs_cur_avail(bufs); - } + if (nbits > 8) { + nghttp2_bufs_fast_addb(bufs, code >> 8); + nbits -= 8; } - return (ssize_t)rembits; + + if (nbits == 8) { + nghttp2_bufs_fast_addb(bufs, code); + *avail_ptr = nghttp2_bufs_cur_avail(bufs); + return 8; + } + + nghttp2_bufs_fast_addb_hold(bufs, code); + *avail_ptr = nghttp2_bufs_cur_avail(bufs); + return (ssize_t)(8 - nbits); } size_t nghttp2_hd_huff_encode_count(const uint8_t *src, size_t len) { @@ -136,17 +152,12 @@ int nghttp2_hd_huff_encode(nghttp2_bufs *bufs, const uint8_t *src, } /* 256 is special terminal symbol, pad with its prefix */ if (rembits < 8) { + /* if rembits < 8, we should have at least 1 buffer space + available */ const nghttp2_huff_sym *sym = &huff_sym_table[256]; - + assert(avail); /* Caution we no longer adjust avail here */ - if (avail) { - nghttp2_bufs_fast_orb(bufs, sym->code >> (sym->nbits - rembits)); - } else { - rv = nghttp2_bufs_orb(bufs, sym->code >> (sym->nbits - rembits)); - if (rv != 0) { - return rv; - } - } + nghttp2_bufs_fast_orb(bufs, sym->code >> (sym->nbits - rembits)); } return 0; |