From c01259d4feb6da3fd50b5fa21a9b9f43c32983b3 Mon Sep 17 00:00:00 2001 From: Johnson Ding Date: Sun, 25 Apr 2021 15:02:50 +0800 Subject: [PATCH] [jpegd]: fix marker parsing error If there is an 0xff between two section, parser will stop searching marker. But if we skip this byte and contine parsing, it may be successfully decoded. Ref to https://redmine.rock-chips.com/issues/295017 Change-Id: Ia73bf66b05ea109ac19a7a5a37241a6381b468d3 Signed-off-by: Johnson Ding --- mpp/codec/dec/jpeg/jpegd_parser.c | 35 +++++++++++++++++++------------ 1 file changed, 22 insertions(+), 13 deletions(-) diff --git a/mpp/codec/dec/jpeg/jpegd_parser.c b/mpp/codec/dec/jpeg/jpegd_parser.c index cc95c56c..6a337b7f 100644 --- a/mpp/codec/dec/jpeg/jpegd_parser.c +++ b/mpp/codec/dec/jpeg/jpegd_parser.c @@ -31,7 +31,7 @@ RK_U32 jpegd_debug = 0x0; /* return the 8 bit start code value and update the search - state. Return -1 if no start code found */ + state. Return 0 if no start code found */ static RK_U8 jpegd_find_marker(const RK_U8 **pbuf_ptr, const RK_U8 *buf_end) { const RK_U8 *buf_ptr = NULL; @@ -39,18 +39,25 @@ static RK_U8 jpegd_find_marker(const RK_U8 **pbuf_ptr, const RK_U8 *buf_end) RK_U8 start_code = 0xff; RK_U32 buf_size = buf_end - *pbuf_ptr + 1; - buf_ptr = memchr(*pbuf_ptr, start_code, buf_size); - if (buf_ptr && (buf_end > buf_ptr) && *(buf_ptr + 1) >= 0xc0 && *(buf_ptr + 1) <= 0xfe) { - val = *(buf_ptr + 1); - jpegd_dbg_marker("find_marker skipped %d bytes\n", buf_ptr - *pbuf_ptr); - goto found; - } else { - buf_ptr = buf_end; - } + while (*pbuf_ptr < buf_end) { + buf_ptr = memchr(*pbuf_ptr, start_code, buf_size); -found: - *pbuf_ptr = buf_ptr + 2; - return val; + if (!buf_ptr) { + mpp_err("Start codec not found!\n"); + return 0; + } + + RK_U8 marker = *(buf_ptr + 1); + if (marker >= 0xc0 && marker <= 0xfe) { + val = *(buf_ptr + 1); + jpegd_dbg_marker("find_marker skipped %d bytes\n", buf_ptr - *pbuf_ptr); + return val; + } else { + jpegd_dbg_marker("0x%x is not a marker\n", marker); + (*pbuf_ptr)++; + } + } + return 0; } static MPP_RET jpegd_find_eoi(const RK_U8 **pbuf_ptr, const RK_U8 *buf_end) @@ -778,9 +785,11 @@ static MPP_RET jpegd_decode_frame(JpegdCtx *ctx) while (buf_ptr < buf_end) { /* find start marker */ start_code = jpegd_find_marker(&buf_ptr, buf_end); - if (start_code < 0) { + if (start_code <= 0) { jpegd_dbg_marker("start code not found\n"); break; + } else { + buf_ptr += 2; } jpegd_dbg_marker("marker = 0x%x, avail_size_in_buf = %d\n",