st/omx/dec: Correct the timestamping

Attach the timestamp to the dpb buffer and use that timestamp
while pushing buffer from dpb list to the omx client.

Reviewed-by: Christian König <christian.koenig@amd.com>
Signed-off-by: Nishanth Peethambaran <nishanth.peethambaran@amd.com>
Cc: "11.1 11.2" <mesa-stable@lists.freedesktop.org>
(cherry picked from commit eeb117a09d)
This commit is contained in:
Nishanth Peethambaran 2016-03-11 01:23:00 -05:00 committed by Emil Velikov
parent e097adc8b4
commit 8b4eb0f123
4 changed files with 34 additions and 8 deletions

View file

@ -419,6 +419,7 @@ static OMX_ERRORTYPE vid_dec_DecodeBuffer(omx_base_PortType *port, OMX_BUFFERHEA
priv->in_buffers[i] = buf;
priv->sizes[i] = buf->nFilledLen;
priv->inputs[i] = buf->pBuffer;
priv->timestamps[i] = buf->nTimeStamp;
while (priv->num_in_buffers > (!!(buf->nFlags & OMX_BUFFERFLAG_EOS) ? 0 : 1)) {
bool eos = !!(priv->in_buffers[0]->nFlags & OMX_BUFFERFLAG_EOS);
@ -469,6 +470,7 @@ static OMX_ERRORTYPE vid_dec_DecodeBuffer(omx_base_PortType *port, OMX_BUFFERHEA
priv->in_buffers[0] = priv->in_buffers[1];
priv->sizes[0] = priv->sizes[1] - delta;
priv->inputs[0] = priv->inputs[1] + delta;
priv->timestamps[0] = priv->timestamps[1];
}
if (r)
@ -526,9 +528,13 @@ static void vid_dec_FrameDecoded(OMX_COMPONENTTYPE *comp, OMX_BUFFERHEADERTYPE*
{
vid_dec_PrivateType *priv = comp->pComponentPrivate;
bool eos = !!(input->nFlags & OMX_BUFFERFLAG_EOS);
OMX_TICKS timestamp;
if (!input->pInputPortPrivate)
input->pInputPortPrivate = priv->Flush(priv);
if (!input->pInputPortPrivate) {
input->pInputPortPrivate = priv->Flush(priv, &timestamp);
if (timestamp != OMX_VID_DEC_TIMESTAMP_INVALID)
input->nTimeStamp = timestamp;
}
if (input->pInputPortPrivate) {
if (output->pInputPortPrivate) {
@ -539,6 +545,7 @@ static void vid_dec_FrameDecoded(OMX_COMPONENTTYPE *comp, OMX_BUFFERHEADERTYPE*
vid_dec_FillOutput(priv, input->pInputPortPrivate, output);
}
output->nFilledLen = output->nAllocLen;
output->nTimeStamp = input->nTimeStamp;
}
if (eos && input->pInputPortPrivate)

View file

@ -59,6 +59,8 @@
#define OMX_VID_DEC_AVC_NAME "OMX.mesa.video_decoder.avc"
#define OMX_VID_DEC_AVC_ROLE "video_decoder.avc"
#define OMX_VID_DEC_TIMESTAMP_INVALID ((OMX_TICKS) -1)
struct vl_vlc;
DERIVEDCLASS(vid_dec_PrivateType, omx_base_filter_PrivateType)
@ -69,7 +71,7 @@ DERIVEDCLASS(vid_dec_PrivateType, omx_base_filter_PrivateType)
struct pipe_video_codec *codec; \
void (*Decode)(vid_dec_PrivateType *priv, struct vl_vlc *vlc, unsigned min_bits_left); \
void (*EndFrame)(vid_dec_PrivateType *priv); \
struct pipe_video_buffer *(*Flush)(vid_dec_PrivateType *priv); \
struct pipe_video_buffer *(*Flush)(vid_dec_PrivateType *priv, OMX_TICKS *timestamp); \
struct pipe_video_buffer *target, *shadow; \
union { \
struct { \
@ -100,6 +102,9 @@ DERIVEDCLASS(vid_dec_PrivateType, omx_base_filter_PrivateType)
OMX_BUFFERHEADERTYPE *in_buffers[2]; \
const void *inputs[2]; \
unsigned sizes[2]; \
OMX_TICKS timestamps[2]; \
OMX_TICKS timestamp; \
bool first_buf_in_frame; \
bool frame_finished; \
bool frame_started; \
unsigned bytes_left; \

View file

@ -45,6 +45,7 @@
struct dpb_list {
struct list_head list;
struct pipe_video_buffer *buffer;
OMX_TICKS timestamp;
unsigned poc;
};
@ -82,7 +83,7 @@ static const uint8_t Default_8x8_Inter[64] = {
static void vid_dec_h264_Decode(vid_dec_PrivateType *priv, struct vl_vlc *vlc, unsigned min_bits_left);
static void vid_dec_h264_EndFrame(vid_dec_PrivateType *priv);
static struct pipe_video_buffer *vid_dec_h264_Flush(vid_dec_PrivateType *priv);
static struct pipe_video_buffer *vid_dec_h264_Flush(vid_dec_PrivateType *priv, OMX_TICKS *timestamp);
void vid_dec_h264_Init(vid_dec_PrivateType *priv)
{
@ -94,6 +95,7 @@ void vid_dec_h264_Init(vid_dec_PrivateType *priv)
LIST_INITHEAD(&priv->codec_data.h264.dpb_list);
priv->picture.h264.field_order_cnt[0] = priv->picture.h264.field_order_cnt[1] = INT_MAX;
priv->first_buf_in_frame = true;
}
static void vid_dec_h264_BeginFrame(vid_dec_PrivateType *priv)
@ -104,6 +106,9 @@ static void vid_dec_h264_BeginFrame(vid_dec_PrivateType *priv)
return;
vid_dec_NeedTarget(priv);
if (priv->first_buf_in_frame)
priv->timestamp = priv->timestamps[0];
priv->first_buf_in_frame = false;
priv->picture.h264.num_ref_frames = priv->picture.h264.pps->sps->max_num_ref_frames;
@ -127,7 +132,8 @@ static void vid_dec_h264_BeginFrame(vid_dec_PrivateType *priv)
priv->frame_started = true;
}
static struct pipe_video_buffer *vid_dec_h264_Flush(vid_dec_PrivateType *priv)
static struct pipe_video_buffer *vid_dec_h264_Flush(vid_dec_PrivateType *priv,
OMX_TICKS *timestamp)
{
struct dpb_list *entry, *result = NULL;
struct pipe_video_buffer *buf;
@ -146,6 +152,8 @@ static struct pipe_video_buffer *vid_dec_h264_Flush(vid_dec_PrivateType *priv)
return NULL;
buf = result->buffer;
if (timestamp)
*timestamp = result->timestamp;
--priv->codec_data.h264.dpb_num;
LIST_DEL(&result->list);
@ -159,6 +167,7 @@ static void vid_dec_h264_EndFrame(vid_dec_PrivateType *priv)
struct dpb_list *entry;
struct pipe_video_buffer *tmp;
bool top_field_first;
OMX_TICKS timestamp;
if (!priv->frame_started)
return;
@ -181,7 +190,9 @@ static void vid_dec_h264_EndFrame(vid_dec_PrivateType *priv)
if (!entry)
return;
priv->first_buf_in_frame = true;
entry->buffer = priv->target;
entry->timestamp = priv->timestamp;
entry->poc = MIN2(priv->picture.h264.field_order_cnt[0], priv->picture.h264.field_order_cnt[1]);
LIST_ADDTAIL(&entry->list, &priv->codec_data.h264.dpb_list);
++priv->codec_data.h264.dpb_num;
@ -192,7 +203,8 @@ static void vid_dec_h264_EndFrame(vid_dec_PrivateType *priv)
return;
tmp = priv->in_buffers[0]->pInputPortPrivate;
priv->in_buffers[0]->pInputPortPrivate = vid_dec_h264_Flush(priv);
priv->in_buffers[0]->pInputPortPrivate = vid_dec_h264_Flush(priv, &timestamp);
priv->in_buffers[0]->nTimeStamp = timestamp;
priv->target = tmp;
priv->frame_finished = priv->in_buffers[0]->pInputPortPrivate != NULL;
}

View file

@ -61,7 +61,7 @@ static uint8_t default_non_intra_matrix[64] = {
static void vid_dec_mpeg12_Decode(vid_dec_PrivateType *priv, struct vl_vlc *vlc, unsigned min_bits_left);
static void vid_dec_mpeg12_EndFrame(vid_dec_PrivateType *priv);
static struct pipe_video_buffer *vid_dec_mpeg12_Flush(vid_dec_PrivateType *priv);
static struct pipe_video_buffer *vid_dec_mpeg12_Flush(vid_dec_PrivateType *priv, OMX_TICKS *timestamp);
void vid_dec_mpeg12_Init(vid_dec_PrivateType *priv)
{
@ -131,10 +131,12 @@ static void vid_dec_mpeg12_EndFrame(vid_dec_PrivateType *priv)
priv->in_buffers[0]->pInputPortPrivate = done;
}
static struct pipe_video_buffer *vid_dec_mpeg12_Flush(vid_dec_PrivateType *priv)
static struct pipe_video_buffer *vid_dec_mpeg12_Flush(vid_dec_PrivateType *priv, OMX_TICKS *timestamp)
{
struct pipe_video_buffer *result = priv->picture.mpeg12.ref[1];
priv->picture.mpeg12.ref[1] = NULL;
if (timestamp)
*timestamp = OMX_VID_DEC_TIMESTAMP_INVALID;
return result;
}