We used to limit this number to two and name them with their usual
usage. The specification is however broader, and you can find files that
use more tables as in the following link:
20050519/tests/A_2_1-BF-01.htm
No real behavior change. (The two globals are now both initialized
at first use instead of before main(), but that should have no
observable effect. The motivation is readability.)
read_webp_first_chunk() sensibly assumes that if decode_webp_header()
succeeds, there are at least sizeof(WebPFileHeader) bytes available.
But if the file size in the header was less than the size of the header,
decode_webp_header() would truncate the data to less than that and
happily report success. Now it no longer does that.
Found by clusterfuzz:
https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=57843&sort=-opened&can=1&q=proj%3Aserenity
Prefix code decoding seems to work fairly well and produces a ton of
log output with `#define WEBP_DEBUG 1`, so remove the log lines.
(If needed it's always possible to just locally revert this commit.)
No behavior change, since WEBP_DEBUG isn't usually defined.
WebP lossless files that use a color indexing transform with <= 16
colors use pixel bundling to pack 2, 4, or 8 pixels into a single pixel.
If the image's width doesn't happen to be an exact multiple of the
bundling factor, we need to:
1. Use ceil_div() instead of just dividing the width by the bundling
factor
2. Remember the original width and use it instead of computing
reduced width times bundling factor
This does these changes, and adds a simple test for it -- it at least
checks that the decoded images have the right size.
(I created these images myself in Photoshop, and used the same
technique as for Tests/LibGfx/test-inputs/catdog-alert-*.webp
to create images with a certain number of colors.)
See the lengthy comment added in this commit for details.
With this, the webp lossless decoder is feature complete :^)
(...except for bug fixes and performance improvements, as always.)
...in addition to modifying in-place. This is needed for bitpacking
support for the color indexing transform (and it could also be used
to make the color indexing transform return an indexed bitmap, which
is something we could do if that's the last transform that's applied).
No behavior change.
Reduces the time to run
Build/lagom/image ~/src/libwebp/webp_js/test_webp_wasm.webp -o tmp.png
from 0.5s to 0.25s.
Before, 60% of the time was spent decoding webp and 40% writing png.
Now, 16% of the time was spent decoding webp and 84% writing png.
That means png writing takes 0.2s, and webp decoding time went from
0.3s to 0.05s.
A template expression without explicit return type deduces its return
type as if for a function whose return type is declared auto. That
does deduce return-by-value, while `decltype(auto)` would deduce
return-by-reference. Explictly saying `decltype(auto)` would work
too, but writing out the type is maybe easier to understand.
No behavior change other than being much faster.
The previous attempt was in commit e5e9d3b877, where I thought
max_symbol describes how many code lengths should be read.
But it looks like it instead describes how many code length input
symbols should be read. (The two aren't the same since one code length
input symbol can produce several code lengths.)
I still agree with the commit description of e5e9d3b877 that the spec
isn't very clear on this :)
This time I've found a file that sets max_symbol and with this change
here, that file decodes correctly. (It's Qpalette.webp, which I'm about
to add as a test case.)
WebP lossless differs from deflate in how it handles 1-element codes.
Deflate consumes one bit from the bitstream to produce the element,
while webp lossless consumes 0 bits. Add a wrapper class to handle
this case.
The `static` here meant we always kept the alphabet sizes of the
first image we happened to load -- and a single webp lossless image
can store several helper images used during decoding.
Usually, the helper images wouldn't use a color cache but the main
image would, but the main image would then use the first entry from
the helper images due to the `static`, which led us to not decoding
the codes for the color cache symbols.
No need to store them in `i32`, the JPEG norm specifies that they are
not bigger than 16 bits for extended JPEGs. So, in this patch, we
replace `i32` with `i16`. It almost divides memory usage by two :^)
The spec is at best misleading here, suggesting that max_symbol should
be set to "num_code_lengths" if it's not explicitly stored.
But num_code_lengths doesn't mean the num_code_lengths mentioned a few
lines further up in the spec, but alphabet_size!
(I had to cheat and look at libwebp instead of the spec for this: See
vp8l_dec.c, ReadHuffmanCode() which passes alphabet_size to
ReadHuffmanCodeLengths() as num_symbols, and ReadHuffmanCodeLengths()
then sets max_symbol to that.)
I haven't yet found a file that uses max_symbol, so this isn't actually
tested. But it's close to what's in libwebp, so maybe it works!
Missing:
* Transform support (used by virtually all lossless webp files)
* Meta prefix / entropy image support
Working:
* Decoding of regular image streams
* Color cache
This happens to be enough to be able to decode
Tests/LibGfx/test-inputs/extended-lossless.webp
The canonical prefix code is very similar to deflate's, enough so that
this can use Compress::CanonicalCode (and take advantage of all the
recent performance improvements there).
This patch adds support for properly read images with four components,
basically CMYK or YCCK. However, we still lack color spaces
transformations for this type of image. So, it just postpones failure.
As mentioned in F.2.1.5 - Inverse DCT (IDCT), the decoder needs to
perform a level shift by adding 128. This used to be done in
`ycbcr_to_rgb` after the conversion. Now, we do it in `inverse_dct` in
order to ensure that the task is done unconditionally.
Consequences of this are that we are no longer required to explicitly
do it for RGB images and also, the `ycbcr_to_rgb` function is exactly
like the specification.
When reading the stream, interpreted as a normal value 0xF0 means skip
15 values and assign the 16th to 0. On the other hand, the marker ZRL
- which has the value 0xF0, means skip 16 values. For baseline JPEGs,
ZRL doesn't need to be interpreted differently as writing the 16th value
has no consequence. This is no longer the case with refining scans.
That's why this patch implement correctly ZRL.
We used to skip over zero coefficient by modifying the loop counter. It
is unfortunately impossible to perform this with SOF2 images as only
coefficients with a zero-history should be skipped.
This induces no behavior change for the user of the function.
This commit is nonsense for anything else than SOF2 images with spectral
approximation. For this particular case, skips like EOB or ZRL only
apply to coefficients with a zero-history. This commit prepares the code
to handle this behavior.