summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuis de Bethencourt <luisbg@osg.samsung.com>2016-01-15 15:56:59 +0000
committerTim-Philipp Müller <tim@centricular.com>2016-02-16 00:24:41 +0000
commit4ee6c17edbac9d65cdba600b172a593b4b40849d (patch)
tree05b0344937b10f17479eb20a0f2154e65f7ed481
parent64ca3b26d97482a9303305185a86782813631b26 (diff)
downloadgstreamer-plugins-good-4ee6c17edbac9d65cdba600b172a593b4b40849d.tar.gz
rtph265pay: add "send VPS/SPS/PPS with every key frame" mode
It's not enough to have timeout or event based VPS/SPS/PPS information sent in RTP packets. There are some scenarios when key frames may appear more frequently than once a second, in which case the minimum timeout for "config-interval" of 1 second for sending VPS/SPS/PPS isn't enough. It might also be desirable in general to make sure the VPS/SPS/PPS is available with every keyframe (packet loss aside), so receivers can actually pick up decoding immediately from the first keyframe if VPS/SPS/PPS is not signaled out of band. This commit adds the possibility to send VPS/SPS/PPS with every key frame. This mode can be enabled by setting "config-interval" property to -1. In this case the payloader will add VPS, SPS and PPS before every key (IDR) frame. https://bugzilla.gnome.org/show_bug.cgi?id=757892
-rw-r--r--gst/rtp/gstrtph265pay.c86
1 files changed, 46 insertions, 40 deletions
diff --git a/gst/rtp/gstrtph265pay.c b/gst/rtp/gstrtph265pay.c
index d72feb0f6..db8800bc6 100644
--- a/gst/rtp/gstrtph265pay.c
+++ b/gst/rtp/gstrtph265pay.c
@@ -162,7 +162,8 @@ gst_rtp_h265_pay_class_init (GstRtpH265PayClass * klass)
g_param_spec_int ("config-interval",
"VPS SPS PPS Send Interval",
"Send VPS, SPS and PPS Insertion Interval in seconds (sprop parameter sets "
- "will be multiplexed in the data stream when detected.) (0 = disabled)",
+ "will be multiplexed in the data stream when detected.) "
+ "(0 = disabled, -1 = send with every IDR frame)",
-1, 3600, DEFAULT_CONFIG_INTERVAL,
G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)
);
@@ -946,47 +947,52 @@ gst_rtp_h265_pay_payload_nal (GstRTPBasePayload * basepayload,
send_vps_sps_pps = FALSE;
/* check if we need to emit an VPS/SPS/PPS now */
- if (((nalType == GST_H265_NAL_SLICE_TRAIL_N)
- || (nalType == GST_H265_NAL_SLICE_TRAIL_R)
- || (nalType == GST_H265_NAL_SLICE_TSA_N)
- || (nalType == GST_H265_NAL_SLICE_TSA_R)
- || (nalType == GST_H265_NAL_SLICE_STSA_N)
- || (nalType == GST_H265_NAL_SLICE_STSA_R)
- || (nalType == GST_H265_NAL_SLICE_RASL_N)
- || (nalType == GST_H265_NAL_SLICE_RASL_R)
- || (nalType == GST_H265_NAL_SLICE_BLA_W_LP)
- || (nalType == GST_H265_NAL_SLICE_BLA_W_RADL)
- || (nalType == GST_H265_NAL_SLICE_BLA_N_LP)
- || (nalType == GST_H265_NAL_SLICE_IDR_W_RADL)
- || (nalType == GST_H265_NAL_SLICE_IDR_N_LP)
- || (nalType == GST_H265_NAL_SLICE_CRA_NUT))
- && rtph265pay->vps_sps_pps_interval > 0) {
-
- if (rtph265pay->last_vps_sps_pps != -1) {
- guint64 diff;
-
- GST_LOG_OBJECT (rtph265pay,
- "now %" GST_TIME_FORMAT ", last VPS/SPS/PPS %" GST_TIME_FORMAT,
- GST_TIME_ARGS (pts), GST_TIME_ARGS (rtph265pay->last_vps_sps_pps));
-
- /* calculate diff between last SPS/PPS in milliseconds */
- if (pts > rtph265pay->last_vps_sps_pps)
- diff = pts - rtph265pay->last_vps_sps_pps;
- else
- diff = 0;
-
- GST_DEBUG_OBJECT (rtph265pay,
- "interval since last VPS/SPS/PPS %" GST_TIME_FORMAT,
- GST_TIME_ARGS (diff));
-
- /* bigger than interval, queue SPS/PPS */
- if (GST_TIME_AS_SECONDS (diff) >= rtph265pay->vps_sps_pps_interval) {
- GST_DEBUG_OBJECT (rtph265pay, "time to send VPS/SPS/PPS");
+ if ((nalType == GST_H265_NAL_SLICE_TRAIL_N)
+ || (nalType == GST_H265_NAL_SLICE_TRAIL_R)
+ || (nalType == GST_H265_NAL_SLICE_TSA_N)
+ || (nalType == GST_H265_NAL_SLICE_TSA_R)
+ || (nalType == GST_H265_NAL_SLICE_STSA_N)
+ || (nalType == GST_H265_NAL_SLICE_STSA_R)
+ || (nalType == GST_H265_NAL_SLICE_RASL_N)
+ || (nalType == GST_H265_NAL_SLICE_RASL_R)
+ || (nalType == GST_H265_NAL_SLICE_BLA_W_LP)
+ || (nalType == GST_H265_NAL_SLICE_BLA_W_RADL)
+ || (nalType == GST_H265_NAL_SLICE_BLA_N_LP)
+ || (nalType == GST_H265_NAL_SLICE_IDR_W_RADL)
+ || (nalType == GST_H265_NAL_SLICE_IDR_N_LP)
+ || (nalType == GST_H265_NAL_SLICE_CRA_NUT)) {
+ if (rtph265pay->vps_sps_pps_interval > 0) {
+ if (rtph265pay->last_vps_sps_pps != -1) {
+ guint64 diff;
+
+ GST_LOG_OBJECT (rtph265pay,
+ "now %" GST_TIME_FORMAT ", last VPS/SPS/PPS %" GST_TIME_FORMAT,
+ GST_TIME_ARGS (pts), GST_TIME_ARGS (rtph265pay->last_vps_sps_pps));
+
+ /* calculate diff between last SPS/PPS in milliseconds */
+ if (pts > rtph265pay->last_vps_sps_pps)
+ diff = pts - rtph265pay->last_vps_sps_pps;
+ else
+ diff = 0;
+
+ GST_DEBUG_OBJECT (rtph265pay,
+ "interval since last VPS/SPS/PPS %" GST_TIME_FORMAT,
+ GST_TIME_ARGS (diff));
+
+ /* bigger than interval, queue SPS/PPS */
+ if (GST_TIME_AS_SECONDS (diff) >= rtph265pay->vps_sps_pps_interval) {
+ GST_DEBUG_OBJECT (rtph265pay, "time to send VPS/SPS/PPS");
+ send_vps_sps_pps = TRUE;
+ }
+ } else {
+ /* no known previous SPS/PPS time, send now */
+ GST_DEBUG_OBJECT (rtph265pay, "no previous VPS/SPS/PPS time, send now");
send_vps_sps_pps = TRUE;
}
- } else {
- /* no known previous SPS/PPS time, send now */
- GST_DEBUG_OBJECT (rtph265pay, "no previous VPS/SPS/PPS time, send now");
+ } else if (rtph265pay->vps_sps_pps_interval == -1) {
+ GST_DEBUG_OBJECT (rtph265pay,
+ "sending VPS/SPS/PPS before current IDR frame");
+ /* send VPS/SPS/PPS before every IDR frame */
send_vps_sps_pps = TRUE;
}
}