1
0
mirror of https://github.com/FFmpeg/FFmpeg.git synced 2025-08-10 06:10:52 +02:00

avcodec/sanm: codec37 buffers are private

codec37 operates on 2 buffers, which must be considered private to
the codec and must therefore not be changed by subsequent FOBJs.

Let codec37 therefore operate on frm1/2 instead of frm0/2, but copy
the decoded image to frm0 where other codecs operate on.

Fixes artifacts encountered in Full Throttle "dazed.san" and also
in a lot of Rebel Assault II gameplay videos: these videos consist of
frames with an initial codec37 FOBJ image to set the stage, and
optional codec1-23 FOBJs overlaid on top of that image.

Signed-off-by: Manuel Lauss <manuel.lauss@gmail.com>
Signed-off-by: Michael Niedermayer <michael@niedermayer.cc>
This commit is contained in:
Manuel Lauss
2025-01-13 22:00:24 +01:00
committed by Michael Niedermayer
parent 4322be512b
commit d68d311bcd

View File

@@ -645,10 +645,11 @@ static int old_codec37(SANMVideoContext *ctx, int top,
ctx->rotate_code = 0; ctx->rotate_code = 0;
if (((seq & 1) || !(flags & 1)) && (compr && compr != 2)) if (((seq & 1) || !(flags & 1)) && (compr && compr != 2)) {
rotate_bufs(ctx, 1); FFSWAP(uint16_t*, ctx->frm1, ctx->frm2);
}
dst = ((uint8_t*)ctx->frm0) + left + top * stride; dst = ((uint8_t*)ctx->frm1) + left + top * stride;
prev = ((uint8_t*)ctx->frm2) + left + top * stride; prev = ((uint8_t*)ctx->frm2) + left + top * stride;
if (mvoff > 2) { if (mvoff > 2) {
@@ -662,7 +663,6 @@ static int old_codec37(SANMVideoContext *ctx, int top,
bytestream2_get_buffer(&ctx->gb, dst, width); bytestream2_get_buffer(&ctx->gb, dst, width);
dst += stride; dst += stride;
} }
memset(ctx->frm1, 0, ctx->height * stride);
memset(ctx->frm2, 0, ctx->height * stride); memset(ctx->frm2, 0, ctx->height * stride);
break; break;
case 1: case 1:
@@ -729,7 +729,6 @@ static int old_codec37(SANMVideoContext *ctx, int top,
case 2: case 2:
if (rle_decode(ctx, dst, decoded_size)) if (rle_decode(ctx, dst, decoded_size))
return AVERROR_INVALIDDATA; return AVERROR_INVALIDDATA;
memset(ctx->frm1, 0, ctx->frm1_size);
memset(ctx->frm2, 0, ctx->frm2_size); memset(ctx->frm2, 0, ctx->frm2_size);
break; break;
case 3: case 3:
@@ -783,6 +782,7 @@ static int old_codec37(SANMVideoContext *ctx, int top,
return AVERROR_PATCHWELCOME; return AVERROR_PATCHWELCOME;
} }
memcpy(ctx->frm0, ctx->frm1, ctx->buf_size);
return 0; return 0;
} }