mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-10-22 02:13:46 +00:00
gst-libs/gst/rtp/gstbasertpdepayload.c: Remove code to deal with RTP to GST time conversion, we now just copy the GST...
Original commit message from CVS: * gst-libs/gst/rtp/gstbasertpdepayload.c: (gst_base_rtp_depayload_init), (gst_base_rtp_depayload_setcaps), (gst_base_rtp_depayload_chain), (gst_base_rtp_depayload_handle_sink_event), (gst_base_rtp_depayload_push_full), (gst_base_rtp_depayload_set_gst_timestamp), (gst_base_rtp_depayload_change_state): Remove code to deal with RTP to GST time conversion, we now just copy the GST timestamp we receive to the outgoing buffers. Handle segment and flushes correctly. * gst-libs/gst/rtp/gstbasertppayload.c: (gst_basertppayload_push): When we have no valid input timestamp, use the previous rtp timestamp on the outgoing RTP packet instead of the RTP base time.
This commit is contained in:
parent
1beb98e6dc
commit
523fd097e6
3 changed files with 74 additions and 87 deletions
17
ChangeLog
17
ChangeLog
|
@ -1,3 +1,20 @@
|
||||||
|
2007-09-16 Wim Taymans <wim.taymans@gmail.com>
|
||||||
|
|
||||||
|
* gst-libs/gst/rtp/gstbasertpdepayload.c:
|
||||||
|
(gst_base_rtp_depayload_init), (gst_base_rtp_depayload_setcaps),
|
||||||
|
(gst_base_rtp_depayload_chain),
|
||||||
|
(gst_base_rtp_depayload_handle_sink_event),
|
||||||
|
(gst_base_rtp_depayload_push_full),
|
||||||
|
(gst_base_rtp_depayload_set_gst_timestamp),
|
||||||
|
(gst_base_rtp_depayload_change_state):
|
||||||
|
Remove code to deal with RTP to GST time conversion, we now just copy
|
||||||
|
the GST timestamp we receive to the outgoing buffers.
|
||||||
|
Handle segment and flushes correctly.
|
||||||
|
|
||||||
|
* gst-libs/gst/rtp/gstbasertppayload.c: (gst_basertppayload_push):
|
||||||
|
When we have no valid input timestamp, use the previous rtp timestamp on
|
||||||
|
the outgoing RTP packet instead of the RTP base time.
|
||||||
|
|
||||||
2007-09-15 David Schleef <ds@schleef.org>
|
2007-09-15 David Schleef <ds@schleef.org>
|
||||||
|
|
||||||
* ext/alsa/gstalsa.c:
|
* ext/alsa/gstalsa.c:
|
||||||
|
|
|
@ -48,16 +48,13 @@ GST_DEBUG_CATEGORY_STATIC (basertpdepayload_debug);
|
||||||
|
|
||||||
struct _GstBaseRTPDepayloadPrivate
|
struct _GstBaseRTPDepayloadPrivate
|
||||||
{
|
{
|
||||||
guint64 clock_base;
|
|
||||||
|
|
||||||
GstClockTime npt_start;
|
GstClockTime npt_start;
|
||||||
GstClockTime npt_stop;
|
GstClockTime npt_stop;
|
||||||
gdouble play_speed;
|
gdouble play_speed;
|
||||||
gdouble play_scale;
|
gdouble play_scale;
|
||||||
|
|
||||||
GstClockTime exttimestamp;
|
|
||||||
|
|
||||||
gboolean discont;
|
gboolean discont;
|
||||||
|
GstClockTime timestamp;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Filter signals and args */
|
/* Filter signals and args */
|
||||||
|
@ -91,7 +88,7 @@ static GstStateChangeReturn gst_base_rtp_depayload_change_state (GstElement *
|
||||||
element, GstStateChange transition);
|
element, GstStateChange transition);
|
||||||
|
|
||||||
static void gst_base_rtp_depayload_set_gst_timestamp
|
static void gst_base_rtp_depayload_set_gst_timestamp
|
||||||
(GstBaseRTPDepayload * filter, guint32 timestamp, GstBuffer * buf);
|
(GstBaseRTPDepayload * filter, guint32 rtptime, GstBuffer * buf);
|
||||||
|
|
||||||
GST_BOILERPLATE (GstBaseRTPDepayload, gst_base_rtp_depayload, GstElement,
|
GST_BOILERPLATE (GstBaseRTPDepayload, gst_base_rtp_depayload, GstElement,
|
||||||
GST_TYPE_ELEMENT);
|
GST_TYPE_ELEMENT);
|
||||||
|
@ -171,6 +168,8 @@ gst_base_rtp_depayload_init (GstBaseRTPDepayload * filter,
|
||||||
|
|
||||||
filter->queue = g_queue_new ();
|
filter->queue = g_queue_new ();
|
||||||
filter->queue_delay = DEFAULT_QUEUE_DELAY;
|
filter->queue_delay = DEFAULT_QUEUE_DELAY;
|
||||||
|
|
||||||
|
gst_segment_init (&filter->segment, GST_FORMAT_UNDEFINED);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -192,7 +191,6 @@ gst_base_rtp_depayload_setcaps (GstPad * pad, GstCaps * caps)
|
||||||
gboolean res;
|
gboolean res;
|
||||||
GstStructure *caps_struct;
|
GstStructure *caps_struct;
|
||||||
const GValue *value;
|
const GValue *value;
|
||||||
guint val;
|
|
||||||
|
|
||||||
filter = GST_BASE_RTP_DEPAYLOAD (gst_pad_get_parent (pad));
|
filter = GST_BASE_RTP_DEPAYLOAD (gst_pad_get_parent (pad));
|
||||||
priv = filter->priv;
|
priv = filter->priv;
|
||||||
|
@ -203,18 +201,13 @@ gst_base_rtp_depayload_setcaps (GstPad * pad, GstCaps * caps)
|
||||||
|
|
||||||
caps_struct = gst_caps_get_structure (caps, 0);
|
caps_struct = gst_caps_get_structure (caps, 0);
|
||||||
|
|
||||||
/* get clock base if any, we need this for the newsegment */
|
|
||||||
if (gst_structure_get_uint (caps_struct, "clock-base", &val))
|
|
||||||
priv->clock_base = val;
|
|
||||||
else
|
|
||||||
priv->clock_base = -1;
|
|
||||||
|
|
||||||
/* get other values for newsegment */
|
/* get other values for newsegment */
|
||||||
value = gst_structure_get_value (caps_struct, "npt-start");
|
value = gst_structure_get_value (caps_struct, "npt-start");
|
||||||
if (value && G_VALUE_HOLDS_UINT64 (value))
|
if (value && G_VALUE_HOLDS_UINT64 (value))
|
||||||
priv->npt_start = g_value_get_uint64 (value);
|
priv->npt_start = g_value_get_uint64 (value);
|
||||||
else
|
else
|
||||||
priv->npt_start = 0;
|
priv->npt_start = 0;
|
||||||
|
GST_DEBUG_OBJECT (filter, "NTP start %" G_GUINT64_FORMAT, priv->npt_start);
|
||||||
|
|
||||||
value = gst_structure_get_value (caps_struct, "npt-stop");
|
value = gst_structure_get_value (caps_struct, "npt-stop");
|
||||||
if (value && G_VALUE_HOLDS_UINT64 (value))
|
if (value && G_VALUE_HOLDS_UINT64 (value))
|
||||||
|
@ -222,6 +215,8 @@ gst_base_rtp_depayload_setcaps (GstPad * pad, GstCaps * caps)
|
||||||
else
|
else
|
||||||
priv->npt_stop = -1;
|
priv->npt_stop = -1;
|
||||||
|
|
||||||
|
GST_DEBUG_OBJECT (filter, "NTP stop %" G_GUINT64_FORMAT, priv->npt_start);
|
||||||
|
|
||||||
value = gst_structure_get_value (caps_struct, "play-speed");
|
value = gst_structure_get_value (caps_struct, "play-speed");
|
||||||
if (value && G_VALUE_HOLDS_DOUBLE (value))
|
if (value && G_VALUE_HOLDS_DOUBLE (value))
|
||||||
priv->play_speed = g_value_get_double (value);
|
priv->play_speed = g_value_get_double (value);
|
||||||
|
@ -234,8 +229,6 @@ gst_base_rtp_depayload_setcaps (GstPad * pad, GstCaps * caps)
|
||||||
else
|
else
|
||||||
priv->play_scale = 1.0;
|
priv->play_scale = 1.0;
|
||||||
|
|
||||||
priv->exttimestamp = -1;
|
|
||||||
|
|
||||||
if (bclass->set_caps)
|
if (bclass->set_caps)
|
||||||
res = bclass->set_caps (filter, caps);
|
res = bclass->set_caps (filter, caps);
|
||||||
else
|
else
|
||||||
|
@ -254,65 +247,70 @@ gst_base_rtp_depayload_chain (GstPad * pad, GstBuffer * in)
|
||||||
GstBaseRTPDepayloadClass *bclass;
|
GstBaseRTPDepayloadClass *bclass;
|
||||||
GstFlowReturn ret = GST_FLOW_OK;
|
GstFlowReturn ret = GST_FLOW_OK;
|
||||||
GstBuffer *out_buf;
|
GstBuffer *out_buf;
|
||||||
|
GstClockTime timestamp;
|
||||||
|
|
||||||
filter = GST_BASE_RTP_DEPAYLOAD (GST_OBJECT_PARENT (pad));
|
filter = GST_BASE_RTP_DEPAYLOAD (GST_OBJECT_PARENT (pad));
|
||||||
|
|
||||||
if (filter->clock_rate == 0)
|
|
||||||
goto not_configured;
|
|
||||||
|
|
||||||
priv = filter->priv;
|
priv = filter->priv;
|
||||||
priv->discont = GST_BUFFER_IS_DISCONT (in);
|
priv->discont = GST_BUFFER_IS_DISCONT (in);
|
||||||
|
|
||||||
|
/* convert to running_time and save the timestamp, this is the timestamp
|
||||||
|
* we put on outgoing buffers. */
|
||||||
|
timestamp = GST_BUFFER_TIMESTAMP (in);
|
||||||
|
timestamp = gst_segment_to_running_time (&filter->segment, GST_FORMAT_TIME,
|
||||||
|
timestamp);
|
||||||
|
priv->timestamp = timestamp;
|
||||||
|
|
||||||
bclass = GST_BASE_RTP_DEPAYLOAD_GET_CLASS (filter);
|
bclass = GST_BASE_RTP_DEPAYLOAD_GET_CLASS (filter);
|
||||||
|
|
||||||
/* let's send it out to processing */
|
/* let's send it out to processing */
|
||||||
out_buf = bclass->process (filter, in);
|
out_buf = bclass->process (filter, in);
|
||||||
if (out_buf) {
|
if (out_buf) {
|
||||||
guint32 timestamp;
|
guint32 rtptime;
|
||||||
|
|
||||||
timestamp = gst_rtp_buffer_get_timestamp (in);
|
rtptime = gst_rtp_buffer_get_timestamp (in);
|
||||||
|
|
||||||
/* push buffer with timestamp
|
/* we pass rtptime as backward compatibility, in reality, the incomming
|
||||||
* We are assuming here that the timestamp of the last RTP buffer
|
* buffer timestamp is always applied to the outgoing packet. */
|
||||||
* is the same as the timestamp wanted on the collector. If this is not a
|
ret = gst_base_rtp_depayload_push_ts (filter, rtptime, out_buf);
|
||||||
* desired result, the process function should push itself with another
|
|
||||||
* timestamp and return NULL.
|
|
||||||
*/
|
|
||||||
ret = gst_base_rtp_depayload_push_ts (filter, timestamp, out_buf);
|
|
||||||
}
|
}
|
||||||
gst_buffer_unref (in);
|
gst_buffer_unref (in);
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
/* ERRORS */
|
|
||||||
not_configured:
|
|
||||||
{
|
|
||||||
GST_ELEMENT_ERROR (filter, STREAM, FORMAT,
|
|
||||||
(NULL), ("no clock rate was specified, likely incomplete input caps"));
|
|
||||||
gst_buffer_unref (in);
|
|
||||||
return GST_FLOW_NOT_NEGOTIATED;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
gst_base_rtp_depayload_handle_sink_event (GstPad * pad, GstEvent * event)
|
gst_base_rtp_depayload_handle_sink_event (GstPad * pad, GstEvent * event)
|
||||||
{
|
{
|
||||||
GstBaseRTPDepayload *filter =
|
GstBaseRTPDepayload *filter;
|
||||||
GST_BASE_RTP_DEPAYLOAD (GST_OBJECT_PARENT (pad));
|
|
||||||
gboolean res = TRUE;
|
gboolean res = TRUE;
|
||||||
|
|
||||||
|
filter = GST_BASE_RTP_DEPAYLOAD (GST_OBJECT_PARENT (pad));
|
||||||
|
|
||||||
switch (GST_EVENT_TYPE (event)) {
|
switch (GST_EVENT_TYPE (event)) {
|
||||||
|
case GST_EVENT_FLUSH_STOP:
|
||||||
|
res = gst_pad_push_event (filter->srcpad, event);
|
||||||
|
|
||||||
|
gst_segment_init (&filter->segment, GST_FORMAT_UNDEFINED);
|
||||||
|
filter->need_newsegment = TRUE;
|
||||||
|
break;
|
||||||
case GST_EVENT_NEWSEGMENT:
|
case GST_EVENT_NEWSEGMENT:
|
||||||
{
|
{
|
||||||
GstFormat format;
|
gboolean update;
|
||||||
|
gdouble rate;
|
||||||
|
GstFormat fmt;
|
||||||
|
gint64 start, stop, position;
|
||||||
|
|
||||||
gst_event_parse_new_segment (event, NULL, NULL, &format, NULL, NULL,
|
gst_event_parse_new_segment (event, &update, &rate, &fmt, &start, &stop,
|
||||||
NULL);
|
&position);
|
||||||
if (format != GST_FORMAT_TIME)
|
|
||||||
goto wrong_format;
|
|
||||||
|
|
||||||
GST_DEBUG_OBJECT (filter, "Upstream sent a NEWSEGMENT, passing through.");
|
gst_segment_set_newsegment (&filter->segment, update, rate, fmt,
|
||||||
/* fallthrough */
|
start, stop, position);
|
||||||
|
|
||||||
|
/* don't pass the event downstream, we generate our own segment including
|
||||||
|
* the NTP time and other things we receive in caps */
|
||||||
|
gst_event_unref (event);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
/* pass other events forward */
|
/* pass other events forward */
|
||||||
|
@ -320,20 +318,11 @@ gst_base_rtp_depayload_handle_sink_event (GstPad * pad, GstEvent * event)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
|
|
||||||
/* ERRORS */
|
|
||||||
wrong_format:
|
|
||||||
{
|
|
||||||
GST_DEBUG_OBJECT (filter,
|
|
||||||
"Upstream sent a NEWSEGMENT in wrong format, dropping.");
|
|
||||||
gst_event_unref (event);
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static GstFlowReturn
|
static GstFlowReturn
|
||||||
gst_base_rtp_depayload_push_full (GstBaseRTPDepayload * filter,
|
gst_base_rtp_depayload_push_full (GstBaseRTPDepayload * filter,
|
||||||
gboolean do_ts, guint32 timestamp, GstBuffer * out_buf)
|
gboolean do_ts, guint32 rtptime, GstBuffer * out_buf)
|
||||||
{
|
{
|
||||||
GstFlowReturn ret;
|
GstFlowReturn ret;
|
||||||
GstCaps *srccaps;
|
GstCaps *srccaps;
|
||||||
|
@ -351,7 +340,7 @@ gst_base_rtp_depayload_push_full (GstBaseRTPDepayload * filter,
|
||||||
|
|
||||||
/* set the timestamp if we must and can */
|
/* set the timestamp if we must and can */
|
||||||
if (bclass->set_gst_timestamp && do_ts)
|
if (bclass->set_gst_timestamp && do_ts)
|
||||||
bclass->set_gst_timestamp (filter, timestamp, out_buf);
|
bclass->set_gst_timestamp (filter, rtptime, out_buf);
|
||||||
|
|
||||||
if (priv->discont) {
|
if (priv->discont) {
|
||||||
GST_BUFFER_FLAG_SET (out_buf, GST_BUFFER_FLAG_DISCONT);
|
GST_BUFFER_FLAG_SET (out_buf, GST_BUFFER_FLAG_DISCONT);
|
||||||
|
@ -411,39 +400,14 @@ gst_base_rtp_depayload_push (GstBaseRTPDepayload * filter, GstBuffer * out_buf)
|
||||||
|
|
||||||
static void
|
static void
|
||||||
gst_base_rtp_depayload_set_gst_timestamp (GstBaseRTPDepayload * filter,
|
gst_base_rtp_depayload_set_gst_timestamp (GstBaseRTPDepayload * filter,
|
||||||
guint32 timestamp, GstBuffer * buf)
|
guint32 rtptime, GstBuffer * buf)
|
||||||
{
|
{
|
||||||
GstClockTime ts, exttimestamp;
|
|
||||||
GstBaseRTPDepayloadPrivate *priv;
|
GstBaseRTPDepayloadPrivate *priv;
|
||||||
|
|
||||||
priv = filter->priv;
|
priv = filter->priv;
|
||||||
|
|
||||||
/* no clock-base set, take first timestamp as base */
|
/* apply incomming timestamp to outgoing buffer */
|
||||||
if (priv->clock_base == -1)
|
GST_BUFFER_TIMESTAMP (buf) = priv->timestamp;
|
||||||
priv->clock_base = timestamp;
|
|
||||||
|
|
||||||
/* get extended timestamp */
|
|
||||||
exttimestamp = gst_rtp_buffer_ext_timestamp (&priv->exttimestamp, timestamp);
|
|
||||||
|
|
||||||
/* subtract clock-base to get a 0 based timestamp. Make sure we don't go
|
|
||||||
* negative. */
|
|
||||||
if (exttimestamp > priv->clock_base)
|
|
||||||
exttimestamp -= priv->clock_base;
|
|
||||||
else
|
|
||||||
exttimestamp = 0;
|
|
||||||
|
|
||||||
/* rtp timestamps are based on the clock_rate
|
|
||||||
* gst timesamps are in nanoseconds */
|
|
||||||
ts = gst_util_uint64_scale_int (exttimestamp, GST_SECOND, filter->clock_rate);
|
|
||||||
|
|
||||||
GST_DEBUG_OBJECT (filter,
|
|
||||||
"timestamp: %u, exttimestamp %" G_GUINT64_FORMAT ", clockrate : %u",
|
|
||||||
timestamp, exttimestamp, filter->clock_rate);
|
|
||||||
|
|
||||||
GST_DEBUG_OBJECT (filter, "RTP: %u, GST: %" GST_TIME_FORMAT ", ts %"
|
|
||||||
GST_TIME_FORMAT, timestamp, GST_TIME_ARGS (ts), GST_TIME_ARGS (ts));
|
|
||||||
|
|
||||||
GST_BUFFER_TIMESTAMP (buf) = ts;
|
|
||||||
|
|
||||||
/* if this is the first buffer send a NEWSEGMENT */
|
/* if this is the first buffer send a NEWSEGMENT */
|
||||||
if (filter->need_newsegment) {
|
if (filter->need_newsegment) {
|
||||||
|
@ -473,19 +437,21 @@ gst_base_rtp_depayload_change_state (GstElement * element,
|
||||||
GstStateChange transition)
|
GstStateChange transition)
|
||||||
{
|
{
|
||||||
GstBaseRTPDepayload *filter;
|
GstBaseRTPDepayload *filter;
|
||||||
|
GstBaseRTPDepayloadPrivate *priv;
|
||||||
GstStateChangeReturn ret;
|
GstStateChangeReturn ret;
|
||||||
|
|
||||||
filter = GST_BASE_RTP_DEPAYLOAD (element);
|
filter = GST_BASE_RTP_DEPAYLOAD (element);
|
||||||
|
priv = filter->priv;
|
||||||
|
|
||||||
switch (transition) {
|
switch (transition) {
|
||||||
case GST_STATE_CHANGE_NULL_TO_READY:
|
case GST_STATE_CHANGE_NULL_TO_READY:
|
||||||
break;
|
break;
|
||||||
case GST_STATE_CHANGE_READY_TO_PAUSED:
|
case GST_STATE_CHANGE_READY_TO_PAUSED:
|
||||||
/* clock_rate needs to be overwritten by child */
|
|
||||||
filter->clock_rate = 0;
|
|
||||||
filter->priv->clock_base = -1;
|
|
||||||
filter->priv->exttimestamp = -1;
|
|
||||||
filter->need_newsegment = TRUE;
|
filter->need_newsegment = TRUE;
|
||||||
|
priv->npt_start = 0;
|
||||||
|
priv->npt_stop = -1;
|
||||||
|
priv->play_speed = 1.0;
|
||||||
|
priv->play_scale = 1.0;
|
||||||
break;
|
break;
|
||||||
case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
|
case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
|
||||||
break;
|
break;
|
||||||
|
|
|
@ -649,7 +649,11 @@ gst_basertppayload_push (GstBaseRTPPayload * payload, GstBuffer * buffer)
|
||||||
|
|
||||||
rtime = gst_util_uint64_scale_int (rtime, payload->clock_rate, GST_SECOND);
|
rtime = gst_util_uint64_scale_int (rtime, payload->clock_rate, GST_SECOND);
|
||||||
|
|
||||||
|
/* add running_time in clock-rate units to the base timestamp */
|
||||||
rtptime += rtime;
|
rtptime += rtime;
|
||||||
|
} else {
|
||||||
|
/* no timestamp to convert, take previous timestamp */
|
||||||
|
rtptime = payload->timestamp;
|
||||||
}
|
}
|
||||||
gst_rtp_buffer_set_timestamp (buffer, rtptime);
|
gst_rtp_buffer_set_timestamp (buffer, rtptime);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue