mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-23 18:21:04 +00:00
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
This commit is contained in:
parent
31a7ad77b6
commit
6f8f82164a
1 changed files with 42 additions and 36 deletions
|
@ -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 ((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;
|
||||
|
||||
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));
|
||||
|
||||
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;
|
||||
|
||||
/* 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));
|
||||
|
||||
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");
|
||||
/* 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;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue