blob: d7de52711c834f6a7aa3256ce1fe3f9d31d2c1f5 [file] [log] [blame]
pbos@webrtc.org9115cde2014-12-09 10:36:40 +00001/* Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
Ilya Nikolaevskiybf352982017-10-02 10:08:25 +02002 *
3 * Use of this source code is governed by a BSD-style license
4 * that can be found in the LICENSE file in the root of the source
5 * tree. An additional intellectual property rights grant can be found
6 * in the file PATENTS. All contributing project authors may
7 * be found in the AUTHORS file in the root of the source tree.
8 */
Mirko Bonadei92ea95e2017-09-15 06:47:31 +02009#ifndef MODULES_VIDEO_CODING_CODECS_VP8_SCREENSHARE_LAYERS_H_
10#define MODULES_VIDEO_CODING_CODECS_VP8_SCREENSHARE_LAYERS_H_
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000011
Erik Språng59021ba2018-10-03 11:05:16 +020012#include <map>
13#include <memory>
philipelb19f27a2019-03-28 16:09:52 +010014#include <utility>
Erik Språng08127a92016-11-16 16:41:30 +010015#include <vector>
pbos@webrtc.orge728ee02014-12-17 13:43:55 +000016
Elad Alon411b49b2019-01-29 14:05:55 +010017#include "api/video_codecs/vp8_frame_config.h"
Erik Språng4529fbc2018-10-12 10:30:31 +020018#include "api/video_codecs/vp8_temporal_layers.h"
Erik Språng59021ba2018-10-03 11:05:16 +020019#include "modules/video_coding/codecs/vp8/include/temporal_layers_checker.h"
philipel9df33532019-03-04 16:37:50 +010020#include "modules/video_coding/include/video_codec_interface.h"
Mirko Bonadei92ea95e2017-09-15 06:47:31 +020021#include "modules/video_coding/utility/frame_dropper.h"
22#include "rtc_base/rate_statistics.h"
Steve Anton10542f22019-01-11 09:11:00 -080023#include "rtc_base/time_utils.h"
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000024
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000025namespace webrtc {
26
27struct CodecSpecificInfoVP8;
sprangb0fdfea2016-03-01 05:51:16 -080028class Clock;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000029
Elad Aloncde8ab22019-03-20 11:56:20 +010030class ScreenshareLayers final : public Vp8FrameBufferController {
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000031 public:
sprang@webrtc.org70f74f32014-12-17 10:57:10 +000032 static const double kMaxTL0FpsReduction;
33 static const double kAcceptableTargetOvershoot;
sprangafe1f742016-04-12 02:45:13 -070034 static const int kMaxFrameIntervalMs;
sprang@webrtc.org70f74f32014-12-17 10:57:10 +000035
Sebastian Janssone64a6882019-03-01 18:04:07 +010036 explicit ScreenshareLayers(int num_temporal_layers);
Erik Språngfb2a66a2018-09-10 10:48:01 +020037 ~ScreenshareLayers() override;
38
Elad Alonfb087812019-05-02 23:25:34 +020039 void SetQpLimits(size_t stream_index, int min_qp, int max_qp) override;
40
Elad Aloncde8ab22019-03-20 11:56:20 +010041 size_t StreamCount() const override;
42
43 bool SupportsEncoderFrameDropping(size_t stream_index) const override;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000044
45 // Returns the recommended VP8 encode flags needed. May refresh the decoder
46 // and/or update the reference buffers.
Elad Alon979c4422019-04-17 12:53:08 +020047 Vp8FrameConfig NextFrameConfig(size_t stream_index,
48 uint32_t rtp_timestamp) override;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000049
Erik Språngbb60a3a2018-03-19 18:25:10 +010050 // New target bitrate, per temporal layer.
Elad Aloncde8ab22019-03-20 11:56:20 +010051 void OnRatesUpdated(size_t stream_index,
52 const std::vector<uint32_t>& bitrates_bps,
Erik Språngbb60a3a2018-03-19 18:25:10 +010053 int framerate_fps) override;
Erik Språng08127a92016-11-16 16:41:30 +010054
Elad Alonfb087812019-05-02 23:25:34 +020055 Vp8EncoderConfig UpdateConfiguration(size_t stream_index) override;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000056
Elad Aloncde8ab22019-03-20 11:56:20 +010057 void OnEncodeDone(size_t stream_index,
58 uint32_t rtp_timestamp,
Erik Språng59021ba2018-10-03 11:05:16 +020059 size_t size_bytes,
60 bool is_keyframe,
61 int qp,
philipel9df33532019-03-04 16:37:50 +010062 CodecSpecificInfo* info) override;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000063
Elad Alon6796ec22019-04-15 10:07:50 +020064 void OnFrameDropped(size_t stream_index, uint32_t rtp_timestamp) override;
65
Elad Aloncde8ab22019-03-20 11:56:20 +010066 void OnPacketLossRateUpdate(float packet_loss_rate) override;
67
68 void OnRttUpdate(int64_t rtt_ms) override;
69
Elad Alon6c371ca2019-04-04 12:28:51 +020070 void OnLossNotification(
Elad Alon123ee9b2019-04-17 12:48:06 +020071 const VideoEncoder::LossNotification& loss_notification) override;
Elad Alon6c371ca2019-04-04 12:28:51 +020072
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000073 private:
sprang916170a2017-05-23 07:47:55 -070074 enum class TemporalLayerState : int { kDrop, kTl0, kTl1, kTl1Sync };
pbos51f083c2017-05-04 06:39:04 -070075
philipelb19f27a2019-03-28 16:09:52 +010076 struct DependencyInfo {
77 DependencyInfo() = default;
78 DependencyInfo(absl::string_view indication_symbols,
79 Vp8FrameConfig frame_config)
80 : decode_target_indications(
81 GenericFrameInfo::DecodeTargetInfo(indication_symbols)),
82 frame_config(frame_config) {}
83
84 absl::InlinedVector<GenericFrameInfo::DecodeTargetIndication, 10>
85 decode_target_indications;
86 Vp8FrameConfig frame_config;
87 };
88
Erik Språng2c4c9142015-06-24 11:24:44 +020089 bool TimeToSync(int64_t timestamp) const;
sprangc7805db2016-11-25 08:09:43 -080090 uint32_t GetCodecTargetBitrateKbps() const;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000091
Elad Alonfb087812019-05-02 23:25:34 +020092 const int number_of_temporal_layers_;
93
94 // TODO(eladalon/sprang): These should be made into const-int set in the ctor.
95 absl::optional<int> min_qp_;
96 absl::optional<int> max_qp_;
97
pbos@webrtc.org9115cde2014-12-09 10:36:40 +000098 int active_layer_;
Erik Språng2c4c9142015-06-24 11:24:44 +020099 int64_t last_timestamp_;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +0000100 int64_t last_sync_timestamp_;
sprangafe1f742016-04-12 02:45:13 -0700101 int64_t last_emitted_tl0_timestamp_;
Erik Språng27a457d2018-01-12 11:00:21 +0100102 int64_t last_frame_time_ms_;
Erik Språng2c4c9142015-06-24 11:24:44 +0200103 rtc::TimestampWrapAroundHandler time_wrap_handler_;
Erik Språng2c4c9142015-06-24 11:24:44 +0200104 uint32_t max_debt_bytes_;
sprangac4a90d2016-12-28 05:58:07 -0800105
philipelb19f27a2019-03-28 16:09:52 +0100106 std::map<uint32_t, DependencyInfo> pending_frame_configs_;
Erik Språng59021ba2018-10-03 11:05:16 +0200107
sprangac4a90d2016-12-28 05:58:07 -0800108 // Configured max framerate.
Danil Chapovalov0040b662018-06-18 10:48:16 +0200109 absl::optional<uint32_t> target_framerate_;
sprangac4a90d2016-12-28 05:58:07 -0800110 // Incoming framerate from capturer.
Danil Chapovalov0040b662018-06-18 10:48:16 +0200111 absl::optional<uint32_t> capture_framerate_;
philipel9df33532019-03-04 16:37:50 +0100112
sprangac4a90d2016-12-28 05:58:07 -0800113 // Tracks what framerate we actually encode, and drops frames on overshoot.
114 RateStatistics encode_framerate_;
Erik Språng08127a92016-11-16 16:41:30 +0100115 bool bitrate_updated_;
Erik Språng2c4c9142015-06-24 11:24:44 +0200116
sprang429600d2017-01-26 06:12:26 -0800117 static constexpr int kMaxNumTemporalLayers = 2;
Erik Språng2c4c9142015-06-24 11:24:44 +0200118 struct TemporalLayer {
119 TemporalLayer()
120 : state(State::kNormal),
121 enhanced_max_qp(-1),
122 last_qp(-1),
123 debt_bytes_(0),
124 target_rate_kbps_(0) {}
125
126 enum class State {
127 kNormal,
128 kDropped,
129 kReencoded,
130 kQualityBoost,
Erik Språngb75d6b82018-08-13 16:05:33 +0200131 kKeyFrame
Erik Språng2c4c9142015-06-24 11:24:44 +0200132 } state;
133
134 int enhanced_max_qp;
135 int last_qp;
136 uint32_t debt_bytes_;
137 uint32_t target_rate_kbps_;
138
139 void UpdateDebt(int64_t delta_ms);
140 } layers_[kMaxNumTemporalLayers];
sprangb0fdfea2016-03-01 05:51:16 -0800141
142 void UpdateHistograms();
philipel9df33532019-03-04 16:37:50 +0100143 TemplateStructure GetTemplateStructure(int num_layers) const;
144
sprangb0fdfea2016-03-01 05:51:16 -0800145 // Data for histogram statistics.
146 struct Stats {
147 int64_t first_frame_time_ms_ = -1;
148 int64_t num_tl0_frames_ = 0;
149 int64_t num_tl1_frames_ = 0;
150 int64_t num_dropped_frames_ = 0;
151 int64_t num_overshoots_ = 0;
152 int64_t tl0_qp_sum_ = 0;
153 int64_t tl1_qp_sum_ = 0;
154 int64_t tl0_target_bitrate_sum_ = 0;
155 int64_t tl1_target_bitrate_sum_ = 0;
156 } stats_;
Erik Språng59021ba2018-10-03 11:05:16 +0200157
Elad Alonfb087812019-05-02 23:25:34 +0200158 Vp8EncoderConfig encoder_config_;
159
Erik Språng59021ba2018-10-03 11:05:16 +0200160 // Optional utility used to verify reference validity.
161 std::unique_ptr<TemporalLayersChecker> checker_;
pbos@webrtc.org9115cde2014-12-09 10:36:40 +0000162};
163} // namespace webrtc
164
Mirko Bonadei92ea95e2017-09-15 06:47:31 +0200165#endif // MODULES_VIDEO_CODING_CODECS_VP8_SCREENSHARE_LAYERS_H_