Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(302)

Unified Diff: webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc

Issue 2510583002: Reland #2 of Issue 2434073003: Extract bitrate allocation ... (Closed)
Patch Set: Addressed comments Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc
diff --git a/webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc b/webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc
index b9721cde1bcc6b6b9bb31a3962db0dfe0c3deb2f..a3e65e4ce0d8c159f6ec68ea7bbf407338d4bfc5 100644
--- a/webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc
+++ b/webrtc/modules/video_coding/codecs/vp8/realtime_temporal_layers.cc
@@ -12,6 +12,8 @@
#include "vpx/vpx_encoder.h"
#include "vpx/vp8cx.h"
+#include "webrtc/base/checks.h"
+#include "webrtc/base/optional.h"
#include "webrtc/modules/video_coding/include/video_codec_interface.h"
#include "webrtc/modules/video_coding/codecs/vp8/include/vp8_common_types.h"
#include "webrtc/modules/video_coding/codecs/vp8/temporal_layers.h"
@@ -95,26 +97,20 @@ class RealTimeTemporalLayers : public TemporalLayers {
layer_ids_(NULL),
encode_flags_length_(0),
encode_flags_(NULL) {
- assert(max_temporal_layers_ >= 1);
- assert(max_temporal_layers_ <= 3);
+ RTC_CHECK_GE(max_temporal_layers_, 1);
+ RTC_CHECK_GE(max_temporal_layers_, 3);
}
virtual ~RealTimeTemporalLayers() {}
- bool ConfigureBitrates(int bitrate_kbit,
- int max_bitrate_kbit,
- int framerate,
- vpx_codec_enc_cfg_t* cfg) override {
+ std::vector<uint32_t> OnRatesUpdated(int bitrate_kbps,
+ int max_bitrate_kbps,
+ int framerate) override {
temporal_layers_ =
CalculateNumberOfTemporalLayers(temporal_layers_, framerate);
temporal_layers_ = std::min(temporal_layers_, max_temporal_layers_);
- assert(temporal_layers_ >= 1 && temporal_layers_ <= 3);
-
- cfg->ts_number_layers = temporal_layers_;
- for (int tl = 0; tl < temporal_layers_; ++tl) {
- cfg->ts_target_bitrate[tl] =
- bitrate_kbit * kVp8LayerRateAlloction[temporal_layers_ - 1][tl];
- }
+ RTC_CHECK_GE(temporal_layers_, 1);
+ RTC_CHECK_LE(temporal_layers_, 3);
switch (temporal_layers_) {
case 1: {
@@ -125,9 +121,6 @@ class RealTimeTemporalLayers : public TemporalLayers {
static const int encode_flags[] = {kTemporalUpdateLastRefAll};
encode_flags_length_ = sizeof(encode_flags) / sizeof(*layer_ids);
encode_flags_ = encode_flags;
-
- cfg->ts_rate_decimator[0] = 1;
- cfg->ts_periodicity = layer_ids_length_;
} break;
case 2: {
@@ -146,10 +139,6 @@ class RealTimeTemporalLayers : public TemporalLayers {
kTemporalUpdateNone};
encode_flags_length_ = sizeof(encode_flags) / sizeof(*layer_ids);
encode_flags_ = encode_flags;
-
- cfg->ts_rate_decimator[0] = 2;
- cfg->ts_rate_decimator[1] = 1;
- cfg->ts_periodicity = layer_ids_length_;
} break;
case 3: {
@@ -168,19 +157,59 @@ class RealTimeTemporalLayers : public TemporalLayers {
kTemporalUpdateNone};
encode_flags_length_ = sizeof(encode_flags) / sizeof(*layer_ids);
encode_flags_ = encode_flags;
-
- cfg->ts_rate_decimator[0] = 4;
- cfg->ts_rate_decimator[1] = 2;
- cfg->ts_rate_decimator[2] = 1;
- cfg->ts_periodicity = layer_ids_length_;
} break;
default:
- assert(false);
- return false;
+ RTC_NOTREACHED();
+ return std::vector<uint32_t>();
+ }
+
+ std::vector<uint32_t> bitrates;
+ const int num_layers = std::max(1, temporal_layers_);
+ for (int i = 0; i < num_layers; ++i) {
+ float layer_bitrate =
+ bitrate_kbps * kVp8LayerRateAlloction[num_layers - 1][i];
+ bitrates.push_back(static_cast<uint32_t>(layer_bitrate + 0.5));
+ }
+ new_bitrates_kbps_ = rtc::Optional<std::vector<uint32_t>>(bitrates);
+
+ // Allocation table is of aggregates, transform to individual rates.
+ uint32_t sum = 0;
+ for (int i = 0; i < num_layers; ++i) {
+ uint32_t layer_bitrate = bitrates[i];
+ RTC_DCHECK_LE(sum, bitrates[i]);
+ bitrates[i] -= sum;
+ sum += layer_bitrate;
+
+ if (sum == static_cast<uint32_t>(bitrate_kbps)) {
+ // Sum adds up; any subsequent layers will be 0.
+ bitrates.resize(i);
+ break;
+ }
+ }
+
+ return bitrates;
+ }
+
+ bool UpdateConfiguration(vpx_codec_enc_cfg_t* cfg) override {
+ if (!new_bitrates_kbps_)
+ return false;
+
+ cfg->ts_number_layers = temporal_layers_;
+ for (int tl = 0; tl < temporal_layers_; ++tl) {
+ cfg->ts_target_bitrate[tl] = (*new_bitrates_kbps_)[tl];
}
+ new_bitrates_kbps_ = rtc::Optional<std::vector<uint32_t>>();
+
+ cfg->ts_periodicity = layer_ids_length_;
+ int decimator = 1;
+ for (int i = temporal_layers_ - 1; i >= 0; --i, decimator *= 2) {
+ cfg->ts_rate_decimator[i] = decimator;
+ }
+
memcpy(cfg->ts_layer_id, layer_ids_,
sizeof(unsigned int) * layer_ids_length_);
+
return true;
}
@@ -248,8 +277,6 @@ class RealTimeTemporalLayers : public TemporalLayers {
void FrameEncoded(unsigned int size, uint32_t timestamp, int qp) override {}
- bool UpdateConfiguration(vpx_codec_enc_cfg_t* cfg) override { return false; }
-
private:
int temporal_layers_;
int max_temporal_layers_;
@@ -266,12 +293,19 @@ class RealTimeTemporalLayers : public TemporalLayers {
// Pattern of encode flags.
int encode_flags_length_;
const int* encode_flags_;
+
+ rtc::Optional<std::vector<uint32_t>> new_bitrates_kbps_;
};
} // namespace
TemporalLayers* RealTimeTemporalLayersFactory::Create(
+ int simulcast_id,
int max_temporal_layers,
uint8_t initial_tl0_pic_idx) const {
- return new RealTimeTemporalLayers(max_temporal_layers, initial_tl0_pic_idx);
+ TemporalLayers* tl =
+ new RealTimeTemporalLayers(max_temporal_layers, initial_tl0_pic_idx);
+ if (listener_)
+ listener_->OnTemporalLayersCreated(simulcast_id, tl);
+ return tl;
}
} // namespace webrtc

Powered by Google App Engine
This is Rietveld 408576698