Make protection_overhead_rate configurable through field trial.

Bug: None
Change-Id: I0a4e03d5f8134809c44d2d0ff88c4b4c8b8a9eaa
Reviewed-on: https://webrtc-review.googlesource.com/c/107341
Commit-Queue: Ying Wang <yinwa@webrtc.org>
Reviewed-by: Rasmus Brandt <brandtr@webrtc.org>
Reviewed-by: Ilya Nikolaevskiy <ilnik@webrtc.org>
Reviewed-by: Sebastian Jansson <srte@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#25293}
diff --git a/modules/video_coding/fec_controller_default.cc b/modules/video_coding/fec_controller_default.cc
index 5fe38e6..841ed74 100644
--- a/modules/video_coding/fec_controller_default.cc
+++ b/modules/video_coding/fec_controller_default.cc
@@ -8,10 +8,17 @@
  *  be found in the AUTHORS file in the root of the source tree.
  */
 
-#include "modules/video_coding/fec_controller_default.h"
+#include <algorithm>
+
+#include "modules/video_coding/fec_controller_default.h"  // NOLINT
+#include "rtc_base/logging.h"
+#include "system_wrappers/include/field_trial.h"
 
 namespace webrtc {
 using rtc::CritScope;
+
+const float kProtectionOverheadRateThreshold = 0.5;
+
 FecControllerDefault::FecControllerDefault(
     Clock* clock,
     VCMProtectionCallback* protection_callback)
@@ -19,13 +26,15 @@
       protection_callback_(protection_callback),
       loss_prot_logic_(new media_optimization::VCMLossProtectionLogic(
           clock_->TimeInMilliseconds())),
-      max_payload_size_(1460) {}
+      max_payload_size_(1460),
+      overhead_threshold_(GetProtectionOverheadRateThreshold()) {}
 
 FecControllerDefault::FecControllerDefault(Clock* clock)
     : clock_(clock),
       loss_prot_logic_(new media_optimization::VCMLossProtectionLogic(
           clock_->TimeInMilliseconds())),
-      max_payload_size_(1460) {}
+      max_payload_size_(1460),
+      overhead_threshold_(GetProtectionOverheadRateThreshold()) {}
 
 FecControllerDefault::~FecControllerDefault(void) {
   loss_prot_logic_->Release();
@@ -46,6 +55,25 @@
   max_payload_size_ = max_payload_size;
 }
 
+float FecControllerDefault::GetProtectionOverheadRateThreshold() {
+  float overhead_threshold =
+      strtof(webrtc::field_trial::FindFullName(
+                 "WebRTC-ProtectionOverheadRateThreshold")
+                 .c_str(),
+             nullptr);
+  if (overhead_threshold > 0 && overhead_threshold <= 1) {
+    RTC_LOG(LS_INFO) << "ProtectionOverheadRateThreshold is set to "
+                     << overhead_threshold;
+    return overhead_threshold;
+  } else if (overhead_threshold < 0 || overhead_threshold > 1) {
+    RTC_LOG(WARNING) << "ProtectionOverheadRateThreshold field trial is set to "
+                        "an invalid value, expecting a value between (0, 1].";
+  }
+  // WebRTC-ProtectionOverheadRateThreshold field trial string is not found, use
+  // the default value.
+  return kProtectionOverheadRateThreshold;
+}
+
 uint32_t FecControllerDefault::UpdateFecRates(
     uint32_t estimated_bitrate_bps,
     int actual_framerate_fps,
@@ -125,9 +153,9 @@
         static_cast<float>(sent_nack_rate_bps + sent_fec_rate_bps) /
         sent_total_rate_bps;
   }
-  // Cap the overhead estimate to 50%.
-  if (protection_overhead_rate > 0.5)
-    protection_overhead_rate = 0.5;
+  // Cap the overhead estimate to a threshold, default is 50%.
+  protection_overhead_rate =
+      std::min(protection_overhead_rate, overhead_threshold_);
   // Source coding rate: total rate - protection overhead.
   return estimated_bitrate_bps * (1.0 - protection_overhead_rate);
 }
diff --git a/modules/video_coding/fec_controller_default.h b/modules/video_coding/fec_controller_default.h
index a95eced..9d79a61 100644
--- a/modules/video_coding/fec_controller_default.h
+++ b/modules/video_coding/fec_controller_default.h
@@ -42,6 +42,7 @@
   void UpdateWithEncodedData(const size_t encoded_image_length,
                              const FrameType encoded_image_frametype) override;
   bool UseLossVectorMask() override;
+  float GetProtectionOverheadRateThreshold();
 
  private:
   enum { kBitrateAverageWinMs = 1000 };
@@ -52,6 +53,7 @@
       RTC_GUARDED_BY(crit_sect_);
   size_t max_payload_size_ RTC_GUARDED_BY(crit_sect_);
   RTC_DISALLOW_COPY_AND_ASSIGN(FecControllerDefault);
+  const float overhead_threshold_;
 };
 
 }  // namespace webrtc