mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-01-23 15:48:23 +00:00
rtcpbuffer: add support XR packet parsing
According to RFC3611, the extended report blocks in XR packet can have variable length. To visit each block, the iterator should look into block header. Once XR type is extracted, users can parse the detailed information by given functions. Loss/Duplicate RLE The Loss RLE and the Duplicate RLE have same format so they can share parsers. For unit test, randomly generated pseudo packet is used. Packet Receipt Times The packet receipt times report block has a list of receipt times which are in [begin_seq, end_seq). Receiver Reference Time paser for XR packet The receiver reference time has ntptime which is 64 bit type. DLRR The DLRR report block consists of sub-blocks which has ssrc, last RR, and delay since last RR. The number of sub-blocks should be calculated from block length. Statistics Summary The Statistics Summary report block provides fixed length information. VoIP Metrics VoIP Metrics consists of several metrics even though they are in a report block. Data retrieving functions are added per metrics. https://bugzilla.gnome.org/show_bug.cgi?id=789822
This commit is contained in:
parent
18c9babef9
commit
5303e2c32b
4 changed files with 1641 additions and 2 deletions
|
@ -1457,6 +1457,7 @@ GstRTCPType
|
|||
GstRTCPPacket
|
||||
GstRTCPSDESType
|
||||
GstRTCPFBType
|
||||
GstRTCPXRType
|
||||
|
||||
gst_rtcp_buffer_new_take_data
|
||||
gst_rtcp_buffer_new_copy_data
|
||||
|
@ -1550,6 +1551,36 @@ gst_rtcp_unix_to_ntp
|
|||
gst_rtcp_sdes_name_to_type
|
||||
gst_rtcp_sdes_type_to_name
|
||||
|
||||
gst_rtcp_packet_xr_first_rb
|
||||
gst_rtcp_packet_xr_next_rb
|
||||
gst_rtcp_packet_xr_get_ssrc
|
||||
gst_rtcp_packet_xr_get_block_length
|
||||
gst_rtcp_packet_xr_get_block_type
|
||||
|
||||
gst_rtcp_packet_xr_get_dlrr_block
|
||||
|
||||
gst_rtcp_packet_xr_get_prt_by_seq
|
||||
gst_rtcp_packet_xr_get_prt_info
|
||||
|
||||
gst_rtcp_packet_xr_get_rle_info
|
||||
gst_rtcp_packet_xr_get_rle_nth_chunk
|
||||
|
||||
gst_rtcp_packet_xr_get_rrt
|
||||
|
||||
gst_rtcp_packet_xr_get_summary_info
|
||||
gst_rtcp_packet_xr_get_summary_jitter
|
||||
gst_rtcp_packet_xr_get_summary_pkt
|
||||
gst_rtcp_packet_xr_get_summary_ttl
|
||||
|
||||
gst_rtcp_packet_xr_get_voip_burst_metrics
|
||||
gst_rtcp_packet_xr_get_voip_configuration_params
|
||||
gst_rtcp_packet_xr_get_voip_delay_metrics
|
||||
gst_rtcp_packet_xr_get_voip_jitter_buffer_params
|
||||
gst_rtcp_packet_xr_get_voip_metrics_ssrc
|
||||
gst_rtcp_packet_xr_get_voip_packet_metrics
|
||||
gst_rtcp_packet_xr_get_voip_quality_metrics
|
||||
gst_rtcp_packet_xr_get_voip_signal_metrics
|
||||
|
||||
<SUBSECTION Standard>
|
||||
GST_RTCP_RTPFB_TYPE_RCTP_SR_REQ
|
||||
GST_TYPE_RTCPFB_TYPE
|
||||
|
@ -1558,6 +1589,7 @@ GST_TYPE_RTCP_TYPE
|
|||
gst_rtcp_type_get_type
|
||||
gst_rtcpfb_type_get_type
|
||||
gst_rtcpsdes_type_get_type
|
||||
gst_rtcpxr_type_get_type
|
||||
</SECTION>
|
||||
|
||||
<SECTION>
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -137,6 +137,34 @@ typedef enum
|
|||
GST_RTCP_SDES_PRIV = 8
|
||||
} GstRTCPSDESType;
|
||||
|
||||
/**
|
||||
* GstRTCPXRType:
|
||||
* @GST_RTCP_XR_TYPE_INVALID: Invalid XR Report Block
|
||||
* @GST_RTCP_XR_TYPE_LRLE: Loss RLE Report Block
|
||||
* @GST_RTCP_XR_TYPE_DRLE: Duplicate RLE Report Block
|
||||
* @GST_RTCP_XR_TYPE_PRT: Packet Receipt Times Report Block
|
||||
* @GST_RTCP_XR_TYPE_RRT: Receiver Reference Time Report Block
|
||||
* @GST_RTCP_XR_TYPE_DLRR: Delay since the last Receiver Report
|
||||
* @GST_RTCP_XR_TYPE_SSUMM: Statistics Summary Report Block
|
||||
* @GST_RTCP_XR_TYPE_VOIP_METRICS: VoIP Metrics Report Block
|
||||
*
|
||||
* Types of RTCP Extended Reports, those are defined in RFC 3611 and other RFCs
|
||||
* according to the [IANA registry](https://www.iana.org/assignments/rtcp-xr-block-types/rtcp-xr-block-types.xhtml).
|
||||
*
|
||||
* Since: 1.16
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
GST_RTCP_XR_TYPE_INVALID = -1,
|
||||
GST_RTCP_XR_TYPE_LRLE = 1,
|
||||
GST_RTCP_XR_TYPE_DRLE = 2,
|
||||
GST_RTCP_XR_TYPE_PRT = 3,
|
||||
GST_RTCP_XR_TYPE_RRT = 4,
|
||||
GST_RTCP_XR_TYPE_DLRR = 5,
|
||||
GST_RTCP_XR_TYPE_SSUMM = 6,
|
||||
GST_RTCP_XR_TYPE_VOIP_METRICS = 7
|
||||
} GstRTCPXRType;
|
||||
|
||||
/**
|
||||
* GST_RTCP_MAX_SDES:
|
||||
*
|
||||
|
@ -217,7 +245,7 @@ struct _GstRTCPPacket
|
|||
gboolean padding; /* padding field of current packet */
|
||||
guint8 count; /* count field of current packet */
|
||||
GstRTCPType type; /* type of current packet */
|
||||
guint16 length; /* length of current packet in 32-bits words */
|
||||
guint16 length; /* length of current packet in 32-bits words minus one, this is validated when doing _get_first_packet() and _move_to_next() */
|
||||
|
||||
guint item_offset; /* current item offset for navigating SDES */
|
||||
guint item_count; /* current item count */
|
||||
|
@ -479,6 +507,105 @@ const gchar * gst_rtcp_sdes_type_to_name (GstRTCPSDESType type);
|
|||
GST_RTP_API
|
||||
GstRTCPSDESType gst_rtcp_sdes_name_to_type (const gchar *name);
|
||||
|
||||
/* extended report */
|
||||
|
||||
GST_RTP_API
|
||||
guint32 gst_rtcp_packet_xr_get_ssrc (GstRTCPPacket *packet);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_first_rb (GstRTCPPacket *packet);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_next_rb (GstRTCPPacket * packet);
|
||||
|
||||
GST_RTP_API
|
||||
GstRTCPXRType gst_rtcp_packet_xr_get_block_type (GstRTCPPacket * packet);
|
||||
|
||||
GST_RTP_API
|
||||
guint16 gst_rtcp_packet_xr_get_block_length (GstRTCPPacket * packet);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_rle_info (GstRTCPPacket * packet,
|
||||
guint32 * ssrc, guint8 * thining,
|
||||
guint16 * begin_seq, guint16 * end_seq,
|
||||
guint32 * chunk_count);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_rle_nth_chunk (GstRTCPPacket * packet, guint nth,
|
||||
guint16 * chunk);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_prt_info (GstRTCPPacket * packet,
|
||||
guint32 * ssrc, guint8 * thining,
|
||||
guint16 * begin_seq, guint16 * end_seq);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_prt_by_seq (GstRTCPPacket * packet, guint16 seq,
|
||||
guint32 * receipt_time);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_rrt (GstRTCPPacket * packet, guint64 * timestamp);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_dlrr_block (GstRTCPPacket * packet,
|
||||
guint nth, guint32 * ssrc,
|
||||
guint32 * last_rr, guint32 * delay);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_summary_info (GstRTCPPacket * packet, guint32 * ssrc,
|
||||
guint16 * begin_seq, guint16 * end_seq);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_summary_pkt (GstRTCPPacket * packet,
|
||||
guint32 * lost_packets, guint32 * dup_packets);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_summary_jitter (GstRTCPPacket * packet,
|
||||
guint32 * min_jitter, guint32 * max_jitter,
|
||||
guint32 * mean_jitter, guint32 * dev_jitter);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_summary_ttl (GstRTCPPacket * packet, gboolean * is_ipv4,
|
||||
guint8 * min_ttl, guint8 * max_ttl,
|
||||
guint8 * mean_ttl, guint8 * dev_ttl);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_metrics_ssrc (GstRTCPPacket * packet, guint32 * ssrc);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_packet_metrics (GstRTCPPacket * packet,
|
||||
guint8 * loss_rate, guint8 * discard_rate);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_burst_metrics (GstRTCPPacket * packet,
|
||||
guint8 * burst_density, guint8 * gap_density,
|
||||
guint16 * burst_duration, guint16 * gap_duration);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_delay_metrics (GstRTCPPacket * packet,
|
||||
guint16 * roundtrip_delay,
|
||||
guint16 * end_system_delay);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_signal_metrics (GstRTCPPacket * packet,
|
||||
guint8 * signal_level, guint8 * noise_level,
|
||||
guint8 * rerl, guint8 * gmin);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_quality_metrics (GstRTCPPacket * packet,
|
||||
guint8 * r_factor, guint8 * ext_r_factor,
|
||||
guint8 * mos_lq, guint8 * mos_cq);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_configuration_params (GstRTCPPacket * packet,
|
||||
guint8 * gmin, guint8 * rx_config);
|
||||
|
||||
GST_RTP_API
|
||||
gboolean gst_rtcp_packet_xr_get_voip_jitter_buffer_params (GstRTCPPacket * packet,
|
||||
guint16 * jb_nominal,
|
||||
guint16 * jb_maximum,
|
||||
guint16 * jb_abs_max);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __GST_RTCPBUFFER_H__ */
|
||||
|
|
|
@ -1137,6 +1137,467 @@ GST_START_TEST (test_rtcp_buffer_app)
|
|||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x0e, /* Type XR, length = 14 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x01, 0x00, 0x00, 0x03, /* Loss RLE, No thining, length = 3 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
0xcf, 0xb7, 0x8f, 0xb7,
|
||||
0x02, 0x00, 0x00, 0x03, /* Dup RLE, No thining, length = 3 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
0xcf, 0xb7, 0x8f, 0xb7,
|
||||
0x03, 0x00, 0x00, 0x04, /* Packet Receipt Times, No thining, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
0x59, 0xf9, 0xdd, 0x7e,
|
||||
0x59, 0xf9, 0xdd, 0x7e,
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp));
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
fail_unless (gst_rtcp_packet_get_type (&packet) == GST_RTCP_TYPE_XR);
|
||||
fail_unless (gst_rtcp_packet_xr_get_ssrc (&packet) ==
|
||||
GST_READ_UINT32_BE (rtcp_pkt + 12));
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_LRLE);
|
||||
fail_unless (gst_rtcp_packet_xr_next_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_DRLE);
|
||||
fail_unless (gst_rtcp_packet_xr_next_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_PRT);
|
||||
|
||||
fail_if (gst_rtcp_packet_xr_next_rb (&packet));
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_rle)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint32 ssrc, chunk_count;
|
||||
guint8 thining;
|
||||
guint16 begin_seq, end_seq, chunk;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x0a, /* Type XR, length = 10 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x01, 0x00, 0x00, 0x03, /* Loss RLE, No thining, length = 3 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
0x80, 0x12, 0x00, 0x00,
|
||||
0x02, 0x00, 0x00, 0x04, /* Dup RLE, No thining, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x7b, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x04,
|
||||
0x8f, 0x21, 0x8f, 0x22,
|
||||
0x8f, 0x23, 0x8f, 0x24
|
||||
};
|
||||
guint8 rtcp_pkt_invalid_pkt_length[] = {
|
||||
0x80, 0xCF, 0x00, 0x04, /* Type XR, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x01, 0x00, 0x00, 0x02, /* Loss RLE, No thining, length = 1 (but really 3) */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
/* check LRLE */
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_LRLE);
|
||||
fail_unless (gst_rtcp_packet_xr_get_rle_info (&packet, &ssrc, &thining,
|
||||
&begin_seq, &end_seq, &chunk_count));
|
||||
fail_unless_equals_int (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 12));
|
||||
fail_unless_equals_int (thining, 0);
|
||||
fail_unless_equals_int (begin_seq, 0x0001);
|
||||
fail_unless_equals_int (end_seq, 0x0002);
|
||||
fail_unless_equals_int (chunk_count, 2);
|
||||
|
||||
gst_rtcp_packet_xr_get_rle_nth_chunk (&packet, 0, &chunk);
|
||||
fail_unless_equals_int (chunk, 0x8012);
|
||||
|
||||
gst_rtcp_packet_xr_get_rle_nth_chunk (&packet, 1, &chunk);
|
||||
fail_unless_equals_int (chunk, 0x0);
|
||||
|
||||
/* check DRLE */
|
||||
fail_unless (gst_rtcp_packet_xr_next_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_DRLE);
|
||||
fail_unless (gst_rtcp_packet_xr_get_rle_info (&packet, &ssrc, &thining,
|
||||
&begin_seq, &end_seq, &chunk_count));
|
||||
fail_unless_equals_int (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 28));
|
||||
fail_unless_equals_int (thining, 0);
|
||||
fail_unless_equals_int (begin_seq, 0x0001);
|
||||
fail_unless_equals_int (end_seq, 0x0004);
|
||||
fail_unless_equals_int (chunk_count, 4);
|
||||
|
||||
gst_rtcp_packet_xr_get_rle_nth_chunk (&packet, 1, &chunk);
|
||||
fail_unless_equals_int (chunk, 0x8f22);
|
||||
|
||||
gst_rtcp_packet_xr_get_rle_nth_chunk (&packet, 2, &chunk);
|
||||
fail_unless_equals_int (chunk, 0x8f23);
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
|
||||
/* Test invalid length */
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt_invalid_pkt_length, sizeof (rtcp_pkt_invalid_pkt_length), 0,
|
||||
sizeof (rtcp_pkt_invalid_pkt_length), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
/* check LRLE (should fail because length is too short) */
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_LRLE);
|
||||
fail_if (gst_rtcp_packet_xr_get_rle_info (&packet, &ssrc, &thining,
|
||||
&begin_seq, &end_seq, &chunk_count));
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_prt)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint32 ssrc, receipt_time;
|
||||
guint8 thining;
|
||||
guint16 begin_seq, end_seq;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x06, /* Type XR, length = 6 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x03, 0x00, 0x00, 0x04, /* Packet Receipt Times, No thining, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x03,
|
||||
0x59, 0xf9, 0xdd, 0x7e,
|
||||
0x59, 0xf9, 0xde, 0x00,
|
||||
};
|
||||
guint8 rtcp_pkt_invalid_pkt_length[] = {
|
||||
0x80, 0xCF, 0x00, 0x04, /* Type XR, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x03, 0x00, 0x00, 0x02, /* Packet Receipt Times, No thining, length = 2 (but should be 4) */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x03,
|
||||
};
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_PRT);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_prt_info (&packet, &ssrc, &thining,
|
||||
&begin_seq, &end_seq));
|
||||
fail_unless (gst_rtcp_packet_xr_get_prt_by_seq (&packet, 2, &receipt_time));
|
||||
fail_unless_equals_int_hex (receipt_time, 0x59f9de00L);
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
|
||||
/* Test for invalid length */
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt_invalid_pkt_length, sizeof (rtcp_pkt_invalid_pkt_length), 0,
|
||||
sizeof (rtcp_pkt_invalid_pkt_length), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_PRT);
|
||||
|
||||
fail_if (gst_rtcp_packet_xr_get_prt_info (&packet, &ssrc, &thining,
|
||||
&begin_seq, &end_seq));
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_rrt)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint64 ntptime;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x04, /* Type XR, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x04, 0x00, 0x00, 0x02, /* Receiver Reference Time, length = 2 */
|
||||
0x01, 0x23, 0x45, 0x67,
|
||||
0x89, 0x01, 0x23, 0x45
|
||||
};
|
||||
guint8 rtcp_pkt_invalid_pkt_length[] = {
|
||||
0x80, 0xCF, 0x00, 0x04, /* Type XR, length = 4 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x04, 0x00, 0x00, 0x01, /* Receiver Reference Time, length = 1 */
|
||||
0x01, 0x23, 0x45, 0x67,
|
||||
0x89, 0x01, 0x23, 0x45
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_RRT);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_rrt (&packet, &ntptime));
|
||||
fail_unless_equals_uint64_hex (ntptime, 0x0123456789012345LL);
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
|
||||
/* Test invalid length */
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt_invalid_pkt_length, sizeof (rtcp_pkt_invalid_pkt_length), 0,
|
||||
sizeof (rtcp_pkt_invalid_pkt_length), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_RRT);
|
||||
|
||||
fail_if (gst_rtcp_packet_xr_get_rrt (&packet, &ntptime));
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_dlrr)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint32 ssrc, last_rr, delay;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x08, /* Type XR, length = 8 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x05, 0x00, 0x00, 0x06, /* DLRR, length = 6 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x01, 0x23, 0x45, 0x67,
|
||||
0x89, 0x01, 0x23, 0x45,
|
||||
0x97, 0x6d, 0x21, 0x6b, /* SSRC of source */
|
||||
0x01, 0x23, 0x45, 0x67,
|
||||
0x89, 0x01, 0x23, 0x45
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_DLRR);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_dlrr_block (&packet, 0, &ssrc, &last_rr,
|
||||
&delay));
|
||||
fail_unless_equals_int_hex (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 12));
|
||||
fail_unless (gst_rtcp_packet_xr_get_dlrr_block (&packet, 1, &ssrc, &last_rr,
|
||||
&delay));
|
||||
fail_unless_equals_int_hex (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 24));
|
||||
|
||||
/* it has only two sub-blocks. */
|
||||
fail_if (gst_rtcp_packet_xr_get_dlrr_block (&packet, 2, &ssrc, &last_rr,
|
||||
&delay));
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_ssumm)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint32 ssrc, lost_packets, dup_packets;
|
||||
guint16 begin_seq, end_seq;
|
||||
guint32 min_jitter, max_jitter, mean_jitter, dev_jitter;
|
||||
guint8 min_ttl, max_ttl, mean_ttl, dev_ttl;
|
||||
gboolean ipv4;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x0b, /* Type XR, length = 11 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x06, 0xe8, 0x00, 0x09, /* Statistics summary, length = 9 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x00, 0x01, 0x00, 0x02,
|
||||
0x00, 0x00, 0x00, 0x01,
|
||||
0x00, 0x00, 0x00, 0x02,
|
||||
0x00, 0x00, 0x00, 0x03,
|
||||
0x00, 0x00, 0x00, 0x04,
|
||||
0x00, 0x00, 0x00, 0x05,
|
||||
0x00, 0x00, 0x00, 0x06,
|
||||
0x01, 0x80, 0x0f, 0x8f
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_SSUMM);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_summary_info (&packet, &ssrc, &begin_seq,
|
||||
&end_seq));
|
||||
fail_unless_equals_int_hex (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 12));
|
||||
fail_unless_equals_int (begin_seq, GST_READ_UINT16_BE (rtcp_pkt + 16));
|
||||
fail_unless_equals_int (end_seq, GST_READ_UINT16_BE (rtcp_pkt + 18));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_summary_pkt (&packet, &lost_packets,
|
||||
&dup_packets));
|
||||
fail_unless_equals_int (lost_packets, GST_READ_UINT32_BE (rtcp_pkt + 20));
|
||||
fail_unless_equals_int (dup_packets, GST_READ_UINT32_BE (rtcp_pkt + 24));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_summary_jitter (&packet, &min_jitter,
|
||||
&max_jitter, &mean_jitter, &dev_jitter));
|
||||
fail_unless_equals_int (min_jitter, GST_READ_UINT32_BE (rtcp_pkt + 28));
|
||||
fail_unless_equals_int (max_jitter, GST_READ_UINT32_BE (rtcp_pkt + 32));
|
||||
fail_unless_equals_int (mean_jitter, GST_READ_UINT32_BE (rtcp_pkt + 36));
|
||||
fail_unless_equals_int (dev_jitter, GST_READ_UINT32_BE (rtcp_pkt + 40));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_summary_ttl (&packet, &ipv4, &min_ttl,
|
||||
&max_ttl, &mean_ttl, &dev_ttl));
|
||||
fail_unless (ipv4);
|
||||
fail_unless_equals_int (min_ttl, rtcp_pkt[44]);
|
||||
fail_unless_equals_int (max_ttl, rtcp_pkt[45]);
|
||||
fail_unless_equals_int (mean_ttl, rtcp_pkt[46]);
|
||||
fail_unless_equals_int (dev_ttl, rtcp_pkt[47]);
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtcp_buffer_xr_voipmtrx)
|
||||
{
|
||||
GstBuffer *buffer;
|
||||
GstRTCPPacket packet;
|
||||
guint32 ssrc;
|
||||
guint8 loss_rate, discard_rate, burst_density, gap_density;
|
||||
guint8 signal_level, noise_level, rerl, gmin;
|
||||
guint8 r_factor, ext_r_factor, mos_lq, mos_cq, rx_config;
|
||||
guint16 burst_duration, gap_duration;
|
||||
guint16 roundtrip_delay, end_system_delay;
|
||||
guint16 jb_nominal, jb_maximum, jb_abs_max;
|
||||
GstRTCPBuffer rtcp = GST_RTCP_BUFFER_INIT;
|
||||
guint8 rtcp_pkt[] = {
|
||||
0x80, 0xCF, 0x00, 0x0a, /* Type XR, length = 10 */
|
||||
0x97, 0x6d, 0x21, 0x6a,
|
||||
0x07, 0x00, 0x00, 0x08, /* VoIP Metrics, length = 8 */
|
||||
0x97, 0x6d, 0x21, 0x6a, /* SSRC of source */
|
||||
0x01, 0x02, 0x03, 0x04,
|
||||
0x05, 0x06, 0x07, 0x08,
|
||||
0x09, 0x0a, 0x0b, 0x0c,
|
||||
0x0d, 0x0e, 0x0f, 0x10,
|
||||
0x11, 0x12, 0x13, 0x14,
|
||||
0x15, 0x00, 0x16, 0x17,
|
||||
0x18, 0x19, 0x1a, 0x1b
|
||||
};
|
||||
|
||||
buffer = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY,
|
||||
rtcp_pkt, sizeof (rtcp_pkt), 0, sizeof (rtcp_pkt), NULL, NULL);
|
||||
gst_rtcp_buffer_map (buffer, GST_MAP_READ, &rtcp);
|
||||
|
||||
fail_unless (gst_rtcp_buffer_get_first_packet (&rtcp, &packet));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_first_rb (&packet));
|
||||
fail_unless (gst_rtcp_packet_xr_get_block_type (&packet) ==
|
||||
GST_RTCP_XR_TYPE_VOIP_METRICS);
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_metrics_ssrc (&packet, &ssrc));
|
||||
fail_unless_equals_int_hex (ssrc, GST_READ_UINT32_BE (rtcp_pkt + 12));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_packet_metrics (&packet, &loss_rate,
|
||||
&discard_rate));
|
||||
fail_unless_equals_int (loss_rate, rtcp_pkt[16]);
|
||||
fail_unless_equals_int (discard_rate, rtcp_pkt[17]);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_burst_metrics (&packet,
|
||||
&burst_density, &gap_density, &burst_duration, &gap_duration));
|
||||
fail_unless_equals_int (burst_density, rtcp_pkt[18]);
|
||||
fail_unless_equals_int (gap_density, rtcp_pkt[19]);
|
||||
fail_unless_equals_int (burst_duration, GST_READ_UINT16_BE (rtcp_pkt + 20));
|
||||
fail_unless_equals_int (gap_duration, GST_READ_UINT16_BE (rtcp_pkt + 22));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_delay_metrics (&packet,
|
||||
&roundtrip_delay, &end_system_delay));
|
||||
fail_unless_equals_int (roundtrip_delay, GST_READ_UINT16_BE (rtcp_pkt + 24));
|
||||
fail_unless_equals_int (end_system_delay, GST_READ_UINT16_BE (rtcp_pkt + 26));
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_signal_metrics (&packet,
|
||||
&signal_level, &noise_level, &rerl, &gmin));
|
||||
fail_unless_equals_int (signal_level, rtcp_pkt[28]);
|
||||
fail_unless_equals_int (noise_level, rtcp_pkt[29]);
|
||||
fail_unless_equals_int (rerl, rtcp_pkt[30]);
|
||||
fail_unless_equals_int (gmin, rtcp_pkt[31]);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_quality_metrics (&packet, &r_factor,
|
||||
&ext_r_factor, &mos_lq, &mos_cq));
|
||||
fail_unless_equals_int (r_factor, rtcp_pkt[32]);
|
||||
fail_unless_equals_int (ext_r_factor, rtcp_pkt[33]);
|
||||
fail_unless_equals_int (mos_lq, rtcp_pkt[34]);
|
||||
fail_unless_equals_int (mos_cq, rtcp_pkt[35]);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_configuration_params (&packet, &gmin,
|
||||
&rx_config));
|
||||
fail_unless_equals_int (gmin, rtcp_pkt[31]);
|
||||
fail_unless_equals_int (rx_config, rtcp_pkt[36]);
|
||||
|
||||
fail_unless (gst_rtcp_packet_xr_get_voip_jitter_buffer_params (&packet,
|
||||
&jb_nominal, &jb_maximum, &jb_abs_max));
|
||||
fail_unless_equals_int (jb_nominal, GST_READ_UINT16_BE (rtcp_pkt + 38));
|
||||
fail_unless_equals_int (jb_maximum, GST_READ_UINT16_BE (rtcp_pkt + 40));
|
||||
fail_unless_equals_int (jb_abs_max, GST_READ_UINT16_BE (rtcp_pkt + 42));
|
||||
|
||||
gst_rtcp_buffer_unmap (&rtcp);
|
||||
gst_buffer_unref (buffer);
|
||||
}
|
||||
|
||||
GST_END_TEST;
|
||||
|
||||
GST_START_TEST (test_rtp_ntp64_extension)
|
||||
{
|
||||
GstBuffer *buf;
|
||||
|
@ -1463,6 +1924,13 @@ rtp_suite (void)
|
|||
tcase_add_test (tc_chain, test_rtcp_validate_reduced_with_padding);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_profile_specific_extension);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_app);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_rle);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_prt);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_rrt);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_dlrr);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_ssumm);
|
||||
tcase_add_test (tc_chain, test_rtcp_buffer_xr_voipmtrx);
|
||||
|
||||
tcase_add_test (tc_chain, test_rtp_ntp64_extension);
|
||||
tcase_add_test (tc_chain, test_rtp_ntp56_extension);
|
||||
|
|
Loading…
Reference in a new issue