From fa393e5d60bcb61ba0e48905b19a3b76847d31ee Mon Sep 17 00:00:00 2001 From: Sebastian Rasmussen Date: Thu, 16 Jan 2014 21:49:59 +0100 Subject: [PATCH] rtpbasepayload: Add statistics property This property allows for an atomically retrieved set of properties that can e.g. be used to generate RTP-Info headers. Fixes https://bugzilla.gnome.org/show_bug.cgi?id=719415 --- gst-libs/gst/rtp/gstrtpbasepayload.c | 50 +++++++++++++++++++++++++++ tests/check/libs/rtp-basepayloading.c | 24 +++++++++++++ 2 files changed, 74 insertions(+) diff --git a/gst-libs/gst/rtp/gstrtpbasepayload.c b/gst-libs/gst/rtp/gstrtpbasepayload.c index c6706b7175..5052adb323 100644 --- a/gst-libs/gst/rtp/gstrtpbasepayload.c +++ b/gst-libs/gst/rtp/gstrtpbasepayload.c @@ -93,6 +93,7 @@ enum PROP_SEQNUM, PROP_PERFECT_RTPTIME, PROP_PTIME_MULTIPLE, + PROP_STATS, PROP_LAST }; @@ -243,6 +244,37 @@ gst_rtp_base_payload_class_init (GstRTPBasePayloadClass * klass) 0, G_MAXINT64, DEFAULT_PTIME_MULTIPLE, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); + /** + * GstRTPBasePayload:stats: + * + * Various payloader statistics retrieved atomically (and are therefore + * synchroized with each other), these can be used e.g. to generate an + * RTP-Info header. This property return a GstStructure named + * application/x-rtp-payload-stats containing the following fields relating to + * the last processed buffer and current state of the stream being payloaded: + * + * + * + * clock-rate + * #G_TYPE_UINT, clock-rate of the + * stream + * + * + * seqnum + * #G_TYPE_UINT, sequence number, same as + * #GstRTPBasePayload:seqnum + * + * + * timestamp + * #G_TYPE_UINT, RTP timestamp, same as + * #GstRTPBasePayload:timestamp + * + * + **/ + g_object_class_install_property (G_OBJECT_CLASS (klass), PROP_STATS, + g_param_spec_boxed ("stats", "Statistics", "Various statistics", + GST_TYPE_STRUCTURE, G_PARAM_READABLE | G_PARAM_STATIC_STRINGS)); + gstelement_class->change_state = gst_rtp_base_payload_change_state; klass->get_caps = gst_rtp_base_payload_getcaps_default; @@ -1051,6 +1083,20 @@ gst_rtp_base_payload_push (GstRTPBasePayload * payload, GstBuffer * buffer) return res; } +static GstStructure * +gst_rtp_base_payload_create_stats (GstRTPBasePayload *rtpbasepayload) +{ + GstStructure *s; + + s = gst_structure_new ("application/x-rtp-payload-stats", + "clock-rate", G_TYPE_UINT, rtpbasepayload->clock_rate, + "seqnum", G_TYPE_UINT, rtpbasepayload->seqnum, + "timestamp", G_TYPE_UINT, rtpbasepayload->timestamp, + NULL); + + return s; +} + static void gst_rtp_base_payload_set_property (GObject * object, guint prop_id, const GValue * value, GParamSpec * pspec) @@ -1158,6 +1204,10 @@ gst_rtp_base_payload_get_property (GObject * object, guint prop_id, case PROP_PTIME_MULTIPLE: g_value_set_int64 (value, rtpbasepayload->ptime_multiple); break; + case PROP_STATS: + g_value_take_boxed (value, + gst_rtp_base_payload_create_stats (rtpbasepayload)); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; diff --git a/tests/check/libs/rtp-basepayloading.c b/tests/check/libs/rtp-basepayloading.c index 0225ac1a1d..c3c6c94f9c 100644 --- a/tests/check/libs/rtp-basepayloading.c +++ b/tests/check/libs/rtp-basepayloading.c @@ -310,6 +310,11 @@ GST_START_TEST (rtp_base_test) GMainLoop *mainloop; GstBus *bus; GstCaps *caps; + GstStructure *stats; + guint clock_rate; + guint seqnum; + guint timestamp; + GObjectClass *klass; pipeline = gst_pipeline_new (NULL); fail_unless (GST_IS_PIPELINE (pipeline)); @@ -330,6 +335,8 @@ GST_START_TEST (rtp_base_test) GST_FORMAT_TIME, NULL); gst_caps_unref (caps); + g_object_set (pay, "seqnum-offset", 0, "timestamp-offset", 0, NULL); + g_object_set (sink, "sync", FALSE, "emit-signals", TRUE, NULL); gst_bin_add_many (GST_BIN (pipeline), src, pay, depay, sink, NULL); @@ -357,6 +364,23 @@ GST_START_TEST (rtp_base_test) push_buffer (src, 1 * GST_SECOND); await_buffer (sink, 1 * GST_SECOND); + klass = G_OBJECT_GET_CLASS (pay); + fail_unless (g_object_class_find_property (klass, "stats") != NULL); + + g_object_get (pay, "stats", &stats, NULL); + + fail_unless (gst_structure_has_field (stats, "clock-rate")); + fail_unless (gst_structure_has_field (stats, "seqnum")); + fail_unless (gst_structure_has_field (stats, "timestamp")); + + fail_unless (gst_structure_get_uint (stats, "clock-rate", &clock_rate)); + fail_unless (gst_structure_get_uint (stats, "seqnum", &seqnum)); + fail_unless (gst_structure_get_uint (stats, "timestamp", ×tamp)); + + fail_unless_equals_int (clock_rate, 42); + fail_unless_equals_int (seqnum, 1); + fail_unless_equals_int (timestamp, 42); + push_eos (src); await_eos (sink);