Add AlrDetector
This is a simple application limited region detector that is quite conservative at the moment. We detect as being application-limited if we see sending rate as less than 30% of the estimated bandwidth over 500 ms. The moment we detect a single burst above 30% over a 100 ms period, we consider ourselves network limited. This class is currently not used. A follow up CL will leverage this to enable probing. BUG=webrtc:6332 Review-Url: https://codereview.webrtc.org/2340763004 Cr-Commit-Position: refs/heads/master@{#14505}
This commit is contained in:
parent
52f6f2057c
commit
3168781d2f
@ -382,6 +382,7 @@ if (rtc_include_tests) {
|
||||
"congestion_controller/transport_feedback_adapter_unittest.cc",
|
||||
"media_file/media_file_unittest.cc",
|
||||
"module_common_types_unittest.cc",
|
||||
"pacing/alr_detector_unittest.cc",
|
||||
"pacing/bitrate_prober_unittest.cc",
|
||||
"pacing/paced_sender_unittest.cc",
|
||||
"pacing/packet_router_unittest.cc",
|
||||
|
||||
@ -10,6 +10,8 @@ import("../../build/webrtc.gni")
|
||||
|
||||
rtc_static_library("pacing") {
|
||||
sources = [
|
||||
"alr_detector.cc",
|
||||
"alr_detector.h",
|
||||
"bitrate_prober.cc",
|
||||
"bitrate_prober.h",
|
||||
"paced_sender.cc",
|
||||
|
||||
80
webrtc/modules/pacing/alr_detector.cc
Normal file
80
webrtc/modules/pacing/alr_detector.cc
Normal file
@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Copyright (c) 2016 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.
|
||||
*/
|
||||
|
||||
#include "webrtc/modules/pacing/alr_detector.h"
|
||||
|
||||
#include "webrtc/base/checks.h"
|
||||
#include "webrtc/base/logging.h"
|
||||
|
||||
namespace {
|
||||
|
||||
// Time period over which outgoing traffic is measured and considered a single
|
||||
// data point.
|
||||
constexpr int kMeasurementPeriodMs = 100;
|
||||
|
||||
// Minimum number of consecutive measurements over |kMeasurementPeriodMs| time
|
||||
// that indicate sending rate is below |kUsagePercent| to consider being
|
||||
// application limited.
|
||||
constexpr int kApplicationLimitedThreshold = 5;
|
||||
|
||||
// Sent traffic percentage as a function of network capaicty to consider traffic
|
||||
// as application limited.
|
||||
// NOTE: This is intentionally conservative at the moment until BW adjustments
|
||||
// of application limited region is fine tuned.
|
||||
constexpr int kUsagePercent = 30;
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
AlrDetector::AlrDetector()
|
||||
: measurement_interval_bytes_sent_(0),
|
||||
measurement_interval_elapsed_time_ms_(0),
|
||||
estimated_bitrate_bps_(0),
|
||||
application_limited_count_(0) {}
|
||||
|
||||
AlrDetector::~AlrDetector() {}
|
||||
|
||||
void AlrDetector::OnBytesSent(size_t bytes_sent, int64_t elapsed_time_ms) {
|
||||
if (measurement_interval_elapsed_time_ms_ > kMeasurementPeriodMs) {
|
||||
RTC_DCHECK(estimated_bitrate_bps_);
|
||||
int max_bytes =
|
||||
(measurement_interval_elapsed_time_ms_ * estimated_bitrate_bps_) /
|
||||
(8 * 1000);
|
||||
RTC_DCHECK_GT(max_bytes, 0);
|
||||
int utilization =
|
||||
static_cast<int>((measurement_interval_bytes_sent_ * 100) / max_bytes);
|
||||
if (utilization < kUsagePercent) {
|
||||
application_limited_count_++;
|
||||
if (application_limited_count_ == kApplicationLimitedThreshold)
|
||||
LOG(LS_INFO) << "ALR start";
|
||||
} else {
|
||||
if (application_limited_count_ >= kApplicationLimitedThreshold)
|
||||
LOG(LS_INFO) << "ALR stop";
|
||||
application_limited_count_ = 0;
|
||||
}
|
||||
measurement_interval_elapsed_time_ms_ = elapsed_time_ms;
|
||||
measurement_interval_bytes_sent_ = bytes_sent;
|
||||
} else {
|
||||
measurement_interval_elapsed_time_ms_ += elapsed_time_ms;
|
||||
measurement_interval_bytes_sent_ += bytes_sent;
|
||||
}
|
||||
}
|
||||
|
||||
void AlrDetector::SetEstimatedBitrate(int bitrate_bps) {
|
||||
RTC_DCHECK(bitrate_bps);
|
||||
estimated_bitrate_bps_ = bitrate_bps;
|
||||
}
|
||||
|
||||
bool AlrDetector::InApplicationLimitedRegion() {
|
||||
return application_limited_count_ >= kApplicationLimitedThreshold;
|
||||
}
|
||||
|
||||
} // namespace webrtc
|
||||
48
webrtc/modules/pacing/alr_detector.h
Normal file
48
webrtc/modules/pacing/alr_detector.h
Normal file
@ -0,0 +1,48 @@
|
||||
/*
|
||||
* Copyright (c) 2016 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_MODULES_PACING_ALR_DETECTOR_H_
|
||||
#define WEBRTC_MODULES_PACING_ALR_DETECTOR_H_
|
||||
|
||||
#include "webrtc/common_types.h"
|
||||
#include "webrtc/modules/pacing/paced_sender.h"
|
||||
#include "webrtc/typedefs.h"
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
// Application limited region detector is a class that utilizes signals of
|
||||
// elapsed time and bytes sent to estimate whether network traffic is
|
||||
// currently limited by the application's ability to generate traffic.
|
||||
//
|
||||
// AlrDetector provides a signal that can be utilized to adjust
|
||||
// estimate bandwidth.
|
||||
// Note: This class is not thread-safe.
|
||||
class AlrDetector {
|
||||
public:
|
||||
AlrDetector();
|
||||
~AlrDetector();
|
||||
void OnBytesSent(size_t bytes_sent, int64_t elapsed_time_ms);
|
||||
// Set current estimated bandwidth.
|
||||
void SetEstimatedBitrate(int bitrate_bps);
|
||||
// Returns true if currently in application-limited region.
|
||||
bool InApplicationLimitedRegion();
|
||||
|
||||
private:
|
||||
size_t measurement_interval_bytes_sent_;
|
||||
int64_t measurement_interval_elapsed_time_ms_;
|
||||
int estimated_bitrate_bps_;
|
||||
// Number of consecutive periods over which we observe traffic is application
|
||||
// limited.
|
||||
int application_limited_count_;
|
||||
};
|
||||
|
||||
} // namespace webrtc
|
||||
|
||||
#endif // WEBRTC_MODULES_PACING_ALR_DETECTOR_H_
|
||||
48
webrtc/modules/pacing/alr_detector_unittest.cc
Normal file
48
webrtc/modules/pacing/alr_detector_unittest.cc
Normal file
@ -0,0 +1,48 @@
|
||||
/*
|
||||
* Copyright (c) 2016 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.
|
||||
*/
|
||||
|
||||
#include "webrtc/test/gtest.h"
|
||||
#include "webrtc/modules/pacing/alr_detector.h"
|
||||
|
||||
namespace {
|
||||
|
||||
constexpr int kMeasuredIntervalMs = 110;
|
||||
constexpr int kEstimatedBitrateBps = 300000;
|
||||
constexpr int kBytesInIntervalAtEstimatedBitrate =
|
||||
(kEstimatedBitrateBps / 8) * kMeasuredIntervalMs / 1000;
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
TEST(AlrDetectorTest, ApplicationLimitedWhenLittleDataSent) {
|
||||
AlrDetector alr_detector;
|
||||
|
||||
alr_detector.SetEstimatedBitrate(kEstimatedBitrateBps);
|
||||
for (int i = 0; i < 6; i++)
|
||||
alr_detector.OnBytesSent(0, kMeasuredIntervalMs);
|
||||
EXPECT_EQ(alr_detector.InApplicationLimitedRegion(), true);
|
||||
|
||||
for (int i = 0; i < 6; i++)
|
||||
alr_detector.OnBytesSent(100, kMeasuredIntervalMs);
|
||||
EXPECT_EQ(alr_detector.InApplicationLimitedRegion(), true);
|
||||
}
|
||||
|
||||
TEST(AlrDetectorTest, NetworkLimitedWhenSendingCloseToEstimate) {
|
||||
AlrDetector alr_detector;
|
||||
|
||||
alr_detector.SetEstimatedBitrate(kEstimatedBitrateBps);
|
||||
for (int i = 0; i < 6; i++)
|
||||
alr_detector.OnBytesSent(kBytesInIntervalAtEstimatedBitrate,
|
||||
kMeasuredIntervalMs);
|
||||
EXPECT_EQ(alr_detector.InApplicationLimitedRegion(), false);
|
||||
}
|
||||
|
||||
} // namespace webrtc
|
||||
@ -19,6 +19,7 @@
|
||||
#include "webrtc/base/checks.h"
|
||||
#include "webrtc/base/logging.h"
|
||||
#include "webrtc/modules/include/module_common_types.h"
|
||||
#include "webrtc/modules/pacing/alr_detector.h"
|
||||
#include "webrtc/modules/pacing/bitrate_prober.h"
|
||||
#include "webrtc/system_wrappers/include/clock.h"
|
||||
#include "webrtc/system_wrappers/include/critical_section_wrapper.h"
|
||||
@ -248,6 +249,7 @@ const float PacedSender::kDefaultPaceMultiplier = 2.5f;
|
||||
PacedSender::PacedSender(Clock* clock, PacketSender* packet_sender)
|
||||
: clock_(clock),
|
||||
packet_sender_(packet_sender),
|
||||
alr_detector_(new AlrDetector()),
|
||||
critsect_(CriticalSectionWrapper::CreateCriticalSection()),
|
||||
paused_(false),
|
||||
media_budget_(new paced_sender::IntervalBudget(0)),
|
||||
@ -260,7 +262,7 @@ PacedSender::PacedSender(Clock* clock, PacketSender* packet_sender)
|
||||
time_last_update_us_(clock->TimeInMicroseconds()),
|
||||
packets_(new paced_sender::PacketQueue(clock)),
|
||||
packet_counter_(0) {
|
||||
UpdateBytesPerInterval(kMinPacketLimitMs);
|
||||
UpdateBudgetWithElapsedTime(kMinPacketLimitMs);
|
||||
}
|
||||
|
||||
PacedSender::~PacedSender() {}
|
||||
@ -298,6 +300,7 @@ void PacedSender::SetEstimatedBitrate(uint32_t bitrate_bps) {
|
||||
pacing_bitrate_kbps_ =
|
||||
std::max(min_send_bitrate_kbps_, estimated_bitrate_bps_ / 1000) *
|
||||
kDefaultPaceMultiplier;
|
||||
alr_detector_->SetEstimatedBitrate(bitrate_bps);
|
||||
}
|
||||
|
||||
void PacedSender::SetSendBitrateLimits(int min_send_bitrate_bps,
|
||||
@ -397,8 +400,8 @@ void PacedSender::Process() {
|
||||
|
||||
media_budget_->set_target_rate_kbps(target_bitrate_kbps);
|
||||
|
||||
int64_t delta_time_ms = std::min(kMaxIntervalTimeMs, elapsed_time_ms);
|
||||
UpdateBytesPerInterval(delta_time_ms);
|
||||
elapsed_time_ms = std::min(kMaxIntervalTimeMs, elapsed_time_ms);
|
||||
UpdateBudgetWithElapsedTime(elapsed_time_ms);
|
||||
}
|
||||
|
||||
bool is_probing = prober_->IsProbing();
|
||||
@ -443,6 +446,7 @@ void PacedSender::Process() {
|
||||
}
|
||||
if (is_probing && bytes_sent > 0)
|
||||
prober_->ProbeSent(clock_->TimeInMilliseconds(), bytes_sent);
|
||||
alr_detector_->OnBytesSent(bytes_sent, elapsed_time_ms);
|
||||
}
|
||||
|
||||
bool PacedSender::SendPacket(const paced_sender::Packet& packet,
|
||||
@ -469,8 +473,7 @@ bool PacedSender::SendPacket(const paced_sender::Packet& packet,
|
||||
// are allocating bandwidth for audio.
|
||||
if (packet.priority != kHighPriority) {
|
||||
// Update media bytes sent.
|
||||
media_budget_->UseBudget(packet.bytes);
|
||||
padding_budget_->UseBudget(packet.bytes);
|
||||
UpdateBudgetWithBytesSent(packet.bytes);
|
||||
}
|
||||
}
|
||||
|
||||
@ -484,14 +487,18 @@ size_t PacedSender::SendPadding(size_t padding_needed, int probe_cluster_id) {
|
||||
critsect_->Enter();
|
||||
|
||||
if (bytes_sent > 0) {
|
||||
media_budget_->UseBudget(bytes_sent);
|
||||
padding_budget_->UseBudget(bytes_sent);
|
||||
UpdateBudgetWithBytesSent(bytes_sent);
|
||||
}
|
||||
return bytes_sent;
|
||||
}
|
||||
|
||||
void PacedSender::UpdateBytesPerInterval(int64_t delta_time_ms) {
|
||||
void PacedSender::UpdateBudgetWithElapsedTime(int64_t delta_time_ms) {
|
||||
media_budget_->IncreaseBudget(delta_time_ms);
|
||||
padding_budget_->IncreaseBudget(delta_time_ms);
|
||||
}
|
||||
|
||||
void PacedSender::UpdateBudgetWithBytesSent(size_t bytes_sent) {
|
||||
media_budget_->UseBudget(bytes_sent);
|
||||
padding_budget_->UseBudget(bytes_sent);
|
||||
}
|
||||
} // namespace webrtc
|
||||
|
||||
@ -21,6 +21,7 @@
|
||||
#include "webrtc/typedefs.h"
|
||||
|
||||
namespace webrtc {
|
||||
class AlrDetector;
|
||||
class BitrateProber;
|
||||
class Clock;
|
||||
class CriticalSectionWrapper;
|
||||
@ -132,7 +133,9 @@ class PacedSender : public Module, public RtpPacketSender {
|
||||
|
||||
private:
|
||||
// Updates the number of bytes that can be sent for the next time interval.
|
||||
void UpdateBytesPerInterval(int64_t delta_time_in_ms)
|
||||
void UpdateBudgetWithElapsedTime(int64_t delta_time_in_ms)
|
||||
EXCLUSIVE_LOCKS_REQUIRED(critsect_);
|
||||
void UpdateBudgetWithBytesSent(size_t bytes)
|
||||
EXCLUSIVE_LOCKS_REQUIRED(critsect_);
|
||||
|
||||
bool SendPacket(const paced_sender::Packet& packet, int probe_cluster_id)
|
||||
@ -142,6 +145,7 @@ class PacedSender : public Module, public RtpPacketSender {
|
||||
|
||||
Clock* const clock_;
|
||||
PacketSender* const packet_sender_;
|
||||
std::unique_ptr<AlrDetector> alr_detector_ GUARDED_BY(critsect_);
|
||||
|
||||
std::unique_ptr<CriticalSectionWrapper> critsect_;
|
||||
bool paused_ GUARDED_BY(critsect_);
|
||||
|
||||
@ -17,6 +17,8 @@
|
||||
'<(webrtc_root)/modules/modules.gyp:rtp_rtcp',
|
||||
],
|
||||
'sources': [
|
||||
'alr_detector.cc',
|
||||
'alr_detector.h',
|
||||
'bitrate_prober.cc',
|
||||
'bitrate_prober.h',
|
||||
'paced_sender.cc',
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user