diff options
author | Zane van Iperen <zane@zanevaniperen.com> | 2020-09-12 22:02:26 +1000 |
---|---|---|
committer | Zane van Iperen <zane@zanevaniperen.com> | 2020-09-19 15:34:25 +1000 |
commit | 9eabe9c4b53365426eddbcdef91f07254f102ae2 (patch) | |
tree | 3408f6dd5895bb4400cab86c5bc4596463ec280f /libavcodec/adpcm.c | |
parent | 624f6df19f79f319faf19718c24a9471fa36f61c (diff) | |
download | ffmpeg-9eabe9c4b53365426eddbcdef91f07254f102ae2.tar.gz |
avcodec/adpcm_argo: support decoding multiple frames
Increases decode speed significantly.
Signed-off-by: Zane van Iperen <zane@zanevaniperen.com>
Diffstat (limited to 'libavcodec/adpcm.c')
-rw-r--r-- | libavcodec/adpcm.c | 16 |
1 files changed, 8 insertions, 8 deletions
diff --git a/libavcodec/adpcm.c b/libavcodec/adpcm.c index e409a3aa6a..14be1f4f88 100644 --- a/libavcodec/adpcm.c +++ b/libavcodec/adpcm.c @@ -181,7 +181,7 @@ static av_cold int adpcm_decode_init(AVCodecContext * avctx) c->vqa_version = AV_RL16(avctx->extradata); break; case AV_CODEC_ID_ADPCM_ARGO: - if (avctx->bits_per_coded_sample != 4) + if (avctx->bits_per_coded_sample != 4 || avctx->block_align != 17 * avctx->channels) return AVERROR_INVALIDDATA; break; case AV_CODEC_ID_ADPCM_ZORK: @@ -745,11 +745,6 @@ static int get_nb_samples(AVCodecContext *avctx, GetByteContext *gb, return 0; nb_samples = 64; break; - case AV_CODEC_ID_ADPCM_ARGO: - if (buf_size < 17 * ch) - return 0; - nb_samples = 32; - break; /* simple 4-bit adpcm */ case AV_CODEC_ID_ADPCM_CT: case AV_CODEC_ID_ADPCM_IMA_APC: @@ -922,6 +917,9 @@ static int get_nb_samples(AVCodecContext *avctx, GetByteContext *gb, case AV_CODEC_ID_ADPCM_PSX: nb_samples = buf_size / (16 * ch) * 28; break; + case AV_CODEC_ID_ADPCM_ARGO: + nb_samples = buf_size / avctx->block_align * 32; + break; case AV_CODEC_ID_ADPCM_ZORK: nb_samples = buf_size / ch; break; @@ -2023,22 +2021,24 @@ static int adpcm_decode_frame(AVCodecContext *avctx, void *data, * Each block relies on the previous two samples of each channel. * They should be 0 initially. */ + for (int block = 0; block < avpkt->size / avctx->block_align; block++) { for (channel = 0; channel < avctx->channels; channel++) { int control, shift; - samples = samples_p[channel]; + samples = samples_p[channel] + block * 32; cs = c->status + channel; /* Get the control byte and decode the samples, 2 at a time. */ control = bytestream2_get_byteu(&gb); shift = (control >> 4) + 2; - for (n = 0; n < nb_samples / 2; n++) { + for (n = 0; n < 16; n++) { int sample = bytestream2_get_byteu(&gb); *samples++ = ff_adpcm_argo_expand_nibble(cs, sample >> 4, shift, control & 0x04); *samples++ = ff_adpcm_argo_expand_nibble(cs, sample >> 0, shift, control & 0x04); } } + } break; case AV_CODEC_ID_ADPCM_ZORK: if (!c->has_status) { |