rtpstats.h 8.52 KB
Newer Older
1
/* GStreamer
2
 * Copyright (C) <2007> Wim Taymans <wim.taymans@gmail.com>
3 4
 * Copyright (C)  2015 Kurento (http://kurento.org/)
 *   @author: Miguel París <mparisdiaz@gmail.com>
5 6 7 8 9 10 11 12 13 14 15 16 17
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this library; if not, write to the
Tim-Philipp Müller's avatar
Tim-Philipp Müller committed
18 19
 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
 * Boston, MA 02110-1301, USA.
20 21 22 23 24 25
 */

#ifndef __RTP_STATS_H__
#define __RTP_STATS_H__

#include <gst/gst.h>
Wim Taymans's avatar
Wim Taymans committed
26
#include <gst/net/gstnetaddressmeta.h>
27
#include <gst/rtp/rtp.h>
Sebastian Dröge's avatar
Sebastian Dröge committed
28
#include <gio/gio.h>
29 30 31 32 33 34 35 36 37 38 39 40

/**
 * RTPSenderReport:
 *
 * A sender report structure.
 */
typedef struct {
  gboolean is_valid;
  guint64 ntptime;
  guint32 rtptime;
  guint32 packet_count;
  guint32 octet_count;
41
  GstClockTime time;
42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57
} RTPSenderReport;

/**
 * RTPReceiverReport:
 *
 * A receiver report structure.
 */
typedef struct {
  gboolean is_valid;
  guint32 ssrc; /* who the report is from */
  guint8  fractionlost;
  guint32 packetslost;
  guint32 exthighestseq;
  guint32 jitter;
  guint32 lsr;
  guint32 dlsr;
58
  guint32 round_trip;
59 60 61
} RTPReceiverReport;

/**
62
 * RTPPacketInfo:
63 64 65 66
 * @send: if this is a packet for sending
 * @rtp: if this info is about an RTP packet
 * @is_list: if this is a bufferlist
 * @data: a #GstBuffer or #GstBufferList
67
 * @address: address of the sender of the packet
68
 * @current_time: current time according to the system clock
69 70
 * @running_time: time of a packet as buffer running_time
 * @ntpnstime: time of a packet NTP time in nanoseconds
71
 * @header_len: number of overhead bytes per packet
72 73
 * @bytes: bytes of the packet including lowlevel overhead
 * @payload_len: bytes of the RTP payload
74 75 76
 * @seqnum: the seqnum of the packet
 * @pt: the payload type of the packet
 * @rtptime: the RTP time of the packet
77
 *
78
 * Structure holding information about the packet.
79 80
 */
typedef struct {
81 82 83 84
  gboolean      send;
  gboolean      rtp;
  gboolean      is_list;
  gpointer      data;
85
  GSocketAddress *address;
86
  GstClockTime  current_time;
87
  GstClockTime  running_time;
88
  guint64       ntpnstime;
89
  guint         header_len;
90
  guint         bytes;
91
  guint         packets;
92
  guint         payload_len;
93 94 95 96 97 98
  guint32       ssrc;
  guint16       seqnum;
  guint8        pt;
  guint32       rtptime;
  guint32       csrc_count;
  guint32       csrcs[16];
99
} RTPPacketInfo;
100 101 102 103 104 105 106 107 108 109 110

/**
 * RTPSourceStats:
 * @packetsreceived: number of received packets in total
 * @prevpacketsreceived: number of packets received in previous reporting
 *                       interval
 * @octetsreceived: number of payload bytes received
 * @bytesreceived: number of total bytes received including headers and lower
 *                 protocol level overhead
 * @max_seqnr: highest sequence number received
 * @transit: previous transit time used for calculating @jitter
111
 * @jitter: current jitter (in clock rate units scaled by 16 for precision)
112 113 114 115 116 117 118 119 120 121 122 123
 * @prev_rtptime: previous time when an RTP packet was received
 * @prev_rtcptime: previous time when an RTCP packet was received
 * @last_rtptime: time when last RTP packet received
 * @last_rtcptime: time when last RTCP packet received
 * @curr_rr: index of current @rr block
 * @rr: previous and current receiver report block
 * @curr_sr: index of current @sr block
 * @sr: previous and current sender report block
 *
 * Stats about a source.
 */
typedef struct {
124 125 126 127 128 129 130 131
  guint64      packets_received;
  guint64      octets_received;
  guint64      bytes_received;

  guint32      prev_expected;
  guint32      prev_received;

  guint16      max_seq;
132
  guint64      cycles;
133 134
  guint32      base_seq;
  guint32      bad_seq;
135 136 137
  guint32      transit;
  guint32      jitter;

138 139 140
  guint64      packets_sent;
  guint64      octets_sent;

141 142
  guint        sent_pli_count;
  guint        recv_pli_count;
143 144
  guint        sent_fir_count;
  guint        recv_fir_count;
145 146
  guint        sent_nack_count;
  guint        recv_nack_count;
147

148 149 150 151 152 153 154 155 156 157 158 159 160
  /* when we received stuff */
  GstClockTime prev_rtptime;
  GstClockTime prev_rtcptime;
  GstClockTime last_rtptime;
  GstClockTime last_rtcptime;

  /* sender and receiver reports */
  gint              curr_rr;
  RTPReceiverReport rr[2];
  gint              curr_sr;
  RTPSenderReport   sr[2];
} RTPSourceStats;

