• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "content/renderer/renderer_webkitplatformsupport_impl.h"
6 
7 #include "base/command_line.h"
8 #include "base/files/file_path.h"
9 #include "base/lazy_instance.h"
10 #include "base/logging.h"
11 #include "base/memory/shared_memory.h"
12 #include "base/message_loop/message_loop_proxy.h"
13 #include "base/metrics/histogram.h"
14 #include "base/numerics/safe_conversions.h"
15 #include "base/strings/string_number_conversions.h"
16 #include "base/strings/utf_string_conversions.h"
17 #include "content/child/blink_glue.h"
18 #include "content/child/database_util.h"
19 #include "content/child/fileapi/webfilesystem_impl.h"
20 #include "content/child/indexed_db/webidbfactory_impl.h"
21 #include "content/child/npapi/npobject_util.h"
22 #include "content/child/quota_dispatcher.h"
23 #include "content/child/quota_message_filter.h"
24 #include "content/child/simple_webmimeregistry_impl.h"
25 #include "content/child/thread_safe_sender.h"
26 #include "content/child/web_database_observer_impl.h"
27 #include "content/child/webblobregistry_impl.h"
28 #include "content/child/webfileutilities_impl.h"
29 #include "content/child/webmessageportchannel_impl.h"
30 #include "content/common/file_utilities_messages.h"
31 #include "content/common/gpu/client/context_provider_command_buffer.h"
32 #include "content/common/gpu/client/gpu_channel_host.h"
33 #include "content/common/gpu/client/webgraphicscontext3d_command_buffer_impl.h"
34 #include "content/common/gpu/gpu_process_launch_causes.h"
35 #include "content/common/mime_registry_messages.h"
36 #include "content/common/view_messages.h"
37 #include "content/public/common/content_switches.h"
38 #include "content/public/common/webplugininfo.h"
39 #include "content/public/renderer/content_renderer_client.h"
40 #include "content/renderer/battery_status/battery_status_dispatcher.h"
41 #include "content/renderer/battery_status/fake_battery_status_dispatcher.h"
42 #include "content/renderer/device_sensors/device_motion_event_pump.h"
43 #include "content/renderer/device_sensors/device_orientation_event_pump.h"
44 #include "content/renderer/dom_storage/webstoragenamespace_impl.h"
45 #include "content/renderer/gamepad_shared_memory_reader.h"
46 #include "content/renderer/media/audio_decoder.h"
47 #include "content/renderer/media/crypto/key_systems.h"
48 #include "content/renderer/media/renderer_webaudiodevice_impl.h"
49 #include "content/renderer/media/renderer_webmidiaccessor_impl.h"
50 #include "content/renderer/media/webcontentdecryptionmodule_impl.h"
51 #include "content/renderer/media/webrtc/peer_connection_dependency_factory.h"
52 #include "content/renderer/render_thread_impl.h"
53 #include "content/renderer/renderer_clipboard_client.h"
54 #include "content/renderer/screen_orientation/mock_screen_orientation_controller.h"
55 #include "content/renderer/webclipboard_impl.h"
56 #include "content/renderer/webgraphicscontext3d_provider_impl.h"
57 #include "content/renderer/webpublicsuffixlist_impl.h"
58 #include "gpu/config/gpu_info.h"
59 #include "ipc/ipc_sync_message_filter.h"
60 #include "media/audio/audio_output_device.h"
61 #include "media/base/audio_hardware_config.h"
62 #include "media/filters/stream_parser_factory.h"
63 #include "net/base/mime_util.h"
64 #include "net/base/net_util.h"
65 #include "third_party/WebKit/public/platform/WebBatteryStatusListener.h"
66 #include "third_party/WebKit/public/platform/WebBlobRegistry.h"
67 #include "third_party/WebKit/public/platform/WebDeviceMotionListener.h"
68 #include "third_party/WebKit/public/platform/WebDeviceOrientationListener.h"
69 #include "third_party/WebKit/public/platform/WebFileInfo.h"
70 #include "third_party/WebKit/public/platform/WebGamepads.h"
71 #include "third_party/WebKit/public/platform/WebMediaStreamCenter.h"
72 #include "third_party/WebKit/public/platform/WebMediaStreamCenterClient.h"
73 #include "third_party/WebKit/public/platform/WebPluginListBuilder.h"
74 #include "third_party/WebKit/public/platform/WebURL.h"
75 #include "third_party/WebKit/public/platform/WebVector.h"
76 #include "ui/gfx/color_profile.h"
77 #include "url/gurl.h"
78 #include "webkit/common/gpu/context_provider_web_context.h"
79 #include "webkit/common/quota/quota_types.h"
80 
81 #if defined(OS_ANDROID)
82 #include "content/renderer/android/synchronous_compositor_factory.h"
83 #include "content/renderer/media/android/audio_decoder_android.h"
84 #endif
85 
86 #if defined(OS_MACOSX)
87 #include "content/common/mac/font_descriptor.h"
88 #include "content/common/mac/font_loader.h"
89 #include "content/renderer/webscrollbarbehavior_impl_mac.h"
90 #include "third_party/WebKit/public/platform/mac/WebSandboxSupport.h"
91 #endif
92 
93 #if defined(OS_POSIX)
94 #include "base/file_descriptor_posix.h"
95 #if !defined(OS_MACOSX) && !defined(OS_ANDROID)
96 #include <map>
97 #include <string>
98 
99 #include "base/synchronization/lock.h"
100 #include "content/common/child_process_sandbox_support_impl_linux.h"
101 #include "third_party/WebKit/public/platform/linux/WebFallbackFont.h"
102 #include "third_party/WebKit/public/platform/linux/WebSandboxSupport.h"
103 #include "third_party/icu/source/common/unicode/utf16.h"
104 #endif
105 #endif
106 
107 #if defined(OS_WIN)
108 #include "content/common/child_process_messages.h"
109 #include "third_party/WebKit/public/platform/win/WebSandboxSupport.h"
110 #endif
111 
112 #if defined(USE_AURA)
113 #include "content/renderer/webscrollbarbehavior_impl_gtkoraura.h"
114 #elif !defined(OS_MACOSX)
115 #include "third_party/WebKit/public/platform/WebScrollbarBehavior.h"
116 #define WebScrollbarBehaviorImpl blink::WebScrollbarBehavior
117 #endif
118 
119 using blink::Platform;
120 using blink::WebAudioDevice;
121 using blink::WebBlobRegistry;
122 using blink::WebDatabaseObserver;
123 using blink::WebFileInfo;
124 using blink::WebFileSystem;
125 using blink::WebGamepad;
126 using blink::WebGamepads;
127 using blink::WebIDBFactory;
128 using blink::WebMIDIAccessor;
129 using blink::WebMediaStreamCenter;
130 using blink::WebMediaStreamCenterClient;
131 using blink::WebMimeRegistry;
132 using blink::WebRTCPeerConnectionHandler;
133 using blink::WebRTCPeerConnectionHandlerClient;
134 using blink::WebStorageNamespace;
135 using blink::WebString;
136 using blink::WebURL;
137 using blink::WebVector;
138 
139 namespace content {
140 
141 namespace {
142 
143 static bool g_sandbox_enabled = true;
144 base::LazyInstance<blink::WebDeviceMotionData>::Leaky
145     g_test_device_motion_data = LAZY_INSTANCE_INITIALIZER;
146 base::LazyInstance<blink::WebDeviceOrientationData>::Leaky
147     g_test_device_orientation_data = LAZY_INSTANCE_INITIALIZER;
148 base::LazyInstance<MockScreenOrientationController>::Leaky
149     g_test_screen_orientation_controller = LAZY_INSTANCE_INITIALIZER;
150 base::LazyInstance<FakeBatteryStatusDispatcher>::Leaky
151     g_test_battery_status_dispatcher = LAZY_INSTANCE_INITIALIZER;
152 
153 } // namespace
154 
155 //------------------------------------------------------------------------------
156 
157 class RendererWebKitPlatformSupportImpl::MimeRegistry
158     : public SimpleWebMimeRegistryImpl {
159  public:
160   virtual blink::WebMimeRegistry::SupportsType supportsMediaMIMEType(
161       const blink::WebString& mime_type,
162       const blink::WebString& codecs,
163       const blink::WebString& key_system);
164   virtual bool supportsMediaSourceMIMEType(const blink::WebString& mime_type,
165                                            const blink::WebString& codecs);
166   virtual bool supportsEncryptedMediaMIMEType(const WebString& key_system,
167                                               const WebString& mime_type,
168                                               const WebString& codecs) OVERRIDE;
169   virtual blink::WebString mimeTypeForExtension(
170       const blink::WebString& file_extension);
171   virtual blink::WebString mimeTypeFromFile(
172       const blink::WebString& file_path);
173 };
174 
175 class RendererWebKitPlatformSupportImpl::FileUtilities
176     : public WebFileUtilitiesImpl {
177  public:
FileUtilities(ThreadSafeSender * sender)178   explicit FileUtilities(ThreadSafeSender* sender)
179       : thread_safe_sender_(sender) {}
180   virtual bool getFileInfo(const WebString& path, WebFileInfo& result);
181  private:
182   bool SendSyncMessageFromAnyThread(IPC::SyncMessage* msg) const;
183   scoped_refptr<ThreadSafeSender> thread_safe_sender_;
184 };
185 
186 #if defined(OS_ANDROID)
187 // WebKit doesn't use WebSandboxSupport on android so we don't need to
188 // implement anything here.
189 class RendererWebKitPlatformSupportImpl::SandboxSupport {
190 };
191 #else
192 class RendererWebKitPlatformSupportImpl::SandboxSupport
193     : public blink::WebSandboxSupport {
194  public:
~SandboxSupport()195   virtual ~SandboxSupport() {}
196 
197 #if defined(OS_WIN)
198   virtual bool ensureFontLoaded(HFONT);
199 #elif defined(OS_MACOSX)
200   virtual bool loadFont(
201       NSFont* src_font,
202       CGFontRef* container,
203       uint32* font_id);
204 #elif defined(OS_POSIX)
205   virtual void getFallbackFontForCharacter(
206       blink::WebUChar32 character,
207       const char* preferred_locale,
208       blink::WebFallbackFont* fallbackFont);
209   virtual void getRenderStyleForStrike(
210       const char* family, int sizeAndStyle, blink::WebFontRenderStyle* out);
211 
212  private:
213   // WebKit likes to ask us for the correct font family to use for a set of
214   // unicode code points. It needs this information frequently so we cache it
215   // here.
216   base::Lock unicode_font_families_mutex_;
217   std::map<int32_t, blink::WebFallbackFont> unicode_font_families_;
218 #endif
219 };
220 #endif  // defined(OS_ANDROID)
221 
222 //------------------------------------------------------------------------------
223 
RendererWebKitPlatformSupportImpl()224 RendererWebKitPlatformSupportImpl::RendererWebKitPlatformSupportImpl()
225     : clipboard_client_(new RendererClipboardClient),
226       clipboard_(new WebClipboardImpl(clipboard_client_.get())),
227       mime_registry_(new RendererWebKitPlatformSupportImpl::MimeRegistry),
228       sudden_termination_disables_(0),
229       plugin_refresh_allowed_(true),
230       child_thread_loop_(base::MessageLoopProxy::current()),
231       web_scrollbar_behavior_(new WebScrollbarBehaviorImpl),
232       gamepad_provider_(NULL) {
233   if (g_sandbox_enabled && sandboxEnabled()) {
234     sandbox_support_.reset(
235         new RendererWebKitPlatformSupportImpl::SandboxSupport);
236   } else {
237     DVLOG(1) << "Disabling sandbox support for testing.";
238   }
239 
240   // ChildThread may not exist in some tests.
241   if (ChildThread::current()) {
242     sync_message_filter_ = ChildThread::current()->sync_message_filter();
243     thread_safe_sender_ = ChildThread::current()->thread_safe_sender();
244     quota_message_filter_ = ChildThread::current()->quota_message_filter();
245     blob_registry_.reset(new WebBlobRegistryImpl(thread_safe_sender_));
246     web_idb_factory_.reset(new WebIDBFactoryImpl(thread_safe_sender_));
247     web_database_observer_impl_.reset(
248         new WebDatabaseObserverImpl(sync_message_filter_));
249   }
250 }
251 
~RendererWebKitPlatformSupportImpl()252 RendererWebKitPlatformSupportImpl::~RendererWebKitPlatformSupportImpl() {
253   WebFileSystemImpl::DeleteThreadSpecificInstance();
254 }
255 
256 //------------------------------------------------------------------------------
257 
clipboard()258 blink::WebClipboard* RendererWebKitPlatformSupportImpl::clipboard() {
259   blink::WebClipboard* clipboard =
260       GetContentClient()->renderer()->OverrideWebClipboard();
261   if (clipboard)
262     return clipboard;
263   return clipboard_.get();
264 }
265 
mimeRegistry()266 blink::WebMimeRegistry* RendererWebKitPlatformSupportImpl::mimeRegistry() {
267   return mime_registry_.get();
268 }
269 
270 blink::WebFileUtilities*
fileUtilities()271 RendererWebKitPlatformSupportImpl::fileUtilities() {
272   if (!file_utilities_) {
273     file_utilities_.reset(new FileUtilities(thread_safe_sender_.get()));
274     file_utilities_->set_sandbox_enabled(sandboxEnabled());
275   }
276   return file_utilities_.get();
277 }
278 
sandboxSupport()279 blink::WebSandboxSupport* RendererWebKitPlatformSupportImpl::sandboxSupport() {
280 #if defined(OS_ANDROID)
281   // WebKit doesn't use WebSandboxSupport on android.
282   return NULL;
283 #else
284   return sandbox_support_.get();
285 #endif
286 }
287 
cookieJar()288 blink::WebCookieJar* RendererWebKitPlatformSupportImpl::cookieJar() {
289   NOTREACHED() << "Use WebFrameClient::cookieJar() instead!";
290   return NULL;
291 }
292 
themeEngine()293 blink::WebThemeEngine* RendererWebKitPlatformSupportImpl::themeEngine() {
294   blink::WebThemeEngine* theme_engine =
295       GetContentClient()->renderer()->OverrideThemeEngine();
296   if (theme_engine)
297     return theme_engine;
298   return BlinkPlatformImpl::themeEngine();
299 }
300 
sandboxEnabled()301 bool RendererWebKitPlatformSupportImpl::sandboxEnabled() {
302   // As explained in Platform.h, this function is used to decide
303   // whether to allow file system operations to come out of WebKit or not.
304   // Even if the sandbox is disabled, there's no reason why the code should
305   // act any differently...unless we're in single process mode.  In which
306   // case, we have no other choice.  Platform.h discourages using
307   // this switch unless absolutely necessary, so hopefully we won't end up
308   // with too many code paths being different in single-process mode.
309   return !CommandLine::ForCurrentProcess()->HasSwitch(switches::kSingleProcess);
310 }
311 
visitedLinkHash(const char * canonical_url,size_t length)312 unsigned long long RendererWebKitPlatformSupportImpl::visitedLinkHash(
313     const char* canonical_url,
314     size_t length) {
315   return GetContentClient()->renderer()->VisitedLinkHash(canonical_url, length);
316 }
317 
isLinkVisited(unsigned long long link_hash)318 bool RendererWebKitPlatformSupportImpl::isLinkVisited(
319     unsigned long long link_hash) {
320   return GetContentClient()->renderer()->IsLinkVisited(link_hash);
321 }
322 
createMessageChannel(blink::WebMessagePortChannel ** channel1,blink::WebMessagePortChannel ** channel2)323 void RendererWebKitPlatformSupportImpl::createMessageChannel(
324     blink::WebMessagePortChannel** channel1,
325     blink::WebMessagePortChannel** channel2) {
326   WebMessagePortChannelImpl::CreatePair(
327       child_thread_loop_.get(), channel1, channel2);
328 }
329 
330 blink::WebPrescientNetworking*
prescientNetworking()331 RendererWebKitPlatformSupportImpl::prescientNetworking() {
332   return GetContentClient()->renderer()->GetPrescientNetworking();
333 }
334 
335 bool
CheckPreparsedJsCachingEnabled() const336 RendererWebKitPlatformSupportImpl::CheckPreparsedJsCachingEnabled() const {
337   static bool checked = false;
338   static bool result = false;
339   if (!checked) {
340     const CommandLine& command_line = *CommandLine::ForCurrentProcess();
341     result = command_line.HasSwitch(switches::kEnablePreparsedJsCaching);
342     checked = true;
343   }
344   return result;
345 }
346 
cacheMetadata(const blink::WebURL & url,double response_time,const char * data,size_t size)347 void RendererWebKitPlatformSupportImpl::cacheMetadata(
348     const blink::WebURL& url,
349     double response_time,
350     const char* data,
351     size_t size) {
352   if (!CheckPreparsedJsCachingEnabled())
353     return;
354 
355   // Let the browser know we generated cacheable metadata for this resource. The
356   // browser may cache it and return it on subsequent responses to speed
357   // the processing of this resource.
358   std::vector<char> copy(data, data + size);
359   RenderThread::Get()->Send(
360       new ViewHostMsg_DidGenerateCacheableMetadata(url, response_time, copy));
361 }
362 
defaultLocale()363 WebString RendererWebKitPlatformSupportImpl::defaultLocale() {
364   return base::ASCIIToUTF16(RenderThread::Get()->GetLocale());
365 }
366 
suddenTerminationChanged(bool enabled)367 void RendererWebKitPlatformSupportImpl::suddenTerminationChanged(bool enabled) {
368   if (enabled) {
369     // We should not get more enables than disables, but we want it to be a
370     // non-fatal error if it does happen.
371     DCHECK_GT(sudden_termination_disables_, 0);
372     sudden_termination_disables_ = std::max(sudden_termination_disables_ - 1,
373                                             0);
374     if (sudden_termination_disables_ != 0)
375       return;
376   } else {
377     sudden_termination_disables_++;
378     if (sudden_termination_disables_ != 1)
379       return;
380   }
381 
382   RenderThread* thread = RenderThread::Get();
383   if (thread)  // NULL in unittests.
384     thread->Send(new ViewHostMsg_SuddenTerminationChanged(enabled));
385 }
386 
387 WebStorageNamespace*
createLocalStorageNamespace()388 RendererWebKitPlatformSupportImpl::createLocalStorageNamespace() {
389   return new WebStorageNamespaceImpl();
390 }
391 
392 
393 //------------------------------------------------------------------------------
394 
idbFactory()395 WebIDBFactory* RendererWebKitPlatformSupportImpl::idbFactory() {
396   return web_idb_factory_.get();
397 }
398 
399 //------------------------------------------------------------------------------
400 
fileSystem()401 WebFileSystem* RendererWebKitPlatformSupportImpl::fileSystem() {
402   return WebFileSystemImpl::ThreadSpecificInstance(child_thread_loop_.get());
403 }
404 
405 //------------------------------------------------------------------------------
406 
407 WebMimeRegistry::SupportsType
supportsMediaMIMEType(const WebString & mime_type,const WebString & codecs,const WebString & key_system)408 RendererWebKitPlatformSupportImpl::MimeRegistry::supportsMediaMIMEType(
409     const WebString& mime_type,
410     const WebString& codecs,
411     const WebString& key_system) {
412   const std::string mime_type_ascii = ToASCIIOrEmpty(mime_type);
413   // Not supporting the container is a flat-out no.
414   if (!net::IsSupportedMediaMimeType(mime_type_ascii))
415     return IsNotSupported;
416 
417   if (!key_system.isEmpty()) {
418     // Check whether the key system is supported with the mime_type and codecs.
419 
420     // Chromium only supports ASCII parameters.
421     if (!base::IsStringASCII(key_system))
422       return IsNotSupported;
423 
424     std::string key_system_ascii =
425         GetUnprefixedKeySystemName(base::UTF16ToASCII(key_system));
426     std::vector<std::string> strict_codecs;
427     bool strip_suffix = !net::IsStrictMediaMimeType(mime_type_ascii);
428     net::ParseCodecString(ToASCIIOrEmpty(codecs), &strict_codecs, strip_suffix);
429 
430     if (!IsSupportedKeySystemWithMediaMimeType(
431             mime_type_ascii, strict_codecs, key_system_ascii)) {
432       return IsNotSupported;
433     }
434 
435     // Continue processing the mime_type and codecs.
436   }
437 
438   // Check list of strict codecs to see if it is supported.
439   if (net::IsStrictMediaMimeType(mime_type_ascii)) {
440     // Check if the codecs are a perfect match.
441     std::vector<std::string> strict_codecs;
442     net::ParseCodecString(ToASCIIOrEmpty(codecs), &strict_codecs, false);
443     if (net::IsSupportedStrictMediaMimeType(mime_type_ascii, strict_codecs))
444       return IsSupported;
445 
446     // We support the container, but no codecs were specified.
447     if (codecs.isNull())
448       return MayBeSupported;
449 
450     return IsNotSupported;
451   }
452 
453   // If we don't recognize the codec, it's possible we support it.
454   std::vector<std::string> parsed_codecs;
455   net::ParseCodecString(ToASCIIOrEmpty(codecs), &parsed_codecs, true);
456   if (!net::AreSupportedMediaCodecs(parsed_codecs))
457     return MayBeSupported;
458 
459   // Otherwise we have a perfect match.
460   return IsSupported;
461 }
462 
463 bool
supportsMediaSourceMIMEType(const blink::WebString & mime_type,const WebString & codecs)464 RendererWebKitPlatformSupportImpl::MimeRegistry::supportsMediaSourceMIMEType(
465     const blink::WebString& mime_type,
466     const WebString& codecs) {
467   const std::string mime_type_ascii = ToASCIIOrEmpty(mime_type);
468   std::vector<std::string> parsed_codec_ids;
469   net::ParseCodecString(ToASCIIOrEmpty(codecs), &parsed_codec_ids, false);
470   if (mime_type_ascii.empty())
471     return false;
472   return media::StreamParserFactory::IsTypeSupported(
473       mime_type_ascii, parsed_codec_ids);
474 }
475 
476 bool
supportsEncryptedMediaMIMEType(const WebString & key_system,const WebString & mime_type,const WebString & codecs)477 RendererWebKitPlatformSupportImpl::MimeRegistry::supportsEncryptedMediaMIMEType(
478     const WebString& key_system,
479     const WebString& mime_type,
480     const WebString& codecs) {
481   // Chromium only supports ASCII parameters.
482   if (!base::IsStringASCII(key_system) || !base::IsStringASCII(mime_type) ||
483       !base::IsStringASCII(codecs)) {
484     return false;
485   }
486 
487   if (key_system.isEmpty())
488     return false;
489 
490   const std::string mime_type_ascii = base::UTF16ToASCII(mime_type);
491 
492   std::vector<std::string> codec_vector;
493   bool strip_suffix = !net::IsStrictMediaMimeType(mime_type_ascii);
494   net::ParseCodecString(base::UTF16ToASCII(codecs), &codec_vector,
495                         strip_suffix);
496 
497   return IsSupportedKeySystemWithMediaMimeType(
498       mime_type_ascii, codec_vector, base::UTF16ToASCII(key_system));
499 }
500 
501 WebString
mimeTypeForExtension(const WebString & file_extension)502 RendererWebKitPlatformSupportImpl::MimeRegistry::mimeTypeForExtension(
503     const WebString& file_extension) {
504   if (IsPluginProcess())
505     return SimpleWebMimeRegistryImpl::mimeTypeForExtension(file_extension);
506 
507   // The sandbox restricts our access to the registry, so we need to proxy
508   // these calls over to the browser process.
509   std::string mime_type;
510   RenderThread::Get()->Send(
511       new MimeRegistryMsg_GetMimeTypeFromExtension(
512           base::FilePath::FromUTF16Unsafe(file_extension).value(), &mime_type));
513   return base::ASCIIToUTF16(mime_type);
514 }
515 
mimeTypeFromFile(const WebString & file_path)516 WebString RendererWebKitPlatformSupportImpl::MimeRegistry::mimeTypeFromFile(
517     const WebString& file_path) {
518   if (IsPluginProcess())
519     return SimpleWebMimeRegistryImpl::mimeTypeFromFile(file_path);
520 
521   // The sandbox restricts our access to the registry, so we need to proxy
522   // these calls over to the browser process.
523   std::string mime_type;
524   RenderThread::Get()->Send(new MimeRegistryMsg_GetMimeTypeFromFile(
525       base::FilePath::FromUTF16Unsafe(file_path),
526       &mime_type));
527   return base::ASCIIToUTF16(mime_type);
528 }
529 
530 //------------------------------------------------------------------------------
531 
getFileInfo(const WebString & path,WebFileInfo & web_file_info)532 bool RendererWebKitPlatformSupportImpl::FileUtilities::getFileInfo(
533     const WebString& path,
534     WebFileInfo& web_file_info) {
535   base::File::Info file_info;
536   base::File::Error status;
537   if (!SendSyncMessageFromAnyThread(new FileUtilitiesMsg_GetFileInfo(
538            base::FilePath::FromUTF16Unsafe(path), &file_info, &status)) ||
539       status != base::File::FILE_OK) {
540     return false;
541   }
542   FileInfoToWebFileInfo(file_info, &web_file_info);
543   web_file_info.platformPath = path;
544   return true;
545 }
546 
547 bool RendererWebKitPlatformSupportImpl::FileUtilities::
SendSyncMessageFromAnyThread(IPC::SyncMessage * msg) const548 SendSyncMessageFromAnyThread(IPC::SyncMessage* msg) const {
549   base::TimeTicks begin = base::TimeTicks::Now();
550   const bool success = thread_safe_sender_->Send(msg);
551   base::TimeDelta delta = base::TimeTicks::Now() - begin;
552   UMA_HISTOGRAM_TIMES("RendererSyncIPC.ElapsedTime", delta);
553   return success;
554 }
555 
556 //------------------------------------------------------------------------------
557 
558 #if defined(OS_WIN)
559 
ensureFontLoaded(HFONT font)560 bool RendererWebKitPlatformSupportImpl::SandboxSupport::ensureFontLoaded(
561     HFONT font) {
562   LOGFONT logfont;
563   GetObject(font, sizeof(LOGFONT), &logfont);
564   RenderThread::Get()->PreCacheFont(logfont);
565   return true;
566 }
567 
568 #elif defined(OS_MACOSX)
569 
loadFont(NSFont * src_font,CGFontRef * out,uint32 * font_id)570 bool RendererWebKitPlatformSupportImpl::SandboxSupport::loadFont(
571     NSFont* src_font, CGFontRef* out, uint32* font_id) {
572   uint32 font_data_size;
573   FontDescriptor src_font_descriptor(src_font);
574   base::SharedMemoryHandle font_data;
575   if (!RenderThread::Get()->Send(new ViewHostMsg_LoadFont(
576         src_font_descriptor, &font_data_size, &font_data, font_id))) {
577     *out = NULL;
578     *font_id = 0;
579     return false;
580   }
581 
582   if (font_data_size == 0 || font_data == base::SharedMemory::NULLHandle() ||
583       *font_id == 0) {
584     LOG(ERROR) << "Bad response from ViewHostMsg_LoadFont() for " <<
585         src_font_descriptor.font_name;
586     *out = NULL;
587     *font_id = 0;
588     return false;
589   }
590 
591   // TODO(jeremy): Need to call back into WebKit to make sure that the font
592   // isn't already activated, based on the font id.  If it's already
593   // activated, don't reactivate it here - crbug.com/72727 .
594 
595   return FontLoader::CGFontRefFromBuffer(font_data, font_data_size, out);
596 }
597 
598 #elif defined(OS_ANDROID)
599 
600 // WebKit doesn't use WebSandboxSupport on android so we don't need to
601 // implement anything here. This is cleaner to support than excluding the
602 // whole class for android.
603 
604 #elif defined(OS_POSIX)
605 
606 void
getFallbackFontForCharacter(blink::WebUChar32 character,const char * preferred_locale,blink::WebFallbackFont * fallbackFont)607 RendererWebKitPlatformSupportImpl::SandboxSupport::getFallbackFontForCharacter(
608     blink::WebUChar32 character,
609     const char* preferred_locale,
610     blink::WebFallbackFont* fallbackFont) {
611   base::AutoLock lock(unicode_font_families_mutex_);
612   const std::map<int32_t, blink::WebFallbackFont>::const_iterator iter =
613       unicode_font_families_.find(character);
614   if (iter != unicode_font_families_.end()) {
615     fallbackFont->name = iter->second.name;
616     fallbackFont->filename = iter->second.filename;
617     fallbackFont->ttcIndex = iter->second.ttcIndex;
618     fallbackFont->isBold = iter->second.isBold;
619     fallbackFont->isItalic = iter->second.isItalic;
620     return;
621   }
622 
623   GetFallbackFontForCharacter(character, preferred_locale, fallbackFont);
624   unicode_font_families_.insert(std::make_pair(character, *fallbackFont));
625 }
626 
627 void
getRenderStyleForStrike(const char * family,int sizeAndStyle,blink::WebFontRenderStyle * out)628 RendererWebKitPlatformSupportImpl::SandboxSupport::getRenderStyleForStrike(
629     const char* family, int sizeAndStyle, blink::WebFontRenderStyle* out) {
630   GetRenderStyleForStrike(family, sizeAndStyle, out);
631 }
632 
633 #endif
634 
635 //------------------------------------------------------------------------------
636 
637 Platform::FileHandle
databaseOpenFile(const WebString & vfs_file_name,int desired_flags)638 RendererWebKitPlatformSupportImpl::databaseOpenFile(
639     const WebString& vfs_file_name, int desired_flags) {
640   return DatabaseUtil::DatabaseOpenFile(
641       vfs_file_name, desired_flags, sync_message_filter_.get());
642 }
643 
databaseDeleteFile(const WebString & vfs_file_name,bool sync_dir)644 int RendererWebKitPlatformSupportImpl::databaseDeleteFile(
645     const WebString& vfs_file_name, bool sync_dir) {
646   return DatabaseUtil::DatabaseDeleteFile(
647       vfs_file_name, sync_dir, sync_message_filter_.get());
648 }
649 
databaseGetFileAttributes(const WebString & vfs_file_name)650 long RendererWebKitPlatformSupportImpl::databaseGetFileAttributes(
651     const WebString& vfs_file_name) {
652   return DatabaseUtil::DatabaseGetFileAttributes(vfs_file_name,
653                                                  sync_message_filter_.get());
654 }
655 
databaseGetFileSize(const WebString & vfs_file_name)656 long long RendererWebKitPlatformSupportImpl::databaseGetFileSize(
657     const WebString& vfs_file_name) {
658   return DatabaseUtil::DatabaseGetFileSize(vfs_file_name,
659                                            sync_message_filter_.get());
660 }
661 
databaseGetSpaceAvailableForOrigin(const WebString & origin_identifier)662 long long RendererWebKitPlatformSupportImpl::databaseGetSpaceAvailableForOrigin(
663     const WebString& origin_identifier) {
664   return DatabaseUtil::DatabaseGetSpaceAvailable(origin_identifier,
665                                                  sync_message_filter_.get());
666 }
667 
canAccelerate2dCanvas()668 bool RendererWebKitPlatformSupportImpl::canAccelerate2dCanvas() {
669   RenderThreadImpl* thread = RenderThreadImpl::current();
670   GpuChannelHost* host = thread->EstablishGpuChannelSync(
671       CAUSE_FOR_GPU_LAUNCH_CANVAS_2D);
672   if (!host)
673     return false;
674 
675   return host->gpu_info().SupportsAccelerated2dCanvas();
676 }
677 
isThreadedCompositingEnabled()678 bool RendererWebKitPlatformSupportImpl::isThreadedCompositingEnabled() {
679   RenderThreadImpl* thread = RenderThreadImpl::current();
680   // thread can be NULL in tests.
681   return thread && thread->compositor_message_loop_proxy().get();
682 }
683 
audioHardwareSampleRate()684 double RendererWebKitPlatformSupportImpl::audioHardwareSampleRate() {
685   RenderThreadImpl* thread = RenderThreadImpl::current();
686   return thread->GetAudioHardwareConfig()->GetOutputSampleRate();
687 }
688 
audioHardwareBufferSize()689 size_t RendererWebKitPlatformSupportImpl::audioHardwareBufferSize() {
690   RenderThreadImpl* thread = RenderThreadImpl::current();
691   return thread->GetAudioHardwareConfig()->GetOutputBufferSize();
692 }
693 
audioHardwareOutputChannels()694 unsigned RendererWebKitPlatformSupportImpl::audioHardwareOutputChannels() {
695   RenderThreadImpl* thread = RenderThreadImpl::current();
696   return thread->GetAudioHardwareConfig()->GetOutputChannels();
697 }
698 
databaseObserver()699 WebDatabaseObserver* RendererWebKitPlatformSupportImpl::databaseObserver() {
700   return web_database_observer_impl_.get();
701 }
702 
703 WebAudioDevice*
createAudioDevice(size_t buffer_size,unsigned input_channels,unsigned channels,double sample_rate,WebAudioDevice::RenderCallback * callback,const blink::WebString & input_device_id)704 RendererWebKitPlatformSupportImpl::createAudioDevice(
705     size_t buffer_size,
706     unsigned input_channels,
707     unsigned channels,
708     double sample_rate,
709     WebAudioDevice::RenderCallback* callback,
710     const blink::WebString& input_device_id) {
711   // Use a mock for testing.
712   blink::WebAudioDevice* mock_device =
713       GetContentClient()->renderer()->OverrideCreateAudioDevice(sample_rate);
714   if (mock_device)
715     return mock_device;
716 
717   // The |channels| does not exactly identify the channel layout of the
718   // device. The switch statement below assigns a best guess to the channel
719   // layout based on number of channels.
720   // TODO(crogers): WebKit should give the channel layout instead of the hard
721   // channel count.
722   media::ChannelLayout layout = media::CHANNEL_LAYOUT_UNSUPPORTED;
723   switch (channels) {
724     case 1:
725       layout = media::CHANNEL_LAYOUT_MONO;
726       break;
727     case 2:
728       layout = media::CHANNEL_LAYOUT_STEREO;
729       break;
730     case 3:
731       layout = media::CHANNEL_LAYOUT_2_1;
732       break;
733     case 4:
734       layout = media::CHANNEL_LAYOUT_4_0;
735       break;
736     case 5:
737       layout = media::CHANNEL_LAYOUT_5_0;
738       break;
739     case 6:
740       layout = media::CHANNEL_LAYOUT_5_1;
741       break;
742     case 7:
743       layout = media::CHANNEL_LAYOUT_7_0;
744       break;
745     case 8:
746       layout = media::CHANNEL_LAYOUT_7_1;
747       break;
748     default:
749       layout = media::CHANNEL_LAYOUT_STEREO;
750   }
751 
752   int session_id = 0;
753   if (input_device_id.isNull() ||
754       !base::StringToInt(base::UTF16ToUTF8(input_device_id), &session_id)) {
755     if (input_channels > 0)
756       DLOG(WARNING) << "createAudioDevice(): request for audio input ignored";
757 
758     input_channels = 0;
759   }
760 
761   media::AudioParameters params(
762       media::AudioParameters::AUDIO_PCM_LOW_LATENCY,
763       layout, input_channels,
764       static_cast<int>(sample_rate), 16, buffer_size,
765       media::AudioParameters::NO_EFFECTS);
766 
767   return new RendererWebAudioDeviceImpl(params, callback, session_id);
768 }
769 
770 #if defined(OS_ANDROID)
loadAudioResource(blink::WebAudioBus * destination_bus,const char * audio_file_data,size_t data_size)771 bool RendererWebKitPlatformSupportImpl::loadAudioResource(
772     blink::WebAudioBus* destination_bus, const char* audio_file_data,
773     size_t data_size) {
774   return DecodeAudioFileData(destination_bus,
775                              audio_file_data,
776                              data_size,
777                              thread_safe_sender_);
778 }
779 #else
loadAudioResource(blink::WebAudioBus * destination_bus,const char * audio_file_data,size_t data_size)780 bool RendererWebKitPlatformSupportImpl::loadAudioResource(
781     blink::WebAudioBus* destination_bus, const char* audio_file_data,
782     size_t data_size) {
783   return DecodeAudioFileData(
784       destination_bus, audio_file_data, data_size);
785 }
786 #endif  // defined(OS_ANDROID)
787 
788 //------------------------------------------------------------------------------
789 
790 blink::WebMIDIAccessor*
createMIDIAccessor(blink::WebMIDIAccessorClient * client)791 RendererWebKitPlatformSupportImpl::createMIDIAccessor(
792     blink::WebMIDIAccessorClient* client) {
793   blink::WebMIDIAccessor* accessor =
794       GetContentClient()->renderer()->OverrideCreateMIDIAccessor(client);
795   if (accessor)
796     return accessor;
797 
798   return new RendererWebMIDIAccessorImpl(client);
799 }
800 
getPluginList(bool refresh,blink::WebPluginListBuilder * builder)801 void RendererWebKitPlatformSupportImpl::getPluginList(
802     bool refresh,
803     blink::WebPluginListBuilder* builder) {
804 #if defined(ENABLE_PLUGINS)
805   std::vector<WebPluginInfo> plugins;
806   if (!plugin_refresh_allowed_)
807     refresh = false;
808   RenderThread::Get()->Send(
809       new ViewHostMsg_GetPlugins(refresh, &plugins));
810   for (size_t i = 0; i < plugins.size(); ++i) {
811     const WebPluginInfo& plugin = plugins[i];
812 
813     builder->addPlugin(
814         plugin.name, plugin.desc,
815         plugin.path.BaseName().AsUTF16Unsafe());
816 
817     for (size_t j = 0; j < plugin.mime_types.size(); ++j) {
818       const WebPluginMimeType& mime_type = plugin.mime_types[j];
819 
820       builder->addMediaTypeToLastPlugin(
821           WebString::fromUTF8(mime_type.mime_type), mime_type.description);
822 
823       for (size_t k = 0; k < mime_type.file_extensions.size(); ++k) {
824         builder->addFileExtensionToLastMediaType(
825             WebString::fromUTF8(mime_type.file_extensions[k]));
826       }
827     }
828   }
829 #endif
830 }
831 
832 //------------------------------------------------------------------------------
833 
834 blink::WebPublicSuffixList*
publicSuffixList()835 RendererWebKitPlatformSupportImpl::publicSuffixList() {
836   return &public_suffix_list_;
837 }
838 
839 //------------------------------------------------------------------------------
840 
841 blink::WebString
signedPublicKeyAndChallengeString(unsigned key_size_index,const blink::WebString & challenge,const blink::WebURL & url)842 RendererWebKitPlatformSupportImpl::signedPublicKeyAndChallengeString(
843     unsigned key_size_index,
844     const blink::WebString& challenge,
845     const blink::WebURL& url) {
846   std::string signed_public_key;
847   RenderThread::Get()->Send(new ViewHostMsg_Keygen(
848       static_cast<uint32>(key_size_index),
849       challenge.utf8(),
850       GURL(url),
851       &signed_public_key));
852   return WebString::fromUTF8(signed_public_key);
853 }
854 
855 //------------------------------------------------------------------------------
856 
screenColorProfile(WebVector<char> * to_profile)857 void RendererWebKitPlatformSupportImpl::screenColorProfile(
858     WebVector<char>* to_profile) {
859 #if defined(OS_WIN)
860   // On Windows screen color profile is only available in the browser.
861   std::vector<char> profile;
862   // This Send() can be called from any impl-side thread. Use a thread
863   // safe send to avoid crashing trying to access RenderThread::Get(),
864   // which is not accessible from arbitrary threads.
865   thread_safe_sender_->Send(
866       new ViewHostMsg_GetMonitorColorProfile(&profile));
867   *to_profile = profile;
868 #else
869   // On other platforms, the primary monitor color profile can be read
870   // directly.
871   gfx::ColorProfile profile;
872   *to_profile = profile.profile();
873 #endif
874 }
875 
876 //------------------------------------------------------------------------------
877 
878 blink::WebScrollbarBehavior*
scrollbarBehavior()879     RendererWebKitPlatformSupportImpl::scrollbarBehavior() {
880   return web_scrollbar_behavior_.get();
881 }
882 
883 //------------------------------------------------------------------------------
884 
blobRegistry()885 WebBlobRegistry* RendererWebKitPlatformSupportImpl::blobRegistry() {
886   // blob_registry_ can be NULL when running some tests.
887   return blob_registry_.get();
888 }
889 
890 //------------------------------------------------------------------------------
891 
sampleGamepads(WebGamepads & gamepads)892 void RendererWebKitPlatformSupportImpl::sampleGamepads(WebGamepads& gamepads) {
893   DCHECK(gamepad_provider_);
894   gamepad_provider_->SampleGamepads(gamepads);
895 }
896 
setGamepadListener(blink::WebGamepadListener * listener)897 void RendererWebKitPlatformSupportImpl::setGamepadListener(
898       blink::WebGamepadListener* listener) {
899   DCHECK(gamepad_provider_);
900   gamepad_provider_->SetGamepadListener(listener);
901 }
902 
903 //------------------------------------------------------------------------------
904 
905 WebRTCPeerConnectionHandler*
createRTCPeerConnectionHandler(WebRTCPeerConnectionHandlerClient * client)906 RendererWebKitPlatformSupportImpl::createRTCPeerConnectionHandler(
907     WebRTCPeerConnectionHandlerClient* client) {
908   RenderThreadImpl* render_thread = RenderThreadImpl::current();
909   DCHECK(render_thread);
910   if (!render_thread)
911     return NULL;
912 
913 #if defined(ENABLE_WEBRTC)
914   WebRTCPeerConnectionHandler* peer_connection_handler =
915       GetContentClient()->renderer()->OverrideCreateWebRTCPeerConnectionHandler(
916           client);
917   if (peer_connection_handler)
918     return peer_connection_handler;
919 
920   PeerConnectionDependencyFactory* rtc_dependency_factory =
921       render_thread->GetPeerConnectionDependencyFactory();
922   return rtc_dependency_factory->CreateRTCPeerConnectionHandler(client);
923 #else
924   return NULL;
925 #endif  // defined(ENABLE_WEBRTC)
926 }
927 
928 //------------------------------------------------------------------------------
929 
930 WebMediaStreamCenter*
createMediaStreamCenter(WebMediaStreamCenterClient * client)931 RendererWebKitPlatformSupportImpl::createMediaStreamCenter(
932     WebMediaStreamCenterClient* client) {
933   RenderThreadImpl* render_thread = RenderThreadImpl::current();
934   DCHECK(render_thread);
935   if (!render_thread)
936     return NULL;
937   return render_thread->CreateMediaStreamCenter(client);
938 }
939 
940 // static
SetSandboxEnabledForTesting(bool enable)941 bool RendererWebKitPlatformSupportImpl::SetSandboxEnabledForTesting(
942     bool enable) {
943   bool was_enabled = g_sandbox_enabled;
944   g_sandbox_enabled = enable;
945   return was_enabled;
946 }
947 
948 //------------------------------------------------------------------------------
949 
950 blink::WebSpeechSynthesizer*
createSpeechSynthesizer(blink::WebSpeechSynthesizerClient * client)951 RendererWebKitPlatformSupportImpl::createSpeechSynthesizer(
952     blink::WebSpeechSynthesizerClient* client) {
953   return GetContentClient()->renderer()->OverrideSpeechSynthesizer(client);
954 }
955 
956 //------------------------------------------------------------------------------
957 
processMemorySizesInBytes(size_t * private_bytes,size_t * shared_bytes)958 bool RendererWebKitPlatformSupportImpl::processMemorySizesInBytes(
959     size_t* private_bytes, size_t* shared_bytes) {
960   content::RenderThread::Get()->Send(
961       new ViewHostMsg_GetProcessMemorySizes(private_bytes, shared_bytes));
962   return true;
963 }
964 
965 //------------------------------------------------------------------------------
966 
967 blink::WebGraphicsContext3D*
createOffscreenGraphicsContext3D(const blink::WebGraphicsContext3D::Attributes & attributes)968 RendererWebKitPlatformSupportImpl::createOffscreenGraphicsContext3D(
969     const blink::WebGraphicsContext3D::Attributes& attributes) {
970   return createOffscreenGraphicsContext3D(attributes, NULL);
971 }
972 
973 blink::WebGraphicsContext3D*
createOffscreenGraphicsContext3D(const blink::WebGraphicsContext3D::Attributes & attributes,blink::WebGraphicsContext3D * share_context)974 RendererWebKitPlatformSupportImpl::createOffscreenGraphicsContext3D(
975     const blink::WebGraphicsContext3D::Attributes& attributes,
976     blink::WebGraphicsContext3D* share_context) {
977   if (!RenderThreadImpl::current())
978     return NULL;
979 
980 #if defined(OS_ANDROID)
981   if (SynchronousCompositorFactory* factory =
982           SynchronousCompositorFactory::GetInstance()) {
983     return factory->CreateOffscreenGraphicsContext3D(attributes);
984   }
985 #endif
986 
987   scoped_refptr<GpuChannelHost> gpu_channel_host(
988       RenderThreadImpl::current()->EstablishGpuChannelSync(
989           CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE));
990 
991   WebGraphicsContext3DCommandBufferImpl::SharedMemoryLimits limits;
992   bool lose_context_when_out_of_memory = false;
993   return WebGraphicsContext3DCommandBufferImpl::CreateOffscreenContext(
994       gpu_channel_host.get(),
995       attributes,
996       lose_context_when_out_of_memory,
997       GURL(attributes.topDocumentURL),
998       limits,
999       static_cast<WebGraphicsContext3DCommandBufferImpl*>(share_context));
1000 }
1001 
1002 //------------------------------------------------------------------------------
1003 
1004 blink::WebGraphicsContext3DProvider* RendererWebKitPlatformSupportImpl::
createSharedOffscreenGraphicsContext3DProvider()1005     createSharedOffscreenGraphicsContext3DProvider() {
1006   scoped_refptr<webkit::gpu::ContextProviderWebContext> provider =
1007       RenderThreadImpl::current()->SharedMainThreadContextProvider();
1008   if (!provider)
1009     return NULL;
1010   return new WebGraphicsContext3DProviderImpl(provider);
1011 }
1012 
1013 //------------------------------------------------------------------------------
1014 
1015 blink::WebCompositorSupport*
compositorSupport()1016 RendererWebKitPlatformSupportImpl::compositorSupport() {
1017   return &compositor_support_;
1018 }
1019 
1020 //------------------------------------------------------------------------------
1021 
convertIDNToUnicode(const blink::WebString & host,const blink::WebString & languages)1022 blink::WebString RendererWebKitPlatformSupportImpl::convertIDNToUnicode(
1023     const blink::WebString& host,
1024     const blink::WebString& languages) {
1025   return net::IDNToUnicode(host.utf8(), languages.utf8());
1026 }
1027 
1028 //------------------------------------------------------------------------------
1029 
setDeviceMotionListener(blink::WebDeviceMotionListener * listener)1030 void RendererWebKitPlatformSupportImpl::setDeviceMotionListener(
1031     blink::WebDeviceMotionListener* listener) {
1032   if (g_test_device_motion_data == 0) {
1033     if (!device_motion_event_pump_) {
1034       device_motion_event_pump_.reset(new DeviceMotionEventPump);
1035       device_motion_event_pump_->Attach(RenderThreadImpl::current());
1036     }
1037     device_motion_event_pump_->SetListener(listener);
1038   } else if (listener) {
1039     // Testing mode: just echo the test data to the listener.
1040     base::MessageLoopProxy::current()->PostTask(
1041         FROM_HERE,
1042         base::Bind(&blink::WebDeviceMotionListener::didChangeDeviceMotion,
1043                    base::Unretained(listener),
1044                    g_test_device_motion_data.Get()));
1045   }
1046 }
1047 
1048 // static
SetMockDeviceMotionDataForTesting(const blink::WebDeviceMotionData & data)1049 void RendererWebKitPlatformSupportImpl::SetMockDeviceMotionDataForTesting(
1050     const blink::WebDeviceMotionData& data) {
1051   g_test_device_motion_data.Get() = data;
1052 }
1053 
1054 // static
ResetMockScreenOrientationForTesting()1055 void RendererWebKitPlatformSupportImpl::ResetMockScreenOrientationForTesting()
1056 {
1057   if (!(g_test_screen_orientation_controller == 0))
1058     g_test_screen_orientation_controller.Get().ResetData();
1059 }
1060 
1061 //------------------------------------------------------------------------------
1062 
setDeviceOrientationListener(blink::WebDeviceOrientationListener * listener)1063 void RendererWebKitPlatformSupportImpl::setDeviceOrientationListener(
1064     blink::WebDeviceOrientationListener* listener) {
1065   if (g_test_device_orientation_data == 0) {
1066     if (!device_orientation_event_pump_) {
1067       device_orientation_event_pump_.reset(new DeviceOrientationEventPump);
1068       device_orientation_event_pump_->Attach(RenderThreadImpl::current());
1069     }
1070     device_orientation_event_pump_->SetListener(listener);
1071   } else if (listener) {
1072     // Testing mode: just echo the test data to the listener.
1073     base::MessageLoopProxy::current()->PostTask(
1074         FROM_HERE,
1075         base::Bind(
1076             &blink::WebDeviceOrientationListener::didChangeDeviceOrientation,
1077             base::Unretained(listener),
1078             g_test_device_orientation_data.Get()));
1079   }
1080 }
1081 
1082 // static
SetMockDeviceOrientationDataForTesting(const blink::WebDeviceOrientationData & data)1083 void RendererWebKitPlatformSupportImpl::SetMockDeviceOrientationDataForTesting(
1084     const blink::WebDeviceOrientationData& data) {
1085   g_test_device_orientation_data.Get() = data;
1086 }
1087 
1088 //------------------------------------------------------------------------------
1089 
vibrate(unsigned int milliseconds)1090 void RendererWebKitPlatformSupportImpl::vibrate(unsigned int milliseconds) {
1091   RenderThread::Get()->Send(
1092       new ViewHostMsg_Vibrate(base::checked_cast<int64>(milliseconds)));
1093 }
1094 
cancelVibration()1095 void RendererWebKitPlatformSupportImpl::cancelVibration() {
1096   RenderThread::Get()->Send(new ViewHostMsg_CancelVibration());
1097 }
1098 
1099 //------------------------------------------------------------------------------
1100 
1101 // static
SetMockScreenOrientationForTesting(RenderView * render_view,blink::WebScreenOrientationType orientation)1102 void RendererWebKitPlatformSupportImpl::SetMockScreenOrientationForTesting(
1103     RenderView* render_view,
1104     blink::WebScreenOrientationType orientation) {
1105   g_test_screen_orientation_controller.Get()
1106       .UpdateDeviceOrientation(render_view, orientation);
1107 }
1108 
1109 //------------------------------------------------------------------------------
1110 
queryStorageUsageAndQuota(const blink::WebURL & storage_partition,blink::WebStorageQuotaType type,blink::WebStorageQuotaCallbacks callbacks)1111 void RendererWebKitPlatformSupportImpl::queryStorageUsageAndQuota(
1112     const blink::WebURL& storage_partition,
1113     blink::WebStorageQuotaType type,
1114     blink::WebStorageQuotaCallbacks callbacks) {
1115   if (!thread_safe_sender_.get() || !quota_message_filter_.get())
1116     return;
1117   QuotaDispatcher::ThreadSpecificInstance(
1118       thread_safe_sender_.get(),
1119       quota_message_filter_.get())->QueryStorageUsageAndQuota(
1120           storage_partition,
1121           static_cast<quota::StorageType>(type),
1122           QuotaDispatcher::CreateWebStorageQuotaCallbacksWrapper(callbacks));
1123 }
1124 
1125 //------------------------------------------------------------------------------
1126 
setBatteryStatusListener(blink::WebBatteryStatusListener * listener)1127 void RendererWebKitPlatformSupportImpl::setBatteryStatusListener(
1128     blink::WebBatteryStatusListener* listener) {
1129   if (RenderThreadImpl::current() &&
1130       RenderThreadImpl::current()->layout_test_mode()) {
1131     // If we are in test mode, we want to use a fake battery status dispatcher,
1132     // which does not communicate with the browser process. Battery status
1133     // changes are signalled by invoking MockBatteryStatusChangedForTesting().
1134     g_test_battery_status_dispatcher.Get().SetListener(listener);
1135     return;
1136   }
1137 
1138   if (!battery_status_dispatcher_) {
1139     battery_status_dispatcher_.reset(
1140         new BatteryStatusDispatcher(RenderThreadImpl::current()));
1141   }
1142   battery_status_dispatcher_->SetListener(listener);
1143 }
1144 
1145 // static
MockBatteryStatusChangedForTesting(const blink::WebBatteryStatus & status)1146 void RendererWebKitPlatformSupportImpl::MockBatteryStatusChangedForTesting(
1147     const blink::WebBatteryStatus& status) {
1148   g_test_battery_status_dispatcher.Get().PostBatteryStatusChange(status);
1149 }
1150 
1151 }  // namespace content
1152