Thread-safe ChannelManager.GetSupportedFormats, used by VideoSource

VideoSource was using VideoCapturer's GetSupportedFormats in a non-thread safe manner.
Now this is handled to (new method) ChannelManager.GetSupportedFormats.

BUG=
R=perkj@webrtc.org, tommi@webrtc.org

Review URL: https://webrtc-codereview.appspot.com/42079004

Cr-Commit-Position: refs/heads/master@{#8495}
git-svn-id: http://webrtc.googlecode.com/svn/trunk@8495 4adac7df-926f-26a2-2b94-8c16560cd09d
diff --git a/talk/app/webrtc/videosource.cc b/talk/app/webrtc/videosource.cc
index 44f3e22..2935c09 100644
--- a/talk/app/webrtc/videosource.cc
+++ b/talk/app/webrtc/videosource.cc
@@ -363,21 +363,21 @@
 void VideoSource::Initialize(
     const webrtc::MediaConstraintsInterface* constraints) {
 
-  std::vector<cricket::VideoFormat> formats;
-  if (video_capturer_->GetSupportedFormats() &&
-      video_capturer_->GetSupportedFormats()->size() > 0) {
-    formats = *video_capturer_->GetSupportedFormats();
-  } else if (video_capturer_->IsScreencast()) {
-    // The screen capturer can accept any resolution and we will derive the
-    // format from the constraints if any.
-    // Note that this only affects tab capturing, not desktop capturing,
-    // since desktop capturer does not respect the VideoFormat passed in.
-    formats.push_back(cricket::VideoFormat(kDefaultFormat));
-  } else {
-    // The VideoCapturer implementation doesn't support capability enumeration.
-    // We need to guess what the camera support.
-    for (int i = 0; i < ARRAY_SIZE(kVideoFormats); ++i) {
-      formats.push_back(cricket::VideoFormat(kVideoFormats[i]));
+  std::vector<cricket::VideoFormat> formats =
+      channel_manager_->GetSupportedFormats(video_capturer_.get());
+  if (formats.empty()) {
+    if (video_capturer_->IsScreencast()) {
+      // The screen capturer can accept any resolution and we will derive the
+      // format from the constraints if any.
+      // Note that this only affects tab capturing, not desktop capturing,
+      // since the desktop capturer does not respect the VideoFormat passed in.
+      formats.push_back(cricket::VideoFormat(kDefaultFormat));
+    } else {
+      // The VideoCapturer implementation doesn't support capability
+      // enumeration. We need to guess what the camera supports.
+      for (int i = 0; i < ARRAY_SIZE(kVideoFormats); ++i) {
+        formats.push_back(cricket::VideoFormat(kVideoFormats[i]));
+      }
     }
   }
 
diff --git a/talk/session/media/channelmanager.cc b/talk/session/media/channelmanager.cc
index e3de339..b507d4b 100644
--- a/talk/session/media/channelmanager.cc
+++ b/talk/session/media/channelmanager.cc
@@ -816,6 +816,23 @@
   }
 }
 
+std::vector<cricket::VideoFormat> ChannelManager::GetSupportedFormats(
+    VideoCapturer* capturer) const {
+  ASSERT(capturer != NULL);
+  std::vector<VideoFormat> formats;
+  worker_thread_->Invoke<void>(rtc::Bind(&ChannelManager::GetSupportedFormats_w,
+                                         this, capturer, &formats));
+  return formats;
+}
+
+void ChannelManager::GetSupportedFormats_w(
+    VideoCapturer* capturer,
+    std::vector<cricket::VideoFormat>* out_formats) const {
+  const std::vector<VideoFormat>* formats = capturer->GetSupportedFormats();
+  if (formats != NULL)
+    *out_formats = *formats;
+}
+
 // TODO(janahan): For now pass this request through the mediaengine to the
 // voice and video engines to do the real work. Once the capturer refactoring
 // is done, we will access the capturer using the ssrc (similar to how the
diff --git a/talk/session/media/channelmanager.h b/talk/session/media/channelmanager.h
index 7e18031..6bbfc5a 100644
--- a/talk/session/media/channelmanager.h
+++ b/talk/session/media/channelmanager.h
@@ -183,6 +183,9 @@
   void SetVoiceLogging(int level, const char* filter);
   void SetVideoLogging(int level, const char* filter);
 
+  // Gets capturer's supported formats in a thread safe manner
+  std::vector<cricket::VideoFormat> GetSupportedFormats(
+      VideoCapturer* capturer) const;
   // The channel manager handles the Tx side for Video processing,
   // as well as Tx and Rx side for Voice processing.
   // (The Rx Video processing will go throug the simplerenderingmanager,
@@ -288,6 +291,9 @@
   bool SetCaptureDevice_w(const Device* cam_device);
   void OnVideoCaptureStateChange(VideoCapturer* capturer,
                                  CaptureState result);
+  void GetSupportedFormats_w(
+      VideoCapturer* capturer,
+      std::vector<cricket::VideoFormat>* out_formats) const;
   bool RegisterVideoProcessor_w(VideoCapturer* capturer,
                                 VideoProcessor* processor);
   bool UnregisterVideoProcessor_w(VideoCapturer* capturer,