161
#define RTP_STATS_BANDWIDTH           64000
162
#define RTP_STATS_RTCP_FRACTION       0.05
163 164 165 166 167 168 169 170 171
/*
 * Minimum average time between RTCP packets from this site (in
 * seconds).  This time prevents the reports from `clumping' when
 * sessions are small and the law of large numbers isn't helping
 * to smooth out the traffic.  It also keeps the report interval
 * from becoming ridiculously small during transient outages like
 * a network partition.
 */
#define RTP_STATS_MIN_INTERVAL      5.0
172
/*
173 174 175 176 177 178 179 180 181 182
 * Fraction of the RTCP bandwidth to be shared among active
 * senders.  (This fraction was chosen so that in a typical
 * session with one or two active senders, the computed report
 * time would be roughly equal to the minimum report time so that
 * we don't unnecessarily slow down receiver reports.) The
 * receiver fraction must be 1 - the sender fraction.
 */
#define RTP_STATS_SENDER_FRACTION       (0.25)
#define RTP_STATS_RECEIVER_FRACTION     (1.0 - RTP_STATS_SENDER_FRACTION)

183
/*
184
 * When receiving a BYE from a source, remove the source from the database
185 186 187 188
 * after this timeout.
 */
#define RTP_STATS_BYE_TIMEOUT           (2 * GST_SECOND)

189
/*
190 191
 * The default and minimum values of the maximum number of missing packets we tolerate.
 * These are packets with asequence number bigger than the last seen packet.
192
 */
193 194 195
#define RTP_DEF_DROPOUT      3000
#define RTP_MIN_DROPOUT      30

196
/*
197 198
 * The default and minimum values of the maximum number of misordered packets we tolerate.
 * These are packets with a sequence number smaller than the last seen packet.
199
 */
200 201
#define RTP_DEF_MISORDER     100
#define RTP_MIN_MISORDER     10
202

203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218
/**
 * RTPPacketRateCtx:
 *
 * Context to calculate the pseudo-average packet rate.
 */
typedef struct {
  gboolean probed;
  guint32 clock_rate;
  guint16 last_seqnum;
  guint64 last_ts;
  guint32 avg_packet_rate;
} RTPPacketRateCtx;

void gst_rtp_packet_rate_ctx_reset (RTPPacketRateCtx * ctx, guint32 clock_rate);
guint32 gst_rtp_packet_rate_ctx_update (RTPPacketRateCtx *ctx, guint16 seqnum, guint32 ts);
guint32 gst_rtp_packet_rate_ctx_get (RTPPacketRateCtx *ctx);
219 220
guint32 gst_rtp_packet_rate_ctx_get_max_dropout (RTPPacketRateCtx *ctx, gint32 time_ms);
guint32 gst_rtp_packet_rate_ctx_get_max_misorder (RTPPacketRateCtx *ctx, gint32 time_ms);
221

222 223 224 225 226 227
/**
 * RTPSessionStats:
 *
 * Stats kept for a session and used to produce RTCP packet timeouts.
 */
typedef struct {
228 229
  guint         bandwidth;
  guint         rtcp_bandwidth;
230 231 232
  gdouble       sender_fraction;
  gdouble       receiver_fraction;
  gdouble       min_interval;
233
  GstClockTime  bye_timeout;
234
  guint         internal_sources;
235
  guint         sender_sources;
236
  guint         internal_sender_sources;
237 238
  guint         active_sources;
  guint         avg_rtcp_packet_size;
239
  guint         bye_members;
240 241 242
  guint         nacks_dropped;
  guint         nacks_sent;
  guint         nacks_received;
243 244
} RTPSessionStats;

245 246
void           rtp_stats_init_defaults              (RTPSessionStats *stats);

247 248 249
void           rtp_stats_set_bandwidths             (RTPSessionStats *stats,
                                                     guint rtp_bw,
                                                     gdouble rtcp_bw,
250
                                                     guint rs, guint rr);
251

252
GstClockTime   rtp_stats_calculate_rtcp_interval    (RTPSessionStats *stats, gboolean sender, GstRTPProfile profile, gboolean ptp, gboolean first);
253 254
GstClockTime   rtp_stats_add_rtcp_jitter            (RTPSessionStats *stats, GstClockTime interval);
GstClockTime   rtp_stats_calculate_bye_interval     (RTPSessionStats *stats);
255
gint64         rtp_stats_get_packets_lost           (const RTPSourceStats *stats);
256 257 258

void           rtp_stats_set_min_interval           (RTPSessionStats *stats,
                                                     gdouble min_interval);
Sebastian Dröge's avatar
Sebastian Dröge committed
259 260 261 262 263


gboolean __g_socket_address_equal (GSocketAddress *a, GSocketAddress *b);
gchar * __g_socket_address_to_string (GSocketAddress * addr);

264
#endif /* __RTP_STATS_H__ */