Commit 60bc31fcf6 for ffmpeg
commit 60bc31fcf6543505e6d2fc1a9399cca95f54ba4d
Author: Martin Mirchev <mmirchev@comp.nus.edu.sg>
Date: Wed Oct 21 18:26:38 2026 +0800
avcodec/jpeglsdec: decode line interleaved scans with more than 8 bits
The ILV=1 (line interleaved) path always called ls_decode_line() with
8 bits per sample, while the ILV=0 path selects 8 or 16 bits from the
frame. JPEG-LS with more than 8 bits is only accepted for a single
component, for which line interleaving is equivalent to ILV=0, but such
a scan was decoded as 8-bit samples into the 16-bit frame: only half of
each line was written and the output was wrong, e.g. a 16-bit gray image
from our encoder with the ILV byte set to 1 decodes to a different
picture than with ILV=0.
Use the 16-bit line decoder for more than 8 bits, as for ILV=0.
Signed-off-by: Martin Mirchev <mmirchev@comp.nus.edu.sg>
diff --git a/libavcodec/jpeglsdec.c b/libavcodec/jpeglsdec.c
index 7633bcceb6..0ab73eb3e4 100644
--- a/libavcodec/jpeglsdec.c
+++ b/libavcodec/jpeglsdec.c
@@ -480,11 +480,18 @@ int ff_jpegls_decode_picture(MJpegDecodeContext *s)
last = zero;
}
for (j = 0; j < stride; j++) {
- ret = ls_decode_line(state, s, last + j, cur + j,
- Rc[j], width, stride, j, 8);
+ if (s->bits <= 8) {
+ ret = ls_decode_line(state, s, last + j, cur + j,
+ Rc[j], width, stride, j, 8);
+ Rc[j] = last[j];
+ } else {
+ /* only single component scans can have more than 8 bits */
+ ret = ls_decode_line(state, s, last, cur,
+ Rc[j], width, stride, j, 16);
+ Rc[j] = *((uint16_t *)last);
+ }
if (ret < 0)
break;
- Rc[j] = last[j];
}
if (ret < 0)
break;