diff --git a/src/gstducatividdec.h b/src/gstducatividdec.h
index a9ddd45112dc15c0d250d20545c3d83726287e74..19a9b335249d680e7d86d8170a9d100f8705c1b7 100644 (file)
--- a/src/gstducatividdec.h
+++ b/src/gstducatividdec.h
#ifndef __GST_DUCATIVIDDEC_H__
#define __GST_DUCATIVIDDEC_H__
+#include <stdint.h>
+#include <stddef.h>
+#include <omap_drm.h>
+#include <omap_drmif.h>
+
#include "gstducati.h"
-#include "gstducatibufferpool.h"
+#include "gstducatibufferpriv.h"
+#include <gst/drm/gstdrmbufferpool.h>
#include <gst/video/video.h>
+#include <gst/video/video-crop.h>
G_BEGIN_DECLS
-
#define GST_TYPE_DUCATIVIDDEC (gst_ducati_viddec_get_type())
#define GST_DUCATIVIDDEC(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), GST_TYPE_DUCATIVIDDEC, GstDucatiVidDec))
#define GST_DUCATIVIDDEC_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), GST_TYPE_DUCATIVIDDEC, GstDucatiVidDecClass))
typedef struct _GstDucatiVidDec GstDucatiVidDec;
typedef struct _GstDucatiVidDecClass GstDucatiVidDecClass;
+#define MAX_BACKLOG_FRAMES 16
+
struct _GstDucatiVidDec
{
GstElement parent;
GstPad *sinkpad, *srcpad;
- GstDucatiBufferPool *pool;
+ GstDRMBufferPool *pool;
/* minimum output size required by the codec: */
gint outsize;
/* minimum number of buffers required by the codec: */
gint min_buffers;
- /* input (unpadded) size of video: */
+ /* input (unpadded, unaligned) size of video: */
+ gint input_width, input_height;
+
+ /* input (unpadded, aligned to MB) size of video: */
gint width, height;
+ gint fps_n, fps_d;
+
/* output (padded) size including any codec padding: */
gint padded_width, padded_height;
/* output stride (>= padded_width) */
gint stride;
+ gboolean interlaced;
+
+ struct omap_bo *input_bo;
/* input buffer, allocated when codec is created: */
guint8 *input;
/* number of bytes pushed to input on current frame: */
gint in_size;
+ /* the crop to attach to output buffers: */
+ GstVideoCrop *crop;
+
/* on first output buffer, we need to send crop info to sink.. and some
* operations like flushing should be avoided if we haven't sent any
* input buffers:
*/
gboolean first_out_buffer, first_in_buffer;
+ gboolean send_crop_event;
+
+ GstSegment segment;
+ gdouble qos_proportion;
+ GstClockTime qos_earliest_time;
+
+ gboolean need_out_buf;
/* by default, codec_data from sinkpad is prepended to first buffer: */
GstBuffer *codec_data;
+ /* workaround enabled to indicate that timestamp from demuxer is PTS,
+ * not DTS (cough, cough.. avi):
+ */
+ gboolean ts_is_pts;
+
+ /* auto-detection for ts_is_pts workaround.. if we detect out of order
+ * timestamps from demuxer/parser, then the ts is definitely DTS,
+ * otherwise it may be PTS and out of order timestamps out of decoder
+ * will trigger the ts_is_pts workaround.
+ */
+ gboolean ts_may_be_pts;
+
+ gboolean wait_keyframe;
+
+ gboolean needs_flushing;
+
+ GHashTable *passed_in_bufs;
+
+#define NDTS 32
+ GstClockTime dts_queue[NDTS];
+ gint dts_ridx, dts_widx;
+ GstClockTime last_dts, last_pts;
+
Engine_Handle engine;
VIDDEC3_Handle codec;
VIDDEC3_Params *params;
VIDDEC3_OutArgs *outArgs;
XDAS_Int16 pageMemType;
+ struct omap_device *device;
+
+ /* Frames waiting to be reordered */
+ GstBuffer *backlog_frames[MAX_BACKLOG_FRAMES + 1];
+ gint backlog_maxframes;
+ gint backlog_nframes;
+ gint backlog_max_maxframes;
};
struct _GstDucatiVidDecClass
* any remaining data, or NULL if none. Consumes reference to 'buf'
*/
GstBuffer * (*push_input) (GstDucatiVidDec * self, GstBuffer * buf);
+
+ /**
+ * Called to handle errors returned by VIDDEC3_process.
+ */
+ gint (*handle_error) (GstDucatiVidDec * self, gint ret, gint extended_error,
+ gint status_extended_error);
+
+ /**
+ * Called to check whether it's a good idea to drop buf or not.
+ */
+ gboolean (*can_drop_frame) (GstDucatiVidDec * self, GstBuffer * buf, gint64 diff);
+
+ gboolean (*query) (GstDucatiVidDec * self, GstPad * pad, GstQuery * query,
+ gboolean * forward);
+
+ /**
+ * Called to push a decoder buffer. Consumes reference to 'buf'.
+ */
+ GstFlowReturn (*push_output) (GstDucatiVidDec * self, GstBuffer * buf);
+
+ /**
+ * Called before a flush happens.
+ */
+ void (*on_flush) (GstDucatiVidDec * self, gboolean eos);
+
+ /**
+ * Called to set new caps on the sink pad.
+ */
+ gboolean (*set_sink_caps) (GstDucatiVidDec * self, GstCaps *caps);
};
GType gst_ducati_viddec_get_type (void);
/* helper methods for derived classes: */
static inline void
-push_input (GstDucatiVidDec * self, guint8 *in, gint sz)
+push_input (GstDucatiVidDec * self, const guint8 *in, gint sz)
{
GST_DEBUG_OBJECT (self, "push: %d bytes)", sz);
memcpy (self->input + self->in_size, in, sz);
self->in_size += sz;
}
+static inline int
+check_start_code (const guint8 *sc, gint scsize,
+ const guint8 *inbuf, gint insize)
+{
+ if (insize < scsize)
+ return FALSE;
+
+ while (scsize) {
+ if (*sc != *inbuf)
+ return FALSE;
+ scsize--;
+ sc++;
+ inbuf++;
+ }
+
+ return TRUE;
+}
+
+static inline int
+find_start_code (const guint8 *sc, gint scsize,
+ const guint8 *inbuf, gint insize)
+{
+ gint size = 0;
+ while (insize) {
+ if (check_start_code (sc, scsize, inbuf, insize))
+ break;
+ insize--;
+ size++;
+ inbuf++;
+ }
+ return size;
+}
+
+gboolean
+gst_ducati_viddec_codec_flush (GstDucatiVidDec * self, gboolean eos);
+
G_END_DECLS
#endif /* __GST_DUCATIVIDDEC_H__ */