blob: 77af2fa7da30c33b5b3a490a19977fb8863b3ca0 [file] [log] [blame]
/*
* Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
*
* Use of this source code is governed by a BSD-style license
* that can be found in the LICENSE file in the root of the source
* tree. An additional intellectual property rights grant can be found
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
#ifndef WEBRTC_VOICE_ENGINE_TRANSPORT_FEEDBACK_PACKET_LOSS_TRACKER_H_
#define WEBRTC_VOICE_ENGINE_TRANSPORT_FEEDBACK_PACKET_LOSS_TRACKER_H_
#include <map>
#include "webrtc/base/optional.h"
#include "webrtc/modules/include/module_common_types.h"
namespace webrtc {
namespace rtcp {
class TransportFeedback;
}
class TransportFeedbackPacketLossTracker final {
public:
// * Up to |max_window_size| latest packet statuses will be used for
// calculating the packet loss metrics.
// * PLR (packet-loss-rate) is reliably computable once the statuses of
// |plr_min_num_packets| packets are known.
// * RPLR (recoverable-packet-loss-rate) is reliably computable once the
// statuses of |rplr_min_num_pairs| pairs are known.
TransportFeedbackPacketLossTracker(size_t max_window_size,
size_t plr_min_num_packets,
size_t rplr_min_num_pairs);
void OnReceivedTransportFeedback(const rtcp::TransportFeedback& feedback);
// Returns the packet loss rate, if the window has enough packet statuses to
// reliably compute it. Otherwise, returns empty.
rtc::Optional<float> GetPacketLossRate() const;
// Returns the first-order-FEC recoverable packet loss rate, if the window has
// enough status pairs to reliably compute it. Otherwise, returns empty.
rtc::Optional<float> GetRecoverablePacketLossRate() const;
// Verifies that the internal states are correct. Only used for tests.
void Validate() const;
private:
// PacketStatus is a map from sequence number to its reception status. The
// status is true if the corresponding packet is received, and false if it is
// lost. Unknown statuses are not present in the map.
typedef std::map<uint16_t, bool> PacketStatus;
typedef PacketStatus::const_iterator PacketStatusIterator;
void Reset();
// ReferenceSequenceNumber() provides a sequence number that defines the
// order of packet reception info stored in |packet_status_window_|. In
// particular, given any sequence number |x|,
// (2^16 + x - ref_seq_num_) % 2^16 defines its actual position in
// |packet_status_window_|.
uint16_t ReferenceSequenceNumber() const;
bool IsOldSequenceNumber(uint16_t seq_num) const;
void InsertPacketStatus(uint16_t seq_num, bool received);
void RemoveOldestPacketStatus();
void UpdateMetrics(PacketStatusIterator it, bool apply /* false = undo */);
void UpdatePlr(PacketStatusIterator it, bool apply /* false = undo */);
void UpdateRplr(PacketStatusIterator it, bool apply /* false = undo */);
PacketStatusIterator PreviousPacketStatus(PacketStatusIterator it);
PacketStatusIterator NextPacketStatus(PacketStatusIterator it);
const size_t max_window_size_;
PacketStatus packet_status_window_;
// |ref_packet_status_| points to the oldest item in |packet_status_window_|.
PacketStatusIterator ref_packet_status_;
// Packet-loss-rate calculation (lost / all-known-packets).
struct PlrState {
explicit PlrState(size_t min_num_packets)
: min_num_packets_(min_num_packets) {
Reset();
}
void Reset() {
num_received_packets_ = 0;
num_lost_packets_ = 0;
}
rtc::Optional<float> GetMetric() const;
const size_t min_num_packets_;
size_t num_received_packets_;
size_t num_lost_packets_;
} plr_state_;
// Recoverable packet loss calculation (first-order-FEC recoverable).
struct RplrState {
explicit RplrState(size_t min_num_pairs)
: min_num_pairs_(min_num_pairs) {
Reset();
}
void Reset() {
num_known_pairs_ = 0;
num_recoverable_losses_ = 0;
}
rtc::Optional<float> GetMetric() const;
// Recoverable packets are those which were lost, but immediately followed
// by a properly received packet. If that second packet carried FEC,
// the data from the former (lost) packet could be recovered.
// The RPLR is calculated as the fraction of such pairs (lost-received) out
// of all pairs of consecutive acked packets.
const size_t min_num_pairs_;
size_t num_known_pairs_;
size_t num_recoverable_losses_;
} rplr_state_;
size_t num_consecutive_old_reports_; // TODO(elad.alon): Upcoming CL removes.
};
} // namespace webrtc
#endif // WEBRTC_VOICE_ENGINE_TRANSPORT_FEEDBACK_PACKET_LOSS_TRACKER_H_