1 /* 2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11 #ifndef MODULES_RTP_RTCP_SOURCE_RECEIVE_STATISTICS_IMPL_H_ 12 #define MODULES_RTP_RTCP_SOURCE_RECEIVE_STATISTICS_IMPL_H_ 13 14 #include <algorithm> 15 #include <map> 16 #include <vector> 17 18 #include "absl/types/optional.h" 19 #include "modules/include/module_common_types_public.h" 20 #include "modules/rtp_rtcp/include/receive_statistics.h" 21 #include "rtc_base/rate_statistics.h" 22 #include "rtc_base/synchronization/mutex.h" 23 #include "rtc_base/thread_annotations.h" 24 25 namespace webrtc { 26 27 class StreamStatisticianImpl : public StreamStatistician { 28 public: 29 StreamStatisticianImpl(uint32_t ssrc, 30 Clock* clock, 31 int max_reordering_threshold); 32 ~StreamStatisticianImpl() override; 33 34 RtpReceiveStats GetStats() const override; 35 36 bool GetActiveStatisticsAndReset(RtcpStatistics* statistics); 37 absl::optional<int> GetFractionLostInPercent() const override; 38 StreamDataCounters GetReceiveStreamDataCounters() const override; 39 uint32_t BitrateReceived() const override; 40 41 void SetMaxReorderingThreshold(int max_reordering_threshold); 42 void EnableRetransmitDetection(bool enable); 43 44 // Updates StreamStatistician for incoming packets. 45 void UpdateCounters(const RtpPacketReceived& packet); 46 47 private: 48 bool IsRetransmitOfOldPacket(const RtpPacketReceived& packet, 49 int64_t now_ms) const 50 RTC_EXCLUSIVE_LOCKS_REQUIRED(stream_lock_); 51 RtcpStatistics CalculateRtcpStatistics() 52 RTC_EXCLUSIVE_LOCKS_REQUIRED(stream_lock_); 53 void UpdateJitter(const RtpPacketReceived& packet, int64_t receive_time_ms) 54 RTC_EXCLUSIVE_LOCKS_REQUIRED(stream_lock_); 55 // Updates StreamStatistician for out of order packets. 56 // Returns true if packet considered to be out of order. 57 bool UpdateOutOfOrder(const RtpPacketReceived& packet, 58 int64_t sequence_number, 59 int64_t now_ms) 60 RTC_EXCLUSIVE_LOCKS_REQUIRED(stream_lock_); 61 // Checks if this StreamStatistician received any rtp packets. ReceivedRtpPacket()62 bool ReceivedRtpPacket() const RTC_EXCLUSIVE_LOCKS_REQUIRED(stream_lock_) { 63 return received_seq_first_ >= 0; 64 } 65 66 const uint32_t ssrc_; 67 Clock* const clock_; 68 mutable Mutex stream_lock_; 69 RateStatistics incoming_bitrate_ RTC_GUARDED_BY(&stream_lock_); 70 // In number of packets or sequence numbers. 71 int max_reordering_threshold_ RTC_GUARDED_BY(&stream_lock_); 72 bool enable_retransmit_detection_ RTC_GUARDED_BY(&stream_lock_); 73 74 // Stats on received RTP packets. 75 uint32_t jitter_q4_ RTC_GUARDED_BY(&stream_lock_); 76 // Cumulative loss according to RFC 3550, which may be negative (and often is, 77 // if packets are reordered and there are non-RTX retransmissions). 78 int32_t cumulative_loss_ RTC_GUARDED_BY(&stream_lock_); 79 // Offset added to outgoing rtcp reports, to make ensure that the reported 80 // cumulative loss is non-negative. Reports with negative values confuse some 81 // senders, in particular, our own loss-based bandwidth estimator. 82 int32_t cumulative_loss_rtcp_offset_ RTC_GUARDED_BY(&stream_lock_); 83 84 int64_t last_receive_time_ms_ RTC_GUARDED_BY(&stream_lock_); 85 uint32_t last_received_timestamp_ RTC_GUARDED_BY(&stream_lock_); 86 SequenceNumberUnwrapper seq_unwrapper_ RTC_GUARDED_BY(&stream_lock_); 87 int64_t received_seq_first_ RTC_GUARDED_BY(&stream_lock_); 88 int64_t received_seq_max_ RTC_GUARDED_BY(&stream_lock_); 89 // Assume that the other side restarted when there are two sequential packets 90 // with large jump from received_seq_max_. 91 absl::optional<uint16_t> received_seq_out_of_order_ 92 RTC_GUARDED_BY(&stream_lock_); 93 94 // Current counter values. 95 StreamDataCounters receive_counters_ RTC_GUARDED_BY(&stream_lock_); 96 97 // Counter values when we sent the last report. 98 int32_t last_report_cumulative_loss_ RTC_GUARDED_BY(&stream_lock_); 99 int64_t last_report_seq_max_ RTC_GUARDED_BY(&stream_lock_); 100 }; 101 102 class ReceiveStatisticsImpl : public ReceiveStatistics { 103 public: 104 explicit ReceiveStatisticsImpl(Clock* clock); 105 106 ~ReceiveStatisticsImpl() override; 107 108 // Implements ReceiveStatisticsProvider. 109 std::vector<rtcp::ReportBlock> RtcpReportBlocks(size_t max_blocks) override; 110 111 // Implements RtpPacketSinkInterface 112 void OnRtpPacket(const RtpPacketReceived& packet) override; 113 114 // Implements ReceiveStatistics. 115 // Note: More specific return type for use in the implementation. 116 StreamStatisticianImpl* GetStatistician(uint32_t ssrc) const override; 117 void SetMaxReorderingThreshold(int max_reordering_threshold) override; 118 void SetMaxReorderingThreshold(uint32_t ssrc, 119 int max_reordering_threshold) override; 120 void EnableRetransmitDetection(uint32_t ssrc, bool enable) override; 121 122 private: 123 StreamStatisticianImpl* GetOrCreateStatistician(uint32_t ssrc); 124 125 Clock* const clock_; 126 mutable Mutex receive_statistics_lock_; 127 uint32_t last_returned_ssrc_; 128 int max_reordering_threshold_ RTC_GUARDED_BY(receive_statistics_lock_); 129 std::map<uint32_t, StreamStatisticianImpl*> statisticians_ 130 RTC_GUARDED_BY(receive_statistics_lock_); 131 }; 132 } // namespace webrtc 133 #endif // MODULES_RTP_RTCP_SOURCE_RECEIVE_STATISTICS_IMPL_H_ 134