• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2016 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 #include "modules/congestion_controller/goog_cc/alr_detector.h"
12 
13 #include <cstdint>
14 #include <cstdio>
15 #include <memory>
16 
17 #include "api/rtc_event_log/rtc_event.h"
18 #include "api/rtc_event_log/rtc_event_log.h"
19 #include "logging/rtc_event_log/events/rtc_event_alr_state.h"
20 #include "rtc_base/checks.h"
21 #include "rtc_base/numerics/safe_conversions.h"
22 #include "rtc_base/time_utils.h"
23 
24 namespace webrtc {
25 
26 namespace {
GetConfigFromTrials(const WebRtcKeyValueConfig * key_value_config)27 AlrDetectorConfig GetConfigFromTrials(
28     const WebRtcKeyValueConfig* key_value_config) {
29   RTC_CHECK(AlrExperimentSettings::MaxOneFieldTrialEnabled(*key_value_config));
30   absl::optional<AlrExperimentSettings> experiment_settings =
31       AlrExperimentSettings::CreateFromFieldTrial(
32           *key_value_config,
33           AlrExperimentSettings::kScreenshareProbingBweExperimentName);
34   if (!experiment_settings) {
35     experiment_settings = AlrExperimentSettings::CreateFromFieldTrial(
36         *key_value_config,
37         AlrExperimentSettings::kStrictPacingAndProbingExperimentName);
38   }
39   AlrDetectorConfig conf;
40   if (experiment_settings) {
41     conf.bandwidth_usage_ratio =
42         experiment_settings->alr_bandwidth_usage_percent / 100.0;
43     conf.start_budget_level_ratio =
44         experiment_settings->alr_start_budget_level_percent / 100.0;
45     conf.stop_budget_level_ratio =
46         experiment_settings->alr_stop_budget_level_percent / 100.0;
47   }
48   conf.Parser()->Parse(
49       key_value_config->Lookup("WebRTC-AlrDetectorParameters"));
50   return conf;
51 }
52 }  //  namespace
53 
Parser()54 std::unique_ptr<StructParametersParser> AlrDetectorConfig::Parser() {
55   return StructParametersParser::Create(   //
56       "bw_usage", &bandwidth_usage_ratio,  //
57       "start", &start_budget_level_ratio,  //
58       "stop", &stop_budget_level_ratio);
59 }
60 
AlrDetector(AlrDetectorConfig config,RtcEventLog * event_log)61 AlrDetector::AlrDetector(AlrDetectorConfig config, RtcEventLog* event_log)
62     : conf_(config), alr_budget_(0, true), event_log_(event_log) {}
63 
AlrDetector(const WebRtcKeyValueConfig * key_value_config)64 AlrDetector::AlrDetector(const WebRtcKeyValueConfig* key_value_config)
65     : AlrDetector(GetConfigFromTrials(key_value_config), nullptr) {}
66 
AlrDetector(const WebRtcKeyValueConfig * key_value_config,RtcEventLog * event_log)67 AlrDetector::AlrDetector(const WebRtcKeyValueConfig* key_value_config,
68                          RtcEventLog* event_log)
69     : AlrDetector(GetConfigFromTrials(key_value_config), event_log) {}
~AlrDetector()70 AlrDetector::~AlrDetector() {}
71 
OnBytesSent(size_t bytes_sent,int64_t send_time_ms)72 void AlrDetector::OnBytesSent(size_t bytes_sent, int64_t send_time_ms) {
73   if (!last_send_time_ms_.has_value()) {
74     last_send_time_ms_ = send_time_ms;
75     // Since the duration for sending the bytes is unknwon, return without
76     // updating alr state.
77     return;
78   }
79   int64_t delta_time_ms = send_time_ms - *last_send_time_ms_;
80   last_send_time_ms_ = send_time_ms;
81 
82   alr_budget_.UseBudget(bytes_sent);
83   alr_budget_.IncreaseBudget(delta_time_ms);
84   bool state_changed = false;
85   if (alr_budget_.budget_ratio() > conf_.start_budget_level_ratio &&
86       !alr_started_time_ms_) {
87     alr_started_time_ms_.emplace(rtc::TimeMillis());
88     state_changed = true;
89   } else if (alr_budget_.budget_ratio() < conf_.stop_budget_level_ratio &&
90              alr_started_time_ms_) {
91     state_changed = true;
92     alr_started_time_ms_.reset();
93   }
94   if (event_log_ && state_changed) {
95     event_log_->Log(
96         std::make_unique<RtcEventAlrState>(alr_started_time_ms_.has_value()));
97   }
98 }
99 
SetEstimatedBitrate(int bitrate_bps)100 void AlrDetector::SetEstimatedBitrate(int bitrate_bps) {
101   RTC_DCHECK(bitrate_bps);
102   int target_rate_kbps =
103       static_cast<double>(bitrate_bps) * conf_.bandwidth_usage_ratio / 1000;
104   alr_budget_.set_target_rate_kbps(target_rate_kbps);
105 }
106 
GetApplicationLimitedRegionStartTime() const107 absl::optional<int64_t> AlrDetector::GetApplicationLimitedRegionStartTime()
108     const {
109   return alr_started_time_ms_;
110 }
111 
112 }  // namespace webrtc
113