Compute loss rate based on byte count rather than packet count in loss based BWE.
2 main reasons: 1. Packet sizes are much different thus a lost audio packet should not be treated similar to a lost video packet. In low bandwidth/traffic policing scenario, the number of send packet is few, thus the computed loss can be imprecise. 2. Given a candidate bandwidth estimate, the objective function (how good the candidate is) is computed by recomputing loss rate = send rate/estimate bandwith + inherent loss. It means the objective function is byte based rather than packet based. Potential risk: the current algorithm params are tuned based on packet count, thus it might not work with byte count, which is much higher than packet count. The change is under field trial and disabled by default. Bug: webrtc:12707 Change-Id: I8b832e7920d2b4cadcd4a072b3a4d4f26a213a20 Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/325065 Reviewed-by: Per Kjellander <perkj@webrtc.org> Commit-Queue: Diep Bui <diepbp@webrtc.org> Cr-Commit-Position: refs/heads/main@{#41013}
This commit is contained in:
parent
40ce7674c4
commit
1f2f5dc951
@ -49,10 +49,13 @@ bool IsValid(Timestamp timestamp) {
|
||||
return timestamp.IsFinite();
|
||||
}
|
||||
|
||||
double ToKiloBytes(DataSize datasize) { return datasize.bytes() / 1000.0; }
|
||||
|
||||
struct PacketResultsSummary {
|
||||
int num_packets = 0;
|
||||
int num_lost_packets = 0;
|
||||
DataSize total_size = DataSize::Zero();
|
||||
DataSize lost_size = DataSize::Zero();
|
||||
Timestamp first_send_time = Timestamp::PlusInfinity();
|
||||
Timestamp last_send_time = Timestamp::MinusInfinity();
|
||||
};
|
||||
@ -67,6 +70,7 @@ PacketResultsSummary GetPacketResultsSummary(
|
||||
for (const PacketResult& packet : packet_results) {
|
||||
if (!packet.IsReceived()) {
|
||||
packet_results_summary.num_lost_packets++;
|
||||
packet_results_summary.lost_size += packet.sent_packet.size;
|
||||
}
|
||||
packet_results_summary.total_size += packet.sent_packet.size;
|
||||
packet_results_summary.first_send_time = std::min(
|
||||
@ -444,6 +448,8 @@ absl::optional<LossBasedBweV2::Config> LossBasedBweV2::CreateConfig(
|
||||
FieldTrialParameter<bool> use_padding_for_increase("UsePadding", false);
|
||||
|
||||
FieldTrialParameter<double> hold_duration_factor("HoldDurationFactor", 0.0);
|
||||
FieldTrialParameter<bool> use_byte_loss_rate("UseByteLossRate", false);
|
||||
|
||||
if (key_value_config) {
|
||||
ParseFieldTrial({&enabled,
|
||||
&bandwidth_rampup_upper_bound_factor,
|
||||
@ -482,7 +488,8 @@ absl::optional<LossBasedBweV2::Config> LossBasedBweV2::CreateConfig(
|
||||
&min_num_observations,
|
||||
&lower_bound_by_acked_rate_factor,
|
||||
&use_padding_for_increase,
|
||||
&hold_duration_factor},
|
||||
&hold_duration_factor,
|
||||
&use_byte_loss_rate},
|
||||
key_value_config->Lookup("WebRTC-Bwe-LossBasedBweV2"));
|
||||
}
|
||||
|
||||
@ -546,6 +553,7 @@ absl::optional<LossBasedBweV2::Config> LossBasedBweV2::CreateConfig(
|
||||
lower_bound_by_acked_rate_factor.Get();
|
||||
config->use_padding_for_increase = use_padding_for_increase.Get();
|
||||
config->hold_duration_factor = hold_duration_factor.Get();
|
||||
config->use_byte_loss_rate = use_byte_loss_rate.Get();
|
||||
|
||||
return config;
|
||||
}
|
||||
@ -742,6 +750,11 @@ bool LossBasedBweV2::IsConfigValid() const {
|
||||
}
|
||||
|
||||
double LossBasedBweV2::GetAverageReportedLossRatio() const {
|
||||
return config_->use_byte_loss_rate ? GetAverageReportedByteLossRatio()
|
||||
: GetAverageReportedPacketLossRatio();
|
||||
}
|
||||
|
||||
double LossBasedBweV2::GetAverageReportedPacketLossRatio() const {
|
||||
if (num_observations_ <= 0) {
|
||||
return 0.0;
|
||||
}
|
||||
@ -763,6 +776,27 @@ double LossBasedBweV2::GetAverageReportedLossRatio() const {
|
||||
return num_lost_packets / num_packets;
|
||||
}
|
||||
|
||||
double LossBasedBweV2::GetAverageReportedByteLossRatio() const {
|
||||
if (num_observations_ <= 0) {
|
||||
return 0.0;
|
||||
}
|
||||
|
||||
DataSize total_bytes = DataSize::Zero();
|
||||
DataSize lost_bytes = DataSize::Zero();
|
||||
for (const Observation& observation : observations_) {
|
||||
if (!observation.IsInitialized()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
double instant_temporal_weight =
|
||||
instant_upper_bound_temporal_weights_[(num_observations_ - 1) -
|
||||
observation.id];
|
||||
total_bytes += instant_temporal_weight * observation.size;
|
||||
lost_bytes += instant_temporal_weight * observation.lost_size;
|
||||
}
|
||||
return lost_bytes / total_bytes;
|
||||
}
|
||||
|
||||
DataRate LossBasedBweV2::GetCandidateBandwidthUpperBound() const {
|
||||
DataRate candidate_bandwidth_upper_bound = max_bitrate_;
|
||||
if (IsInLossLimitedState() && IsValid(bandwidth_limit_in_current_window_)) {
|
||||
@ -846,16 +880,29 @@ LossBasedBweV2::Derivatives LossBasedBweV2::GetDerivatives(
|
||||
|
||||
double temporal_weight =
|
||||
temporal_weights_[(num_observations_ - 1) - observation.id];
|
||||
|
||||
derivatives.first +=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets / loss_probability) -
|
||||
(observation.num_received_packets / (1.0 - loss_probability)));
|
||||
derivatives.second -=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets / std::pow(loss_probability, 2)) +
|
||||
(observation.num_received_packets /
|
||||
std::pow(1.0 - loss_probability, 2)));
|
||||
if (config_->use_byte_loss_rate) {
|
||||
derivatives.first +=
|
||||
temporal_weight *
|
||||
((ToKiloBytes(observation.lost_size) / loss_probability) -
|
||||
(ToKiloBytes(observation.size - observation.lost_size) /
|
||||
(1.0 - loss_probability)));
|
||||
derivatives.second -=
|
||||
temporal_weight *
|
||||
((ToKiloBytes(observation.lost_size) /
|
||||
std::pow(loss_probability, 2)) +
|
||||
(ToKiloBytes(observation.size - observation.lost_size) /
|
||||
std::pow(1.0 - loss_probability, 2)));
|
||||
} else {
|
||||
derivatives.first +=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets / loss_probability) -
|
||||
(observation.num_received_packets / (1.0 - loss_probability)));
|
||||
derivatives.second -=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets / std::pow(loss_probability, 2)) +
|
||||
(observation.num_received_packets /
|
||||
std::pow(1.0 - loss_probability, 2)));
|
||||
}
|
||||
}
|
||||
|
||||
if (derivatives.second >= 0.0) {
|
||||
@ -927,13 +974,23 @@ double LossBasedBweV2::GetObjective(
|
||||
|
||||
double temporal_weight =
|
||||
temporal_weights_[(num_observations_ - 1) - observation.id];
|
||||
|
||||
objective +=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets * std::log(loss_probability)) +
|
||||
(observation.num_received_packets * std::log(1.0 - loss_probability)));
|
||||
objective +=
|
||||
temporal_weight * high_bandwidth_bias * observation.num_packets;
|
||||
if (config_->use_byte_loss_rate) {
|
||||
objective +=
|
||||
temporal_weight *
|
||||
((ToKiloBytes(observation.lost_size) * std::log(loss_probability)) +
|
||||
(ToKiloBytes(observation.size - observation.lost_size) *
|
||||
std::log(1.0 - loss_probability)));
|
||||
objective +=
|
||||
temporal_weight * high_bandwidth_bias * ToKiloBytes(observation.size);
|
||||
} else {
|
||||
objective +=
|
||||
temporal_weight *
|
||||
((observation.num_lost_packets * std::log(loss_probability)) +
|
||||
(observation.num_received_packets *
|
||||
std::log(1.0 - loss_probability)));
|
||||
objective +=
|
||||
temporal_weight * high_bandwidth_bias * observation.num_packets;
|
||||
}
|
||||
}
|
||||
|
||||
return objective;
|
||||
@ -1036,6 +1093,7 @@ bool LossBasedBweV2::PushBackObservation(
|
||||
partial_observation_.num_lost_packets +=
|
||||
packet_results_summary.num_lost_packets;
|
||||
partial_observation_.size += packet_results_summary.total_size;
|
||||
partial_observation_.lost_size += packet_results_summary.lost_size;
|
||||
|
||||
// This is the first packet report we have received.
|
||||
if (!IsValid(last_send_time_most_recent_observation_)) {
|
||||
@ -1061,6 +1119,8 @@ bool LossBasedBweV2::PushBackObservation(
|
||||
observation.num_packets - observation.num_lost_packets;
|
||||
observation.sending_rate =
|
||||
GetSendingRate(partial_observation_.size / observation_duration);
|
||||
observation.lost_size = partial_observation_.lost_size;
|
||||
observation.size = partial_observation_.size;
|
||||
observation.id = num_observations_++;
|
||||
observations_[observation.id % config_->observation_window_size] =
|
||||
observation;
|
||||
|
||||
@ -120,6 +120,7 @@ class LossBasedBweV2 {
|
||||
double lower_bound_by_acked_rate_factor = 0.0;
|
||||
bool use_padding_for_increase = false;
|
||||
double hold_duration_factor = 0.0;
|
||||
bool use_byte_loss_rate = false;
|
||||
};
|
||||
|
||||
struct Derivatives {
|
||||
@ -134,6 +135,8 @@ class LossBasedBweV2 {
|
||||
int num_lost_packets = 0;
|
||||
int num_received_packets = 0;
|
||||
DataRate sending_rate = DataRate::MinusInfinity();
|
||||
DataSize size = DataSize::Zero();
|
||||
DataSize lost_size = DataSize::Zero();
|
||||
int id = -1;
|
||||
};
|
||||
|
||||
@ -141,6 +144,7 @@ class LossBasedBweV2 {
|
||||
int num_packets = 0;
|
||||
int num_lost_packets = 0;
|
||||
DataSize size = DataSize::Zero();
|
||||
DataSize lost_size = DataSize::Zero();
|
||||
};
|
||||
|
||||
static absl::optional<Config> CreateConfig(
|
||||
@ -149,6 +153,8 @@ class LossBasedBweV2 {
|
||||
|
||||
// Returns `0.0` if not enough loss statistics have been received.
|
||||
double GetAverageReportedLossRatio() const;
|
||||
double GetAverageReportedPacketLossRatio() const;
|
||||
double GetAverageReportedByteLossRatio() const;
|
||||
std::vector<ChannelParameters> GetCandidates(bool in_alr) const;
|
||||
DataRate GetCandidateBandwidthUpperBound() const;
|
||||
Derivatives GetDerivatives(const ChannelParameters& channel_parameters) const;
|
||||
|
||||
@ -31,6 +31,7 @@ using ::webrtc::test::ExplicitKeyValueConfig;
|
||||
constexpr TimeDelta kObservationDurationLowerBound = TimeDelta::Millis(250);
|
||||
constexpr TimeDelta kDelayedIncreaseWindow = TimeDelta::Millis(300);
|
||||
constexpr double kMaxIncreaseFactor = 1.5;
|
||||
constexpr int kPacketSize = 15'000;
|
||||
|
||||
class LossBasedBweV2Test : public ::testing::TestWithParam<bool> {
|
||||
protected:
|
||||
@ -90,8 +91,8 @@ class LossBasedBweV2Test : public ::testing::TestWithParam<bool> {
|
||||
std::vector<PacketResult> CreatePacketResultsWithReceivedPackets(
|
||||
Timestamp first_packet_timestamp) {
|
||||
std::vector<PacketResult> enough_feedback(2);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[0].sent_packet.send_time = first_packet_timestamp;
|
||||
enough_feedback[1].sent_packet.send_time =
|
||||
first_packet_timestamp + kObservationDurationLowerBound;
|
||||
@ -102,12 +103,13 @@ class LossBasedBweV2Test : public ::testing::TestWithParam<bool> {
|
||||
return enough_feedback;
|
||||
}
|
||||
|
||||
std::vector<PacketResult> CreatePacketResultsWith10pLossRate(
|
||||
Timestamp first_packet_timestamp) {
|
||||
std::vector<PacketResult> CreatePacketResultsWith10pPacketLossRate(
|
||||
Timestamp first_packet_timestamp,
|
||||
DataSize lost_packet_size = DataSize::Bytes(kPacketSize)) {
|
||||
std::vector<PacketResult> enough_feedback(10);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
for (unsigned i = 0; i < enough_feedback.size(); ++i) {
|
||||
enough_feedback[i].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[i].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[i].sent_packet.send_time =
|
||||
first_packet_timestamp +
|
||||
static_cast<int>(i) * kObservationDurationLowerBound;
|
||||
@ -116,14 +118,15 @@ class LossBasedBweV2Test : public ::testing::TestWithParam<bool> {
|
||||
static_cast<int>(i + 1) * kObservationDurationLowerBound;
|
||||
}
|
||||
enough_feedback[9].receive_time = Timestamp::PlusInfinity();
|
||||
enough_feedback[9].sent_packet.size = lost_packet_size;
|
||||
return enough_feedback;
|
||||
}
|
||||
|
||||
std::vector<PacketResult> CreatePacketResultsWith50pLossRate(
|
||||
std::vector<PacketResult> CreatePacketResultsWith50pPacketLossRate(
|
||||
Timestamp first_packet_timestamp) {
|
||||
std::vector<PacketResult> enough_feedback(2);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[0].sent_packet.send_time = first_packet_timestamp;
|
||||
enough_feedback[1].sent_packet.send_time =
|
||||
first_packet_timestamp + kObservationDurationLowerBound;
|
||||
@ -136,8 +139,8 @@ class LossBasedBweV2Test : public ::testing::TestWithParam<bool> {
|
||||
std::vector<PacketResult> CreatePacketResultsWith100pLossRate(
|
||||
Timestamp first_packet_timestamp) {
|
||||
std::vector<PacketResult> enough_feedback(2);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(15'000);
|
||||
enough_feedback[0].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[1].sent_packet.size = DataSize::Bytes(kPacketSize);
|
||||
enough_feedback[0].sent_packet.send_time = first_packet_timestamp;
|
||||
enough_feedback[1].sent_packet.send_time =
|
||||
first_packet_timestamp + kObservationDurationLowerBound;
|
||||
@ -461,7 +464,7 @@ TEST_F(LossBasedBweV2Test, UseAckedBitrateForEmegencyBackOff) {
|
||||
// Create two packet results, first packet has 50% loss rate, second packet
|
||||
// has 100% loss rate.
|
||||
std::vector<PacketResult> enough_feedback_1 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
std::vector<PacketResult> enough_feedback_2 =
|
||||
CreatePacketResultsWith100pLossRate(
|
||||
@ -814,7 +817,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
CreatePacketResultsWithReceivedPackets(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
std::vector<PacketResult> enough_feedback_2 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kDelayedIncreaseWindow - TimeDelta::Millis(2));
|
||||
std::vector<PacketResult> enough_feedback_3 =
|
||||
@ -913,7 +916,7 @@ TEST_F(LossBasedBweV2Test, NotIncreaseIfInherentLossLessThanAverageLoss) {
|
||||
DataRate::KilobitsPerSec(600));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_1 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_10p_loss_1,
|
||||
@ -921,7 +924,7 @@ TEST_F(LossBasedBweV2Test, NotIncreaseIfInherentLossLessThanAverageLoss) {
|
||||
/*in_alr=*/false);
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_2 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -947,7 +950,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
DataRate::KilobitsPerSec(600));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_1 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_10p_loss_1, delay_based_estimate,
|
||||
@ -955,7 +958,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
/*in_alr=*/false);
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_2 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -981,7 +984,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
DataRate::KilobitsPerSec(600));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_1 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_10p_loss_1, delay_based_estimate,
|
||||
@ -989,7 +992,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
/*in_alr=*/false);
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_2 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -1017,7 +1020,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
DataRate::KilobitsPerSec(600));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_1 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_10p_loss_1, delay_based_estimate,
|
||||
@ -1025,7 +1028,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
/*in_alr=*/false);
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_2 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -1053,7 +1056,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
DataRate::KilobitsPerSec(600));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_50p_loss_1 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_50p_loss_1, delay_based_estimate,
|
||||
@ -1061,7 +1064,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
/*in_alr=*/false);
|
||||
|
||||
std::vector<PacketResult> enough_feedback_50p_loss_2 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -1327,7 +1330,7 @@ TEST_F(LossBasedBweV2Test, HasDecreaseStateBecauseOfUpperBound) {
|
||||
DataRate::KilobitsPerSec(500));
|
||||
|
||||
std::vector<PacketResult> enough_feedback_10p_loss_1 =
|
||||
CreatePacketResultsWith10pLossRate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_10p_loss_1,
|
||||
@ -1357,7 +1360,7 @@ TEST_F(LossBasedBweV2Test, HasIncreaseStateBecauseOfLowerBound) {
|
||||
|
||||
// Network has a high loss to create a loss scenario.
|
||||
std::vector<PacketResult> enough_feedback_50p_loss_1 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero());
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
enough_feedback_50p_loss_1,
|
||||
@ -1371,7 +1374,7 @@ TEST_F(LossBasedBweV2Test, HasIncreaseStateBecauseOfLowerBound) {
|
||||
loss_based_bandwidth_estimator.SetAcknowledgedBitrate(
|
||||
DataRate::KilobitsPerSec(200));
|
||||
std::vector<PacketResult> enough_feedback_50p_loss_2 =
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound);
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
@ -1398,7 +1401,7 @@ TEST_F(LossBasedBweV2Test,
|
||||
loss_based_bandwidth_estimator.SetAcknowledgedBitrate(
|
||||
DataRate::KilobitsPerSec(150));
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero()),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/true);
|
||||
@ -1439,7 +1442,7 @@ TEST_F(LossBasedBweV2Test, HasDelayBasedStateIfLossBasedBweIsMax) {
|
||||
DataRate::KilobitsPerSec(1000));
|
||||
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
/*feedback=*/CreatePacketResultsWith50pLossRate(
|
||||
/*feedback=*/CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound),
|
||||
/*delay_based_estimate=*/DataRate::KilobitsPerSec(2000),
|
||||
@ -1474,7 +1477,7 @@ TEST_F(LossBasedBweV2Test, IncreaseUsingPaddingStateIfFieldTrial) {
|
||||
loss_based_bandwidth_estimator.SetBandwidthEstimate(
|
||||
DataRate::KilobitsPerSec(2500));
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero()),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/false);
|
||||
@ -1498,7 +1501,7 @@ TEST_F(LossBasedBweV2Test, IncreaseEstimateIfNotHold) {
|
||||
loss_based_bandwidth_estimator.SetBandwidthEstimate(
|
||||
DataRate::KilobitsPerSec(2500));
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero()),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/false);
|
||||
@ -1527,7 +1530,7 @@ TEST_F(LossBasedBweV2Test, IncreaseEstimateAfterHoldDuration) {
|
||||
loss_based_bandwidth_estimator.SetBandwidthEstimate(
|
||||
DataRate::KilobitsPerSec(2500));
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero()),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/false);
|
||||
@ -1564,7 +1567,7 @@ TEST_F(LossBasedBweV2Test, IncreaseEstimateAfterHoldDuration) {
|
||||
|
||||
// Get another 50p packet loss.
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero() +
|
||||
kObservationDurationLowerBound * 3),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
@ -1610,7 +1613,7 @@ TEST_F(LossBasedBweV2Test, EndHoldDurationIfDelayBasedEstimateWorks) {
|
||||
loss_based_bandwidth_estimator.SetBandwidthEstimate(
|
||||
DataRate::KilobitsPerSec(2500));
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith50pLossRate(
|
||||
CreatePacketResultsWith50pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero()),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/false);
|
||||
@ -1632,5 +1635,26 @@ TEST_F(LossBasedBweV2Test, EndHoldDurationIfDelayBasedEstimateWorks) {
|
||||
estimate + DataRate::KilobitsPerSec(10));
|
||||
}
|
||||
|
||||
TEST_F(LossBasedBweV2Test, UseByteLossRate) {
|
||||
ExplicitKeyValueConfig key_value_config(
|
||||
ShortObservationConfig("UseByteLossRate:true"));
|
||||
LossBasedBweV2 loss_based_bandwidth_estimator(&key_value_config);
|
||||
loss_based_bandwidth_estimator.SetBandwidthEstimate(
|
||||
DataRate::KilobitsPerSec(500));
|
||||
// Create packet feedback having 10% packet loss but more than 50% byte loss.
|
||||
loss_based_bandwidth_estimator.UpdateBandwidthEstimate(
|
||||
CreatePacketResultsWith10pPacketLossRate(
|
||||
/*first_packet_timestamp=*/Timestamp::Zero(),
|
||||
/*lost_packet_size=*/DataSize::Bytes(kPacketSize * 20)),
|
||||
/*delay_based_estimate=*/DataRate::PlusInfinity(),
|
||||
/*in_alr=*/false);
|
||||
EXPECT_EQ(loss_based_bandwidth_estimator.GetLossBasedResult().state,
|
||||
LossBasedState::kDecreasing);
|
||||
// The estimate is bounded by the instant upper bound due to high loss.
|
||||
EXPECT_LT(
|
||||
loss_based_bandwidth_estimator.GetLossBasedResult().bandwidth_estimate,
|
||||
DataRate::KilobitsPerSec(150));
|
||||
}
|
||||
|
||||
} // namespace
|
||||
} // namespace webrtc
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user