congestion_controller.cc revision 4fbd145dcefd23169a9b1612d5ca92dace8196d6
19ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org/*
29ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
39ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *
49ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  Use of this source code is governed by a BSD-style license
59ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  that can be found in the LICENSE file in the root of the source
69ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  tree. An additional intellectual property rights grant can be found
79ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  in the file PATENTS.  All contributing project authors may
89ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org *  be found in the AUTHORS file in the root of the source tree.
99ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org */
109ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org
1129b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/vie_channel_group.h"
129ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org
13a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org#include "webrtc/base/checks.h"
1438344ed2806c8fed60d67d280ca44c32e36707c0pbos@webrtc.org#include "webrtc/base/thread_annotations.h"
1529b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/common.h"
16e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer#include "webrtc/modules/pacing/include/paced_sender.h"
17e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer#include "webrtc/modules/pacing/include/packet_router.h"
18867fb5224e1ba6a1c2cd523c005499a93ed61a08sprang#include "webrtc/modules/remote_bitrate_estimator/include/send_time_history.h"
19468e62a97426a8d001e9187f3ca1d1e43f80b970Erik Språng#include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_abs_send_time.h"
20468e62a97426a8d001e9187f3ca1d1e43f80b970Erik Språng#include "webrtc/modules/remote_bitrate_estimator/remote_bitrate_estimator_single_stream.h"
216b8d3551681f40b880507cecc88f478a12383cc7Erik Språng#include "webrtc/modules/remote_bitrate_estimator/remote_estimator_proxy.h"
225e023eb337eed9746ecea7fc6fbb0fca386f1961sprang#include "webrtc/modules/remote_bitrate_estimator/transport_feedback_adapter.h"
2329b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/modules/rtp_rtcp/interface/rtp_rtcp.h"
2429b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/modules/utility/interface/process_thread.h"
25a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org#include "webrtc/system_wrappers/interface/critical_section_wrapper.h"
265574dacd1f83d8ac83458d27e54be6507f3a06a4mflodman@webrtc.org#include "webrtc/system_wrappers/interface/logging.h"
2729b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/call_stats.h"
2829b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/encoder_state_feedback.h"
29a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org#include "webrtc/video_engine/payload_router.h"
3029b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/vie_channel.h"
3129b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/vie_encoder.h"
3229b2219914a059fe5164c312e7cc6d1bf0b4e610andresp@webrtc.org#include "webrtc/video_engine/vie_remb.h"
33a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org#include "webrtc/voice_engine/include/voe_video_sync.h"
349ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org
359ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.orgnamespace webrtc {
36a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.orgnamespace {
37a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
385ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.orgstatic const uint32_t kTimeOffsetSwitchThreshold = 30;
395ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org
40a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.orgclass WrappingBitrateEstimator : public RemoteBitrateEstimator {
41a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org public:
42ef35f069e739feaae16fdfcc815d7af5cb05e9aepbos  WrappingBitrateEstimator(RemoteBitrateObserver* observer, Clock* clock)
43a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org      : observer_(observer),
44a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org        clock_(clock),
45a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org        crit_sect_(CriticalSectionWrapper::CreateCriticalSection()),
464fbd145dcefd23169a9b1612d5ca92dace8196d6stefan        rbe_(new RemoteBitrateEstimatorSingleStream(observer_, clock_)),
475ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org        using_absolute_send_time_(false),
484fbd145dcefd23169a9b1612d5ca92dace8196d6stefan        packets_since_absolute_send_time_(0),
494fbd145dcefd23169a9b1612d5ca92dace8196d6stefan        min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps) {}
50a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
511295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org  virtual ~WrappingBitrateEstimator() {}
521295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org
5314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  void IncomingPacket(int64_t arrival_time_ms,
5414665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org                      size_t payload_size,
55ff4ea9310e981da6292fb044cff9eeefd986cf2bStefan Holmer                      const RTPHeader& header,
56ff4ea9310e981da6292fb044cff9eeefd986cf2bStefan Holmer                      bool was_paced) override {
57a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
58a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org    PickEstimatorFromHeader(header);
59ff4ea9310e981da6292fb044cff9eeefd986cf2bStefan Holmer    rbe_->IncomingPacket(arrival_time_ms, payload_size, header, was_paced);
60a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
61a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
6214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  int32_t Process() override {
631295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
641295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org    return rbe_->Process();
65a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
66a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
6714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  int64_t TimeUntilNextProcess() override {
681295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
691295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org    return rbe_->TimeUntilNextProcess();
70a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
71a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
722328a94ec7ee545a26e8220c5ae157e1b3b5144fstefan  void OnRttUpdate(int64_t avg_rtt_ms, int64_t max_rtt_ms) override {
73a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
742328a94ec7ee545a26e8220c5ae157e1b3b5144fstefan    rbe_->OnRttUpdate(avg_rtt_ms, max_rtt_ms);
75a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
76a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
7714665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  void RemoveStream(unsigned int ssrc) override {
78a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
79a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    rbe_->RemoveStream(ssrc);
80a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
81a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
8214665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  bool LatestEstimate(std::vector<unsigned int>* ssrcs,
8314665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org                      unsigned int* bitrate_bps) const override {
84a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
85a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org    return rbe_->LatestEstimate(ssrcs, bitrate_bps);
86a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  }
87a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
8814665ff7d4024d07e58622f498b23fd980001871kjellander@webrtc.org  bool GetStats(ReceiveBandwidthEstimatorStats* output) const override {
891f64f067840212b3e5b67a0d6a50bcd805b5bc1ajiayl@webrtc.org    CriticalSectionScoped cs(crit_sect_.get());
901f64f067840212b3e5b67a0d6a50bcd805b5bc1ajiayl@webrtc.org    return rbe_->GetStats(output);
911f64f067840212b3e5b67a0d6a50bcd805b5bc1ajiayl@webrtc.org  }
921f64f067840212b3e5b67a0d6a50bcd805b5bc1ajiayl@webrtc.org
934fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  void SetMinBitrate(int min_bitrate_bps) {
944fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    CriticalSectionScoped cs(crit_sect_.get());
954fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    rbe_->SetMinBitrate(min_bitrate_bps);
964fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    min_bitrate_bps_ = min_bitrate_bps;
974fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  }
984fbd145dcefd23169a9b1612d5ca92dace8196d6stefan
99a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org private:
100a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org  void PickEstimatorFromHeader(const RTPHeader& header)
101a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org      EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) {
1025ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org    if (header.extension.hasAbsoluteSendTime) {
1035ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      // If we see AST in header, switch RBE strategy immediately.
1045ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      if (!using_absolute_send_time_) {
1055574dacd1f83d8ac83458d27e54be6507f3a06a4mflodman@webrtc.org        LOG(LS_INFO) <<
1065574dacd1f83d8ac83458d27e54be6507f3a06a4mflodman@webrtc.org            "WrappingBitrateEstimator: Switching to absolute send time RBE.";
1075ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org        using_absolute_send_time_ = true;
108a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org        PickEstimator();
1095ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      }
1105ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      packets_since_absolute_send_time_ = 0;
1115ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org    } else {
1125ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      // When we don't see AST, wait for a few packets before going back to TOF.
1135ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      if (using_absolute_send_time_) {
1145ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org        ++packets_since_absolute_send_time_;
1155ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org        if (packets_since_absolute_send_time_ >= kTimeOffsetSwitchThreshold) {
1165574dacd1f83d8ac83458d27e54be6507f3a06a4mflodman@webrtc.org          LOG(LS_INFO) << "WrappingBitrateEstimator: Switching to transmission "
1175574dacd1f83d8ac83458d27e54be6507f3a06a4mflodman@webrtc.org                       << "time offset RBE.";
1185ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org          using_absolute_send_time_ = false;
119a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org          PickEstimator();
1205ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org        }
1215ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org      }
1225ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org    }
1235ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org  }
1245ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org
125a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org  // Instantiate RBE for Time Offset or Absolute Send Time extensions.
126a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org  void PickEstimator() EXCLUSIVE_LOCKS_REQUIRED(crit_sect_.get()) {
127a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org    if (using_absolute_send_time_) {
1284fbd145dcefd23169a9b1612d5ca92dace8196d6stefan      rbe_.reset(new RemoteBitrateEstimatorAbsSendTime(observer_, clock_));
129a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org    } else {
1304fbd145dcefd23169a9b1612d5ca92dace8196d6stefan      rbe_.reset(new RemoteBitrateEstimatorSingleStream(observer_, clock_));
131a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org    }
1324fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    rbe_->SetMinBitrate(min_bitrate_bps_);
133a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org  }
134a16147c03726e54b2ecb1e48c7171a33d83a5261stefan@webrtc.org
135a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  RemoteBitrateObserver* observer_;
136a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org  Clock* clock_;
13700b8f6b3643332cce1ee711715f7fbb824d793cakwiberg@webrtc.org  rtc::scoped_ptr<CriticalSectionWrapper> crit_sect_;
13800b8f6b3643332cce1ee711715f7fbb824d793cakwiberg@webrtc.org  rtc::scoped_ptr<RemoteBitrateEstimator> rbe_;
1395ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org  bool using_absolute_send_time_;
1405ab756703ea32f2c2ff9878d6eae628c7380bc14pbos@webrtc.org  uint32_t packets_since_absolute_send_time_;
1414fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  int min_bitrate_bps_;
142a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
1433c089d751ede283e21e186885eaf705c3257ccd2henrikg  RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(WrappingBitrateEstimator);
144a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org};
145867fb5224e1ba6a1c2cd523c005499a93ed61a08sprang
146a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org}  // namespace
1479ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org
1482251d6e17438e1a085ff4f88ad19de513214bec1Peter BoströmChannelGroup::ChannelGroup(ProcessThread* process_thread)
149b5865079868c4dec49571e7aef0aa52124b50c64stefan@webrtc.org    : remb_(new VieRemb()),
150792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org      bitrate_allocator_(new BitrateAllocator()),
1517c894b7cc718773f32d21985ff33a64f9e13946emflodman@webrtc.org      call_stats_(new CallStats()),
152e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      packet_router_(new PacketRouter()),
153e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      pacer_(new PacedSender(Clock::GetRealTimeClock(),
154e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer                             packet_router_.get(),
155e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer                             BitrateController::kDefaultStartBitrateKbps,
156e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer                             PacedSender::kDefaultPaceMultiplier *
157e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer                                 BitrateController::kDefaultStartBitrateKbps,
158e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer                             0)),
1596b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      remote_bitrate_estimator_(
1606b8d3551681f40b880507cecc88f478a12383cc7Erik Språng          new WrappingBitrateEstimator(remb_.get(), Clock::GetRealTimeClock())),
1616b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      remote_estimator_proxy_(
1626b8d3551681f40b880507cecc88f478a12383cc7Erik Språng          new RemoteEstimatorProxy(Clock::GetRealTimeClock(),
1636b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                                   packet_router_.get())),
1646b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      encoder_state_feedback_(new EncoderStateFeedback()),
165e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      process_thread_(process_thread),
166847855b865987524be768c7771959f927db25808stefan      pacer_thread_(ProcessThread::Create("PacerThread")),
167e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      // Constructed last as this object calls the provided callback on
168e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      // construction.
169e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      bitrate_controller_(
170e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer          BitrateController::CreateBitrateController(Clock::GetRealTimeClock(),
1714fbd145dcefd23169a9b1612d5ca92dace8196d6stefan                                                     this)),
1724fbd145dcefd23169a9b1612d5ca92dace8196d6stefan      min_bitrate_bps_(RemoteBitrateEstimator::kDefaultMinBitrateBps) {
1731295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org  call_stats_->RegisterStatsObserver(remote_bitrate_estimator_.get());
17444caf01c34d4fddec039f917c83fed7e0ce977b2andresp@webrtc.org
175e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  pacer_thread_->RegisterModule(pacer_.get());
176e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  pacer_thread_->Start();
177e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer
1786b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  process_thread->RegisterModule(remote_estimator_proxy_.get());
1791295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org  process_thread->RegisterModule(remote_bitrate_estimator_.get());
1807c894b7cc718773f32d21985ff33a64f9e13946emflodman@webrtc.org  process_thread->RegisterModule(call_stats_.get());
18144caf01c34d4fddec039f917c83fed7e0ce977b2andresp@webrtc.org  process_thread->RegisterModule(bitrate_controller_.get());
18249888ce42858e308c7b0575697f06e2483a34daepwestin@webrtc.org}
1839ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org
1849ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.orgChannelGroup::~ChannelGroup() {
185e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  pacer_thread_->Stop();
186e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  pacer_thread_->DeRegisterModule(pacer_.get());
18744caf01c34d4fddec039f917c83fed7e0ce977b2andresp@webrtc.org  process_thread_->DeRegisterModule(bitrate_controller_.get());
1886cd201cf31dc8e50bf815139b0c9fdc83d3ba2bfandrew@webrtc.org  process_thread_->DeRegisterModule(call_stats_.get());
1891295dc6a237a7c2d2cb0dbfd53c57babf1034901andresp@webrtc.org  process_thread_->DeRegisterModule(remote_bitrate_estimator_.get());
1906b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  process_thread_->DeRegisterModule(remote_estimator_proxy_.get());
19144caf01c34d4fddec039f917c83fed7e0ce977b2andresp@webrtc.org  call_stats_->DeregisterStatsObserver(remote_bitrate_estimator_.get());
1926b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  if (transport_feedback_adapter_.get())
1936b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    call_stats_->DeregisterStatsObserver(transport_feedback_adapter_.get());
19491d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg  RTC_DCHECK(channel_map_.empty());
19591d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg  RTC_DCHECK(!remb_->InUse());
19691d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg  RTC_DCHECK(vie_encoder_map_.empty());
197a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
198a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
199a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgbool ChannelGroup::CreateSendChannel(int channel_id,
2002251d6e17438e1a085ff4f88ad19de513214bec1Peter Boström                                     Transport* transport,
2017083e119e8f39d2ec9e504461c1bb6e0bc6be5ffPeter Boström                                     SendStatisticsProxy* stats_proxy,
2027083e119e8f39d2ec9e504461c1bb6e0bc6be5ffPeter Boström                                     I420FrameCallback* pre_encode_callback,
2035a3ebd761cb2789aa63e4ae7c0035234a3e3b5f3Peter Boström                                     int number_of_cores,
2046b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                                     const VideoSendStream::Config& config) {
2056b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  TransportFeedbackObserver* transport_feedback_observer = nullptr;
2066b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  bool transport_seq_enabled = false;
2076b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  for (const RtpExtension& extension : config.rtp.extensions) {
2086b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    if (extension.name == RtpExtension::kTransportSequenceNumber) {
2096b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      transport_seq_enabled = true;
2106b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      break;
2116b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    }
2126b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  }
2136b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  if (transport_seq_enabled) {
2146b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    if (transport_feedback_adapter_.get() == nullptr) {
2156b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      transport_feedback_adapter_.reset(new TransportFeedbackAdapter(
2166b8d3551681f40b880507cecc88f478a12383cc7Erik Språng          bitrate_controller_->CreateRtcpBandwidthObserver(),
2176b8d3551681f40b880507cecc88f478a12383cc7Erik Språng          Clock::GetRealTimeClock(), process_thread_));
2186b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      transport_feedback_adapter_->SetBitrateEstimator(
2196b8d3551681f40b880507cecc88f478a12383cc7Erik Språng          new RemoteBitrateEstimatorAbsSendTime(
2204fbd145dcefd23169a9b1612d5ca92dace8196d6stefan              transport_feedback_adapter_.get(), Clock::GetRealTimeClock()));
2214fbd145dcefd23169a9b1612d5ca92dace8196d6stefan      transport_feedback_adapter_->GetBitrateEstimator()->SetMinBitrate(
2224fbd145dcefd23169a9b1612d5ca92dace8196d6stefan          min_bitrate_bps_);
2236b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      call_stats_->RegisterStatsObserver(transport_feedback_adapter_.get());
2246b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    }
2256b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    transport_feedback_observer = transport_feedback_adapter_.get();
2266b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  }
2276b8d3551681f40b880507cecc88f478a12383cc7Erik Språng
2286b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  const std::vector<uint32_t>& ssrcs = config.rtp.ssrcs;
22991d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg  RTC_DCHECK(!ssrcs.empty());
2307083e119e8f39d2ec9e504461c1bb6e0bc6be5ffPeter Boström  rtc::scoped_ptr<ViEEncoder> vie_encoder(new ViEEncoder(
2317083e119e8f39d2ec9e504461c1bb6e0bc6be5ffPeter Boström      channel_id, number_of_cores, process_thread_, stats_proxy,
2327083e119e8f39d2ec9e504461c1bb6e0bc6be5ffPeter Boström      pre_encode_callback, pacer_.get(), bitrate_allocator_.get()));
233a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  if (!vie_encoder->Init()) {
234a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    return false;
235a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
236a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ViEEncoder* encoder = vie_encoder.get();
237ac547a653862744d0aae560713f8418ad2852085Peter Boström  if (!CreateChannel(channel_id, transport, number_of_cores,
2386b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                     vie_encoder.release(), ssrcs.size(), true,
2396b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                     remote_bitrate_estimator_.get(),
2406b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                     transport_feedback_observer)) {
241a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    return false;
242a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
243a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ViEChannel* channel = channel_map_[channel_id];
244a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  // Connect the encoder with the send packet router, to enable sending.
245a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  encoder->StartThreadsAndSetSharedMembers(channel->send_payload_router(),
246a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org                                           channel->vcm_protection_callback());
247a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
248a753177f93872a069353f8674d51ca4898b55cb5Peter Boström  encoder_state_feedback_->AddEncoder(ssrcs, encoder);
249a753177f93872a069353f8674d51ca4898b55cb5Peter Boström  std::vector<uint32_t> first_ssrc(1, ssrcs[0]);
250a753177f93872a069353f8674d51ca4898b55cb5Peter Boström  encoder->SetSsrcs(first_ssrc);
251a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  return true;
252a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
253a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
2546b8d3551681f40b880507cecc88f478a12383cc7Erik Språngbool ChannelGroup::CreateReceiveChannel(
2556b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    int channel_id,
2566b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    Transport* transport,
2576b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    int number_of_cores,
2586b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    const VideoReceiveStream::Config& config) {
2596b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  bool send_side_bwe = false;
2606b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  for (const RtpExtension& extension : config.rtp.extensions) {
2616b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    if (extension.name == RtpExtension::kTransportSequenceNumber) {
2626b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      send_side_bwe = true;
2636b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      break;
2646b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    }
2656b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  }
2666b8d3551681f40b880507cecc88f478a12383cc7Erik Språng
2676b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  RemoteBitrateEstimator* bitrate_estimator;
2686b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  if (send_side_bwe) {
2696b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    bitrate_estimator = remote_estimator_proxy_.get();
2706b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  } else {
2716b8d3551681f40b880507cecc88f478a12383cc7Erik Språng    bitrate_estimator = remote_bitrate_estimator_.get();
2726b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  }
2736b8d3551681f40b880507cecc88f478a12383cc7Erik Språng  return CreateChannel(channel_id, transport, number_of_cores, nullptr, 1,
2746b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                       false, bitrate_estimator, nullptr);
275a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
276a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
277a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgbool ChannelGroup::CreateChannel(int channel_id,
2782251d6e17438e1a085ff4f88ad19de513214bec1Peter Boström                                 Transport* transport,
279a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org                                 int number_of_cores,
280a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org                                 ViEEncoder* vie_encoder,
281d6f1a38165455d743fbe61f6980f22be6a3c4de9Peter Boström                                 size_t max_rtp_streams,
2826b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                                 bool sender,
2836b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                                 RemoteBitrateEstimator* bitrate_estimator,
2846b8d3551681f40b880507cecc88f478a12383cc7Erik Språng                                 TransportFeedbackObserver* feedback_observer) {
285a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  rtc::scoped_ptr<ViEChannel> channel(new ViEChannel(
286ac547a653862744d0aae560713f8418ad2852085Peter Boström      number_of_cores, transport, process_thread_,
287ef35f069e739feaae16fdfcc815d7af5cb05e9aepbos      encoder_state_feedback_->GetRtcpIntraFrameObserver(),
2886b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      bitrate_controller_->CreateRtcpBandwidthObserver(), feedback_observer,
2896b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      bitrate_estimator, call_stats_->rtcp_rtt_stats(), pacer_.get(),
2906b8d3551681f40b880507cecc88f478a12383cc7Erik Språng      packet_router_.get(), max_rtp_streams, sender));
291a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  if (channel->Init() != 0) {
292a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    return false;
293a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
294a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
295a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  // Register the channel to receive stats updates.
296a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  call_stats_->RegisterStatsObserver(channel->GetStatsObserver());
297a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
298a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  // Store the channel, add it to the channel group and save the vie_encoder.
299a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  channel_map_[channel_id] = channel.release();
300d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  if (vie_encoder) {
301d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    rtc::CritScope lock(&encoder_map_crit_);
302e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer    vie_encoder_map_[channel_id] = vie_encoder;
303e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  }
304a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
305a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  return true;
306a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
307a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
308a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgvoid ChannelGroup::DeleteChannel(int channel_id) {
309a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ViEChannel* vie_channel = PopChannel(channel_id);
310a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
311a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ViEEncoder* vie_encoder = GetEncoder(channel_id);
312a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
313a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  call_stats_->DeregisterStatsObserver(vie_channel->GetStatsObserver());
31476c53d36bc455fe89ca1f860d5171633198fe907Peter Boström  SetChannelRembStatus(false, false, vie_channel);
315a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
316d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  // If we're a sender, remove the feedback and stop all encoding threads and
317d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  // processing. This must be done before deleting the channel.
318d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  if (vie_encoder) {
319a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    encoder_state_feedback_->RemoveEncoder(vie_encoder);
320a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    vie_encoder->StopThreadsAndRemoveSharedMembers();
321a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
322a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
323a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  unsigned int remote_ssrc = 0;
324a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  vie_channel->GetRemoteSSRC(&remote_ssrc);
325d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  channel_map_.erase(channel_id);
326a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  remote_bitrate_estimator_->RemoveStream(remote_ssrc);
327a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
328a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  delete vie_channel;
329d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos
330a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  if (vie_encoder) {
331d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    {
332d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos      rtc::CritScope lock(&encoder_map_crit_);
333d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos      vie_encoder_map_.erase(vie_encoder_map_.find(channel_id));
334d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    }
335a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    delete vie_encoder;
336a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
337a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
338a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  LOG(LS_VERBOSE) << "Channel deleted " << channel_id;
3399ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org}
340a6db54d4c9a2bfc703bc208eb5cbc19505e9cef3solenberg@webrtc.org
341a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgViEChannel* ChannelGroup::GetChannel(int channel_id) const {
342a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ChannelMap::const_iterator it = channel_map_.find(channel_id);
343a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  if (it == channel_map_.end()) {
344a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    LOG(LS_ERROR) << "Channel doesn't exist " << channel_id;
345a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    return NULL;
346a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  }
347a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  return it->second;
348a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
349a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
350a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgViEEncoder* ChannelGroup::GetEncoder(int channel_id) const {
351d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  rtc::CritScope lock(&encoder_map_crit_);
352a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  EncoderMap::const_iterator it = vie_encoder_map_.find(channel_id);
353d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  if (it == vie_encoder_map_.end())
354d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    return nullptr;
355a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  return it->second;
356a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
357a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
358a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgViEChannel* ChannelGroup::PopChannel(int channel_id) {
359a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ChannelMap::iterator c_it = channel_map_.find(channel_id);
36091d6edef35e7275879c30ce16ecb8b6dc73c6e4ahenrikg  RTC_DCHECK(c_it != channel_map_.end());
361a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  ViEChannel* channel = c_it->second;
362a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  channel_map_.erase(c_it);
363a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
364a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org  return channel;
365a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org}
366a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org
367a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgvoid ChannelGroup::SetSyncInterface(VoEVideoSync* sync_interface) {
368d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos  for (auto channel : channel_map_)
369a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.org    channel.second->SetVoiceChannel(-1, sync_interface);
370792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org}
371792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org
3724fbd145dcefd23169a9b1612d5ca92dace8196d6stefanvoid ChannelGroup::SetBweBitrates(int min_bitrate_bps,
3734fbd145dcefd23169a9b1612d5ca92dace8196d6stefan                                  int start_bitrate_bps,
3744fbd145dcefd23169a9b1612d5ca92dace8196d6stefan                                  int max_bitrate_bps) {
3754fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  if (start_bitrate_bps > 0)
3764fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    bitrate_controller_->SetStartBitrate(start_bitrate_bps);
3774fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  bitrate_controller_->SetMinMaxBitrate(min_bitrate_bps, max_bitrate_bps);
3784fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  if (remote_bitrate_estimator_.get())
3794fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    remote_bitrate_estimator_->SetMinBitrate(min_bitrate_bps);
3804fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  if (transport_feedback_adapter_.get())
3814fbd145dcefd23169a9b1612d5ca92dace8196d6stefan    transport_feedback_adapter_->GetBitrateEstimator()->SetMinBitrate(
3824fbd145dcefd23169a9b1612d5ca92dace8196d6stefan        min_bitrate_bps);
3834fbd145dcefd23169a9b1612d5ca92dace8196d6stefan  min_bitrate_bps_ = min_bitrate_bps;
3844fbd145dcefd23169a9b1612d5ca92dace8196d6stefan}
3854fbd145dcefd23169a9b1612d5ca92dace8196d6stefan
386a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgBitrateController* ChannelGroup::GetBitrateController() const {
387cb89c6f91491e683e47e5505536c154c905d5194bjornv@webrtc.org  return bitrate_controller_.get();
388f72881406fba86adc2d649bb1caee0d5604f9339stefan@webrtc.org}
389f72881406fba86adc2d649bb1caee0d5604f9339stefan@webrtc.org
390a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgRemoteBitrateEstimator* ChannelGroup::GetRemoteBitrateEstimator() const {
3919354cc965c04a0c79ea36622043751596a6fd015stefan@webrtc.org  return remote_bitrate_estimator_.get();
3929354cc965c04a0c79ea36622043751596a6fd015stefan@webrtc.org}
3939354cc965c04a0c79ea36622043751596a6fd015stefan@webrtc.org
394a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgCallStats* ChannelGroup::GetCallStats() const {
3957c894b7cc718773f32d21985ff33a64f9e13946emflodman@webrtc.org  return call_stats_.get();
3967c894b7cc718773f32d21985ff33a64f9e13946emflodman@webrtc.org}
3977c894b7cc718773f32d21985ff33a64f9e13946emflodman@webrtc.org
398a50e6f073deecfd9004e6e4946eabd8c34621608stefan@webrtc.orgEncoderStateFeedback* ChannelGroup::GetEncoderStateFeedback() const {
399aca26292aeb35c91e70dd22d5923bf74ce68fa30mflodman@webrtc.org  return encoder_state_feedback_.get();
400aca26292aeb35c91e70dd22d5923bf74ce68fa30mflodman@webrtc.org}
401aca26292aeb35c91e70dd22d5923bf74ce68fa30mflodman@webrtc.org
402e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmerint64_t ChannelGroup::GetPacerQueuingDelayMs() const {
403e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  return pacer_->QueueInMs();
404e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer}
405e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer
40676c53d36bc455fe89ca1f860d5171633198fe907Peter Boströmvoid ChannelGroup::SetChannelRembStatus(bool sender,
407d16e839c6d29831e79312180085b6a19149df43fpbos@webrtc.org                                        bool receiver,
408d16e839c6d29831e79312180085b6a19149df43fpbos@webrtc.org                                        ViEChannel* channel) {
4099ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  // Update the channel state.
410d16e839c6d29831e79312180085b6a19149df43fpbos@webrtc.org  channel->EnableRemb(sender || receiver);
4119354cc965c04a0c79ea36622043751596a6fd015stefan@webrtc.org  // Update the REMB instance with necessary RTP modules.
4129ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  RtpRtcp* rtp_module = channel->rtp_rtcp();
4139ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  if (sender) {
4149ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org    remb_->AddRembSender(rtp_module);
4159ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  } else {
4169ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org    remb_->RemoveRembSender(rtp_module);
4179ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  }
4189ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  if (receiver) {
4199ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org    remb_->AddReceiveChannel(rtp_module);
4209ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  } else {
4219ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org    remb_->RemoveReceiveChannel(rtp_module);
4229ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org  }
4239ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org}
424792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org
425792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.orgvoid ChannelGroup::OnNetworkChanged(uint32_t target_bitrate_bps,
426792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org                                    uint8_t fraction_loss,
427792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org                                    int64_t rtt) {
428792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org  bitrate_allocator_->OnNetworkChanged(target_bitrate_bps, fraction_loss, rtt);
429e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  int pad_up_to_bitrate_bps = 0;
430e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  {
431d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    rtc::CritScope lock(&encoder_map_crit_);
432d6fc47ea9585fa405d8617ccc0b7704d2c9e8a0apbos    for (const auto& encoder : vie_encoder_map_)
433a4a8d4ad27bd0bd7a6cc5df697951d4531ddb4eestefan      pad_up_to_bitrate_bps += encoder.second->GetPaddingNeededBps();
434e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  }
435e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer  pacer_->UpdateBitrate(
436e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      target_bitrate_bps / 1000,
437e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      PacedSender::kDefaultPaceMultiplier * target_bitrate_bps / 1000,
438e59041672283a28bde0b043c0c2bc198272f82e1Stefan Holmer      pad_up_to_bitrate_bps / 1000);
439792f1a14e2b62382c5c6080d0b8fdc5c89d27bc6stefan@webrtc.org}
4409ec883e8bd334acfc246741f7a2cca3e55d7f5b2mflodman@webrtc.org}  // namespace webrtc
441