ducatividdec: move frame reordering to the base class
[glsdk/gst-plugin-ducati.git] / src / gstducatih264dec.c
index 9b553505bcf599c3eee66ef2359767fdb43807e1..561b2f07be47871e57cfb8e22c6c5a6edec036ea 100644 (file)
@@ -179,7 +179,7 @@ gst_ducati_h264dec_query (GstDucatiVidDec * vdec, GstPad * pad,
         latency = 0;
 
       /* Take into account the backlog frames for reordering */
-      latency *= (self->backlog_maxframes + 1);
+      latency *= (vdec->backlog_maxframes + 1);
 
       if (min == GST_CLOCK_TIME_NONE)
         min = latency;
@@ -267,7 +267,6 @@ gst_ducati_h264dec_get_max_dpb_size (GstDucatiVidDec * self, GstCaps * caps)
 static gboolean
 gst_ducati_h264dec_set_sink_caps (GstDucatiVidDec * self, GstCaps * caps)
 {
-  GstDucatiH264Dec *h264dec = GST_DUCATIH264DEC (self);
   GstStructure *structure;
 
   GST_DEBUG_OBJECT (self, "set_sink_caps: %" GST_PTR_FORMAT, caps);
@@ -302,7 +301,7 @@ gst_ducati_h264dec_set_sink_caps (GstDucatiVidDec * self, GstCaps * caps)
   }
 #endif
 
-  h264dec->backlog_maxframes = -1;
+  self->backlog_maxframes = -1;
 
   structure = gst_caps_get_structure (caps, 0);
   if (structure) {
@@ -315,113 +314,29 @@ gst_ducati_h264dec_set_sink_caps (GstDucatiVidDec * self, GstCaps * caps)
             &num_reorder_frames)
         && num_reorder_frames >= 0) {
       if (num_reorder_frames > MAX_BACKLOG_FRAMES) {
-        h264dec->backlog_maxframes = MAX_BACKLOG_FRAMES;
+        self->backlog_maxframes = MAX_BACKLOG_FRAMES;
         GST_WARNING_OBJECT (self,
             "Stream needs %d frames for reordering, we can only accomodate %d",
             num_reorder_frames, MAX_BACKLOG_FRAMES);
       } else {
-        h264dec->backlog_maxframes = num_reorder_frames;
+        self->backlog_maxframes = num_reorder_frames;
         GST_INFO_OBJECT (self, "Num frames for reordering: %d",
-            h264dec->backlog_maxframes);
+            self->backlog_maxframes);
       }
     }
   }
 
   /* If not present, use the spec forumula for a bound */
-  if (h264dec->backlog_maxframes < 0) {
-    h264dec->backlog_maxframes =
-        gst_ducati_h264dec_get_max_dpb_size (self, caps);
+  if (self->backlog_maxframes < 0) {
+    self->backlog_maxframes = gst_ducati_h264dec_get_max_dpb_size (self, caps);
     GST_WARNING_OBJECT (self,
         "num-reorder-frames not found on caps, defaulting to %d",
-        h264dec->backlog_maxframes);
+        self->backlog_maxframes);
   }
 
   return TRUE;
 }
 
