Skip to content
Snippets Groups Projects
Commit aac88b53 authored by Kostya Shishkov's avatar Kostya Shishkov
Browse files

Decode previous 32 frames to avoid seeking artifacts in MPC

Originally committed as revision 7393 to svn://svn.ffmpeg.org/ffmpeg/trunk
parent 0587b0ca
No related branches found
No related tags found
No related merge requests found
...@@ -51,6 +51,7 @@ typedef struct { ...@@ -51,6 +51,7 @@ typedef struct {
int lastframelen, bands; int lastframelen, bands;
int oldDSCF[2][BANDS]; int oldDSCF[2][BANDS];
int rnd; int rnd;
int frames_to_skip;
/* for synthesis */ /* for synthesis */
DECLARE_ALIGNED_16(MPA_INT, synth_buf[MPA_MAX_CHANNELS][512*2]); DECLARE_ALIGNED_16(MPA_INT, synth_buf[MPA_MAX_CHANNELS][512*2]);
int synth_buf_offset[MPA_MAX_CHANNELS]; int synth_buf_offset[MPA_MAX_CHANNELS];
...@@ -98,6 +99,7 @@ static int mpc7_decode_init(AVCodecContext * avctx) ...@@ -98,6 +99,7 @@ static int mpc7_decode_init(AVCodecContext * avctx)
c->lastframelen = get_bits(&gb, 11); c->lastframelen = get_bits(&gb, 11);
av_log(avctx, AV_LOG_DEBUG, "IS: %d, MSS: %d, TG: %d, LFL: %d, bands: %d\n", av_log(avctx, AV_LOG_DEBUG, "IS: %d, MSS: %d, TG: %d, LFL: %d, bands: %d\n",
c->IS, c->MSS, c->gapless, c->lastframelen, c->bands); c->IS, c->MSS, c->gapless, c->lastframelen, c->bands);
c->frames_to_skip = 0;
if(vlc_inited) return 0; if(vlc_inited) return 0;
av_log(avctx, AV_LOG_DEBUG, "Initing VLC\n"); av_log(avctx, AV_LOG_DEBUG, "Initing VLC\n");
...@@ -328,11 +330,23 @@ static int mpc7_decode_frame(AVCodecContext * avctx, ...@@ -328,11 +330,23 @@ static int mpc7_decode_frame(AVCodecContext * avctx,
av_log(NULL,0, "Error decoding frame: used %i of %i bits\n", bits_used, bits_avail); av_log(NULL,0, "Error decoding frame: used %i of %i bits\n", bits_used, bits_avail);
return -1; return -1;
} }
if(c->frames_to_skip){
c->frames_to_skip--;
*data_size = 0;
return buf_size;
}
*data_size = (buf[1] ? c->lastframelen : MPC_FRAME_SIZE) * 4; *data_size = (buf[1] ? c->lastframelen : MPC_FRAME_SIZE) * 4;
return buf_size; return buf_size;
} }
static void mpc7_decode_flush(AVCodecContext *avctx)
{
MPCContext *c = avctx->priv_data;
memset(c->oldDSCF, 0, sizeof(c->oldDSCF));
c->frames_to_skip = 32;
}
AVCodec mpc7_decoder = { AVCodec mpc7_decoder = {
"mpc sv7", "mpc sv7",
...@@ -343,4 +357,5 @@ AVCodec mpc7_decoder = { ...@@ -343,4 +357,5 @@ AVCodec mpc7_decoder = {
NULL, NULL,
NULL, NULL,
mpc7_decode_frame, mpc7_decode_frame,
.flush = mpc7_decode_flush,
}; };
...@@ -22,6 +22,7 @@ ...@@ -22,6 +22,7 @@
#include "bitstream.h" #include "bitstream.h"
#define MPC_FRAMESIZE 1152 #define MPC_FRAMESIZE 1152
#define DELAY_FRAMES 32
static const int mpc_rate[4] = { 44100, 48000, 37800, 32000 }; static const int mpc_rate[4] = { 44100, 48000, 37800, 32000 };
typedef struct { typedef struct {
...@@ -155,6 +156,7 @@ static int mpc_read_packet(AVFormatContext *s, AVPacket *pkt) ...@@ -155,6 +156,7 @@ static int mpc_read_packet(AVFormatContext *s, AVPacket *pkt)
pkt->data[1] = (c->curframe > c->fcount); pkt->data[1] = (c->curframe > c->fcount);
pkt->stream_index = 0; pkt->stream_index = 0;
pkt->pts = cur;
ret = get_buffer(&s->pb, pkt->data + 4, size); ret = get_buffer(&s->pb, pkt->data + 4, size);
if(c->curbits) if(c->curbits)
url_fseek(&s->pb, -4, SEEK_CUR); url_fseek(&s->pb, -4, SEEK_CUR);
...@@ -188,7 +190,7 @@ static int mpc_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp ...@@ -188,7 +190,7 @@ static int mpc_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp
MPCContext *c = s->priv_data; MPCContext *c = s->priv_data;
AVPacket pkt1, *pkt = &pkt1; AVPacket pkt1, *pkt = &pkt1;
int ret; int ret;
int index = av_index_search_timestamp(st, timestamp, flags); int index = av_index_search_timestamp(st, timestamp - DELAY_FRAMES, flags);
uint32_t lastframe; uint32_t lastframe;
/* if found, seek there */ /* if found, seek there */
...@@ -199,6 +201,7 @@ static int mpc_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp ...@@ -199,6 +201,7 @@ static int mpc_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp
/* if timestamp is out of bounds, return error */ /* if timestamp is out of bounds, return error */
if(timestamp < 0 || timestamp >= c->fcount) if(timestamp < 0 || timestamp >= c->fcount)
return -1; return -1;
timestamp -= DELAY_FRAMES;
/* seek to the furthest known position and read packets until /* seek to the furthest known position and read packets until
we reach desired position */ we reach desired position */
lastframe = c->curframe; lastframe = c->curframe;
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment