avcodec/vima: IMA4 subtag support

Support decoding of the IMA4 ADPCM QT scheme used in some LucasArts
SANM files.

Signed-off-by: Manuel Lauss <manuel.lauss@gmail.com>
This commit is contained in:
Manuel Lauss
2025-08-16 10:44:06 +02:00
parent 1e95f1b269
commit 9141fe9653

View File

@@ -28,6 +28,7 @@
#include "libavutil/channel_layout.h"
#include "libavutil/thread.h"
#include "adpcm.h"
#include "adpcm_data.h"
#include "avcodec.h"
#include "codec_internal.h"
@@ -159,6 +160,19 @@ static int decode_frame(AVCodecContext *avctx, AVFrame *frame,
if ((ret = ff_get_buffer(avctx, frame, 0)) < 0)
return ret;
if (show_bits_long(&gb, 32) == MKBETAG('I','M','A','4')) {
int16_t *dest = (int16_t *)frame->data[0];
ADPCMChannelStatus cs;
skip_bits_long(&gb, 32); /* skip the 'IMA4' tag */
cs.predictor = (int16_t)get_xbits_le(&gb, 16);
cs.step_index = av_clip(get_bits(&gb, 8), 0, 88);
for (int i = 0; i < samples; i++) {
ff_adpcm_ima_qt_expand_nibble(&cs, get_bits(&gb, 4));
for (int j = 0; j < channels; j++)
*dest++ = cs.predictor;
}
} else {
for (chan = 0; chan < channels; chan++) {
uint16_t *dest = (uint16_t *)frame->data[0] + chan;
int step_index = channel_hint[chan];
@@ -200,6 +214,7 @@ static int decode_frame(AVCodecContext *avctx, AVFrame *frame,
step_index += step_index_tables[lookup_size - 2][lookup];
}
}
}
*got_frame_ptr = 1;