diff mbox series

[FFmpeg-devel,7/7] avcodec/webp: Use LE VLC table for LE bitstream reader

Message ID 20201012081217.1643833-7-andreas.rheinhardt@gmail.com
State Accepted
Commit 00772ef4f7c87e708b5292a696c3efc78d234366
Headers show
Series [FFmpeg-devel,1/7] avcodec/indeo2: Remove #ifdef BITSTREAM_READER_LE cruft | expand

Checks

Context Check Description
andriy/x86_make success Make finished
andriy/x86_make_fate success Make fate finished
andriy/PPC64_make warning Make failed

Commit Message

Andreas Rheinhardt Oct. 12, 2020, 8:12 a.m. UTC
The WebP format uses Huffman tables and the decoder therefore uses
VLC tables. Given that WebP is a LE format, a LE bitreader is used;
yet the VLC table is not created for a LE reader (the process used to
create the tables puts the last bit to be read in the lowest bit) and
therefore custom code for reading the VLCs that reverses the bits
read is used instead of get_vlc2(). This commit changes this to use
a table designed for LE bitreader which allows to use get_vlc2() directly.
The necessary reversing of the codes is delegated to
ff_init_vlc_sparse() (and is therefore only done during init and not
when actually reading the VLCs).

Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt@gmail.com>
---
 libavcodec/webp.c | 42 ++----------------------------------------
 1 file changed, 2 insertions(+), 40 deletions(-)

Comments

Paul B Mahol Oct. 12, 2020, 9:48 a.m. UTC | #1
On Mon, Oct 12, 2020 at 10:12:17AM +0200, Andreas Rheinhardt wrote:
> The WebP format uses Huffman tables and the decoder therefore uses
> VLC tables. Given that WebP is a LE format, a LE bitreader is used;
> yet the VLC table is not created for a LE reader (the process used to
> create the tables puts the last bit to be read in the lowest bit) and
> therefore custom code for reading the VLCs that reverses the bits
> read is used instead of get_vlc2(). This commit changes this to use
> a table designed for LE bitreader which allows to use get_vlc2() directly.
> The necessary reversing of the codes is delegated to
> ff_init_vlc_sparse() (and is therefore only done during init and not
> when actually reading the VLCs).

lgtm
diff mbox series

Patch

diff --git a/libavcodec/webp.c b/libavcodec/webp.c
index c6d0206846..6140c7ea4a 100644
--- a/libavcodec/webp.c
+++ b/libavcodec/webp.c
@@ -232,44 +232,6 @@  static void image_ctx_free(ImageContext *img)
     memset(img, 0, sizeof(*img));
 }
 
-
-/* Differs from get_vlc2() in the following ways:
- *   - codes are bit-reversed
- *   - assumes 8-bit table to make reversal simpler
- *   - assumes max depth of 2 since the max code length for WebP is 15
- */
-static av_always_inline int webp_get_vlc(GetBitContext *gb, VLC_TYPE (*table)[2])
-{
-    int n, nb_bits;
-    unsigned int index;
-    int code;
-
-    OPEN_READER(re, gb);
-    UPDATE_CACHE(re, gb);
-
-    index = SHOW_UBITS(re, gb, 8);
-    index = ff_reverse[index];
-    code  = table[index][0];
-    n     = table[index][1];
-
-    if (n < 0) {
-        LAST_SKIP_BITS(re, gb, 8);
-        UPDATE_CACHE(re, gb);
-
-        nb_bits = -n;
-
-        index = SHOW_UBITS(re, gb, nb_bits);
-        index = (ff_reverse[index] >> (8 - nb_bits)) + code;
-        code  = table[index][0];
-        n     = table[index][1];
-    }
-    SKIP_BITS(re, gb, n);
-
-    CLOSE_READER(re, gb);
-
-    return code;
-}
-
 static int huff_reader_get_symbol(HuffReader *r, GetBitContext *gb)
 {
     if (r->simple) {
@@ -278,7 +240,7 @@  static int huff_reader_get_symbol(HuffReader *r, GetBitContext *gb)
         else
             return r->simple_symbols[get_bits1(gb)];
     } else
-        return webp_get_vlc(gb, r->vlc.table);
+        return get_vlc2(gb, r->vlc.table, 8, 2);
 }
 
 static int huff_reader_build_canonical(HuffReader *r, int *code_lengths,
@@ -332,7 +294,7 @@  static int huff_reader_build_canonical(HuffReader *r, int *code_lengths,
 
     ret = init_vlc(&r->vlc, 8, alphabet_size,
                    code_lengths, sizeof(*code_lengths), sizeof(*code_lengths),
-                   codes, sizeof(*codes), sizeof(*codes), 0);
+                   codes, sizeof(*codes), sizeof(*codes), INIT_VLC_OUTPUT_LE);
     if (ret < 0) {
         av_free(codes);
         return ret;