-/* The following few functions reorder buffers by "picture order
-   count", which is passed through OFFSET_END by h264parse.
- */
-
-static GstFlowReturn
-gst_ducati_h264dec_push_earliest (GstDucatiH264Dec * self)
-{
-  guint64 earliest_poc = G_MAXUINT64;
-  guint earliest_index = 0, i;
-  GstBuffer *buf;
-
-  if (self->backlog_nframes == 0)
-    return GST_FLOW_OK;
-
-  /* work out which frame has the earliest poc */
-  for (i = 0; i < self->backlog_nframes; i++) {
-    guint64 poc = GST_BUFFER_OFFSET_END (self->backlog_frames[i]);
-    if (earliest_poc == G_MAXUINT64 || poc < earliest_poc) {
-      earliest_poc = poc;
-      earliest_index = i;
-    }
-  }
-
-  /* send it, giving away the ref */
-  buf = self->backlog_frames[earliest_index];
-  self->backlog_frames[earliest_index] =
-      self->backlog_frames[--self->backlog_nframes];
-  GST_DEBUG_OBJECT (self, "Actually pushing backlog buffer %" GST_PTR_FORMAT,
-      buf);
-  return gst_pad_push (GST_DUCATIVIDDEC (self)->srcpad, buf);
-}
-
-static GstBuffer *
-gst_ducati_h264dec_push_input (GstDucatiVidDec * self, GstBuffer * buf)
-{
-  GstDucatiH264Dec *h264dec = GST_DUCATIH264DEC (self);
-
-  /* If we're about to push an IDR frame, then we can flush all the frames
-     we currently have queued. This is necessary as picture order count
-     is local to each IDR + set of non IDR frames, so will restart at 0
-     when next IDR frames comes in. */
-  if (!GST_BUFFER_FLAG_IS_SET (buf, GST_BUFFER_FLAG_DELTA_UNIT)) {
-    GST_DEBUG_OBJECT (self, "Got keyframe, pushing %u frames",
-        h264dec->backlog_nframes);
-    while (h264dec->backlog_nframes > 0) {
-      gst_ducati_h264dec_push_earliest (h264dec);
-    }
-  }
-
-  return parent_class->push_input (self, buf);
-}
-
-static GstFlowReturn
-gst_ducati_h264dec_push_output (GstDucatiVidDec * self, GstBuffer * buf)
-{
-  GstDucatiH264Dec *h264dec = GST_DUCATIH264DEC (self);
-  GstFlowReturn ret = GST_FLOW_OK;
-
-  /* add the frame to the list, the array will own the ref */
-  GST_DEBUG_OBJECT (self, "Adding buffer %" GST_PTR_FORMAT " to backlog", buf);
-  h264dec->backlog_frames[h264dec->backlog_nframes++] = buf;
-
-  /* push till we have no more than the max needed, or error */
-  while (h264dec->backlog_nframes > h264dec->backlog_maxframes) {
-    ret = gst_ducati_h264dec_push_earliest (h264dec);
-    if (ret != GST_FLOW_OK)
-      break;
-  }
-
-  return ret;
-}
-
-static void
-gst_ducati_h264dec_on_flush (GstDucatiVidDec * self, gboolean eos)
-{
-  GstDucatiH264Dec *h264dec = GST_DUCATIH264DEC (self);
-
-  /* push everything on the backlog, ignoring errors */
-  while (h264dec->backlog_nframes > 0) {
-    gst_ducati_h264dec_push_earliest (h264dec);
-  }
-}
-
 /* GObject vmethod implementations */
 
 static void
@@ -452,9 +367,6 @@ gst_ducati_h264dec_class_init (GstDucatiH264DecClass * klass)
   bclass->can_drop_frame =
       GST_DEBUG_FUNCPTR (gst_ducati_h264dec_can_drop_frame);
   bclass->query = GST_DEBUG_FUNCPTR (gst_ducati_h264dec_query);
-  bclass->push_input = GST_DEBUG_FUNCPTR (gst_ducati_h264dec_push_input);
-  bclass->push_output = GST_DEBUG_FUNCPTR (gst_ducati_h264dec_push_output);
-  bclass->on_flush = GST_DEBUG_FUNCPTR (gst_ducati_h264dec_on_flush);
   bclass->set_sink_caps = GST_DEBUG_FUNCPTR (gst_ducati_h264dec_set_sink_caps);
 }
 
@@ -462,6 +374,4 @@ static void
 gst_ducati_h264dec_init (GstDucatiH264Dec * self,
     GstDucatiH264DecClass * gclass)
 {
-  self->backlog_maxframes = 0;
-  self->backlog_nframes = 0;
 }