Create field trial for vp8 number of thread on iOS.

Without the added preprocessor check, iOS device will be using the desktop logic to determine the number of thread. This put iPhone 8 and iPhone X to use 3 threads and all other iPhones after iPhone 5 to use a single thread.
This CL added a preprocessor for WEBRTC_IOS to have it own thread number calculation logic. In which, the maximum number of thread is fetched from a field_trial and capped by the number of CPU available on the device.

Bug: webrtc:10005
Change-Id: I8c6257fcbf85b07bc986b5f733dbabb3feee37f7
Reviewed-on: https://webrtc-review.googlesource.com/c/110941
Commit-Queue: Jiawei Ou <ouj@fb.com>
Reviewed-by: Erik Språng <sprang@webrtc.org>
Reviewed-by: Kári Helgason <kthelgason@webrtc.org>
Reviewed-by: Magnus Flodman <mflodman@webrtc.org>
Reviewed-by: Niels Moller <nisse@webrtc.org>
Cr-Commit-Position: refs/heads/master@{#25997}
diff --git a/modules/video_coding/BUILD.gn b/modules/video_coding/BUILD.gn
index 988cbb8..2ec46e6 100644
--- a/modules/video_coding/BUILD.gn
+++ b/modules/video_coding/BUILD.gn
@@ -447,6 +447,7 @@
     "../../rtc_base:rtc_base_approved",
     "../../rtc_base:rtc_numerics",
     "../../rtc_base/experiments:cpu_speed_experiment",
+    "../../rtc_base/experiments:field_trial_parser",
     "../../system_wrappers",
     "../../system_wrappers:field_trial",
     "../../system_wrappers:metrics",
diff --git a/modules/video_coding/codecs/test/videocodec_test_libvpx.cc b/modules/video_coding/codecs/test/videocodec_test_libvpx.cc
index 1e365de..445b0c2 100644
--- a/modules/video_coding/codecs/test/videocodec_test_libvpx.cc
+++ b/modules/video_coding/codecs/test/videocodec_test_libvpx.cc
@@ -342,8 +342,7 @@
   fixture->RunTest(rate_profiles, &rc_thresholds, &quality_thresholds, nullptr);
 }
 
-// TODO(webrtc:9267): Fails on iOS
-#if defined(WEBRTC_ANDROID) || defined(WEBRTC_IOS)
+#if defined(WEBRTC_ANDROID)
 #define MAYBE_MultiresVP8 DISABLED_MultiresVP8
 #else
 #define MAYBE_MultiresVP8 MultiresVP8
@@ -360,9 +359,13 @@
   auto fixture = CreateVideoCodecTestFixture(config);
 
   std::vector<RateProfile> rate_profiles = {{1500, 30, config.num_frames}};
-
+#if defined(WEBRTC_ARCH_ARM) || defined(WEBRTC_ARCH_ARM64)
+  std::vector<RateControlThresholds> rc_thresholds = {
+      {3.5, 1.04, 6, 0.18, 0.14, 0.07, 0, 1}};
+#else
   std::vector<RateControlThresholds> rc_thresholds = {
       {5, 1, 5, 1, 0.3, 0.1, 0, 1}};
+#endif
   std::vector<QualityThresholds> quality_thresholds = {{34, 32, 0.90, 0.88}};
 
   fixture->RunTest(rate_profiles, &rc_thresholds, &quality_thresholds, nullptr);
diff --git a/modules/video_coding/codecs/vp8/libvpx_vp8_encoder.cc b/modules/video_coding/codecs/vp8/libvpx_vp8_encoder.cc
index 9114d95..808bfaa 100644
--- a/modules/video_coding/codecs/vp8/libvpx_vp8_encoder.cc
+++ b/modules/video_coding/codecs/vp8/libvpx_vp8_encoder.cc
@@ -30,6 +30,7 @@
 #include "modules/video_coding/utility/simulcast_rate_allocator.h"
 #include "modules/video_coding/utility/simulcast_utility.h"
 #include "rtc_base/checks.h"
+#include "rtc_base/experiments/field_trial_parser.h"
 #include "rtc_base/scoped_ref_ptr.h"
 #include "rtc_base/trace_event.h"
 #include "system_wrappers/include/field_trial.h"
@@ -40,6 +41,11 @@
 namespace {
 const char kVp8TrustedRateControllerFieldTrial[] =
     "WebRTC-LibvpxVp8TrustedRateController";
+#if defined(WEBRTC_IOS)
+const char kVP8IosMaxNumberOfThreadFieldTrial[] =
+    "WebRTC-VP8IosMaxNumberOfThread";
+const char kVP8IosMaxNumberOfThreadFieldTrialParameter[] = "max_thread";
+#endif
 
 // QP is obtained from VP8-bitstream for HW, so the QP corresponds to the
 // bitstream range of [0, 127] and not the user-level range of [0,63].
@@ -565,6 +571,20 @@
   }
   return 1;
 #else
+#if defined(WEBRTC_IOS)
+  std::string trial_string =
+      field_trial::FindFullName(kVP8IosMaxNumberOfThreadFieldTrial);
+  FieldTrialParameter<int> max_thread_number(
+      kVP8IosMaxNumberOfThreadFieldTrialParameter, 0);
+  ParseFieldTrial({&max_thread_number}, trial_string);
+  if (max_thread_number.Get() > 0) {
+    if (width * height < 320 * 180) {
+      return 1;  // Use single thread for small screens
+    }
+    // thread number must be less than or equal to the number of CPUs.
+    return std::min(cpus, max_thread_number.Get());
+  }
+#endif  // defined(WEBRTC_IOS)
   if (width * height >= 1920 * 1080 && cpus > 8) {
     return 8;  // 8 threads for 1080p on high perf machines.
   } else if (width * height > 1280 * 960 && cpus >= 6) {
diff --git a/system_wrappers/source/cpu_info.cc b/system_wrappers/source/cpu_info.cc
index c17d59d..136d977 100644
--- a/system_wrappers/source/cpu_info.cc
+++ b/system_wrappers/source/cpu_info.cc
@@ -32,7 +32,7 @@
   number_of_cores = static_cast<int>(si.dwNumberOfProcessors);
 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_ANDROID)
   number_of_cores = static_cast<int>(sysconf(_SC_NPROCESSORS_ONLN));
-#elif defined(WEBRTC_MAC)
+#elif defined(WEBRTC_MAC) || defined(WEBRTC_IOS)
   int name[] = {CTL_HW, HW_AVAILCPU};
   size_t size = sizeof(number_of_cores);
   if (0 != sysctl(name, 2, &number_of_cores, &size, NULL, 0)) {