• 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 "ppapi/proxy/ppb_instance_proxy.h"
6 
7 #include "base/memory/ref_counted.h"
8 #include "build/build_config.h"
9 #include "ppapi/c/pp_errors.h"
10 #include "ppapi/c/pp_time.h"
11 #include "ppapi/c/pp_var.h"
12 #include "ppapi/c/ppb_audio_config.h"
13 #include "ppapi/c/ppb_instance.h"
14 #include "ppapi/c/ppb_messaging.h"
15 #include "ppapi/c/ppb_mouse_lock.h"
16 #include "ppapi/c/private/pp_content_decryptor.h"
17 #include "ppapi/proxy/broker_resource.h"
18 #include "ppapi/proxy/browser_font_singleton_resource.h"
19 #include "ppapi/proxy/content_decryptor_private_serializer.h"
20 #include "ppapi/proxy/enter_proxy.h"
21 #include "ppapi/proxy/extensions_common_resource.h"
22 #include "ppapi/proxy/flash_clipboard_resource.h"
23 #include "ppapi/proxy/flash_file_resource.h"
24 #include "ppapi/proxy/flash_fullscreen_resource.h"
25 #include "ppapi/proxy/flash_resource.h"
26 #include "ppapi/proxy/gamepad_resource.h"
27 #include "ppapi/proxy/host_dispatcher.h"
28 #include "ppapi/proxy/isolated_file_system_private_resource.h"
29 #include "ppapi/proxy/network_proxy_resource.h"
30 #include "ppapi/proxy/pdf_resource.h"
31 #include "ppapi/proxy/plugin_dispatcher.h"
32 #include "ppapi/proxy/ppapi_messages.h"
33 #include "ppapi/proxy/serialized_var.h"
34 #include "ppapi/proxy/truetype_font_singleton_resource.h"
35 #include "ppapi/shared_impl/ppapi_globals.h"
36 #include "ppapi/shared_impl/ppb_url_util_shared.h"
37 #include "ppapi/shared_impl/ppb_view_shared.h"
38 #include "ppapi/shared_impl/var.h"
39 #include "ppapi/thunk/enter.h"
40 #include "ppapi/thunk/ppb_graphics_2d_api.h"
41 #include "ppapi/thunk/ppb_graphics_3d_api.h"
42 #include "ppapi/thunk/thunk.h"
43 
44 // Windows headers interfere with this file.
45 #ifdef PostMessage
46 #undef PostMessage
47 #endif
48 
49 using ppapi::thunk::EnterInstanceNoLock;
50 using ppapi::thunk::EnterResourceNoLock;
51 using ppapi::thunk::PPB_Graphics2D_API;
52 using ppapi::thunk::PPB_Graphics3D_API;
53 using ppapi::thunk::PPB_Instance_API;
54 
55 namespace ppapi {
56 namespace proxy {
57 
58 namespace {
59 
60 const char kSerializationError[] = "Failed to convert a PostMessage "
61     "argument from a PP_Var to a Javascript value. It may have cycles or be of "
62     "an unsupported type.";
63 
CreateInstanceProxy(Dispatcher * dispatcher)64 InterfaceProxy* CreateInstanceProxy(Dispatcher* dispatcher) {
65   return new PPB_Instance_Proxy(dispatcher);
66 }
67 
RequestSurroundingText(PP_Instance instance)68 void RequestSurroundingText(PP_Instance instance) {
69   PluginDispatcher* dispatcher = PluginDispatcher::GetForInstance(instance);
70   if (!dispatcher)
71     return;  // Instance has gone away while message was pending.
72 
73   InstanceData* data = dispatcher->GetInstanceData(instance);
74   DCHECK(data);  // Should have it, since we still have a dispatcher.
75   data->is_request_surrounding_text_pending = false;
76   if (!data->should_do_request_surrounding_text)
77     return;
78 
79   // Just fake out a RequestSurroundingText message to the proxy for the PPP
80   // interface.
81   InterfaceProxy* proxy = dispatcher->GetInterfaceProxy(API_ID_PPP_TEXT_INPUT);
82   if (!proxy)
83     return;
84   proxy->OnMessageReceived(PpapiMsg_PPPTextInput_RequestSurroundingText(
85       API_ID_PPP_TEXT_INPUT, instance,
86       PPB_Instance_Shared::kExtraCharsForTextInput));
87 }
88 
89 }  // namespace
90 
PPB_Instance_Proxy(Dispatcher * dispatcher)91 PPB_Instance_Proxy::PPB_Instance_Proxy(Dispatcher* dispatcher)
92     : InterfaceProxy(dispatcher),
93       callback_factory_(this) {
94 }
95 
~PPB_Instance_Proxy()96 PPB_Instance_Proxy::~PPB_Instance_Proxy() {
97 }
98 
99 // static
GetInfoPrivate()100 const InterfaceProxy::Info* PPB_Instance_Proxy::GetInfoPrivate() {
101   static const Info info = {
102     ppapi::thunk::GetPPB_Instance_Private_0_1_Thunk(),
103     PPB_INSTANCE_PRIVATE_INTERFACE_0_1,
104     API_ID_NONE,  // 1_0 is the canonical one.
105     false,
106     &CreateInstanceProxy,
107   };
108   return &info;
109 }
110 
OnMessageReceived(const IPC::Message & msg)111 bool PPB_Instance_Proxy::OnMessageReceived(const IPC::Message& msg) {
112   // Prevent the dispatcher from going away during a call to ExecuteScript.
113   // This must happen OUTSIDE of ExecuteScript since the SerializedVars use
114   // the dispatcher upon return of the function (converting the
115   // SerializedVarReturnValue/OutParam to a SerializedVar in the destructor).
116 #if !defined(OS_NACL)
117   ScopedModuleReference death_grip(dispatcher());
118 #endif
119 
120   bool handled = true;
121   IPC_BEGIN_MESSAGE_MAP(PPB_Instance_Proxy, msg)
122 #if !defined(OS_NACL)
123     // Plugin -> Host messages.
124     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetWindowObject,
125                         OnHostMsgGetWindowObject)
126     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetOwnerElementObject,
127                         OnHostMsgGetOwnerElementObject)
128     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_BindGraphics,
129                         OnHostMsgBindGraphics)
130     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_IsFullFrame,
131                         OnHostMsgIsFullFrame)
132     IPC_MESSAGE_HANDLER(
133         PpapiHostMsg_PPBInstance_GetAudioHardwareOutputSampleRate,
134         OnHostMsgGetAudioHardwareOutputSampleRate)
135     IPC_MESSAGE_HANDLER(
136         PpapiHostMsg_PPBInstance_GetAudioHardwareOutputBufferSize,
137         OnHostMsgGetAudioHardwareOutputBufferSize)
138     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_ExecuteScript,
139                         OnHostMsgExecuteScript)
140     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetDefaultCharSet,
141                         OnHostMsgGetDefaultCharSet)
142     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_PostMessage,
143                         OnHostMsgPostMessage)
144     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SetFullscreen,
145                         OnHostMsgSetFullscreen)
146     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetScreenSize,
147                         OnHostMsgGetScreenSize)
148     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_RequestInputEvents,
149                         OnHostMsgRequestInputEvents)
150     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_ClearInputEvents,
151                         OnHostMsgClearInputEvents)
152     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_LockMouse,
153                         OnHostMsgLockMouse)
154     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_UnlockMouse,
155                         OnHostMsgUnlockMouse)
156     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SetCursor,
157                         OnHostMsgSetCursor)
158     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SetTextInputType,
159                         OnHostMsgSetTextInputType)
160     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_UpdateCaretPosition,
161                         OnHostMsgUpdateCaretPosition)
162     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_CancelCompositionText,
163                         OnHostMsgCancelCompositionText)
164     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_UpdateSurroundingText,
165                         OnHostMsgUpdateSurroundingText)
166     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetDocumentURL,
167                         OnHostMsgGetDocumentURL)
168     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_ResolveRelativeToDocument,
169                         OnHostMsgResolveRelativeToDocument)
170     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DocumentCanRequest,
171                         OnHostMsgDocumentCanRequest)
172     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DocumentCanAccessDocument,
173                         OnHostMsgDocumentCanAccessDocument)
174     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetPluginInstanceURL,
175                         OnHostMsgGetPluginInstanceURL)
176     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_GetPluginReferrerURL,
177                         OnHostMsgGetPluginReferrerURL)
178     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SessionCreated,
179                         OnHostMsgSessionCreated)
180     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SessionMessage,
181                         OnHostMsgSessionMessage)
182     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SessionReady,
183                         OnHostMsgSessionReady)
184     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SessionClosed,
185                         OnHostMsgSessionClosed)
186     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_SessionError,
187                         OnHostMsgSessionError)
188     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DeliverBlock,
189                         OnHostMsgDeliverBlock)
190     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DecoderInitializeDone,
191                         OnHostMsgDecoderInitializeDone)
192     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DecoderDeinitializeDone,
193                         OnHostMsgDecoderDeinitializeDone)
194     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DecoderResetDone,
195                         OnHostMsgDecoderResetDone)
196     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DeliverFrame,
197                         OnHostMsgDeliverFrame)
198     IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBInstance_DeliverSamples,
199                         OnHostMsgDeliverSamples)
200 #endif  // !defined(OS_NACL)
201 
202     // Host -> Plugin messages.
203     IPC_MESSAGE_HANDLER(PpapiMsg_PPBInstance_MouseLockComplete,
204                         OnPluginMsgMouseLockComplete)
205 
206     IPC_MESSAGE_UNHANDLED(handled = false)
207   IPC_END_MESSAGE_MAP()
208   return handled;
209 }
210 
BindGraphics(PP_Instance instance,PP_Resource device)211 PP_Bool PPB_Instance_Proxy::BindGraphics(PP_Instance instance,
212                                          PP_Resource device) {
213   // If device is 0, pass a null HostResource. This signals the host to unbind
214   // all devices.
215   HostResource host_resource;
216   PP_Resource pp_resource = 0;
217   if (device) {
218     Resource* resource =
219         PpapiGlobals::Get()->GetResourceTracker()->GetResource(device);
220     if (!resource || resource->pp_instance() != instance)
221       return PP_FALSE;
222     host_resource = resource->host_resource();
223     pp_resource = resource->pp_resource();
224   } else {
225     // Passing 0 means unbinding all devices.
226     dispatcher()->Send(new PpapiHostMsg_PPBInstance_BindGraphics(
227         API_ID_PPB_INSTANCE, instance, 0));
228     return PP_TRUE;
229   }
230 
231   // We need to pass different resource to Graphics 2D and 3D right now.  Once
232   // 3D is migrated to the new design, we should be able to unify this.
233   EnterResourceNoLock<PPB_Graphics2D_API> enter_2d(device, false);
234   EnterResourceNoLock<PPB_Graphics3D_API> enter_3d(device, false);
235   if (enter_2d.succeeded()) {
236     dispatcher()->Send(new PpapiHostMsg_PPBInstance_BindGraphics(
237         API_ID_PPB_INSTANCE, instance, pp_resource));
238     return PP_TRUE;
239   } else if (enter_3d.succeeded()) {
240     dispatcher()->Send(new PpapiHostMsg_PPBInstance_BindGraphics(
241         API_ID_PPB_INSTANCE, instance, host_resource.host_resource()));
242     return PP_TRUE;
243   }
244   return PP_FALSE;
245 }
246 
IsFullFrame(PP_Instance instance)247 PP_Bool PPB_Instance_Proxy::IsFullFrame(PP_Instance instance) {
248   PP_Bool result = PP_FALSE;
249   dispatcher()->Send(new PpapiHostMsg_PPBInstance_IsFullFrame(
250       API_ID_PPB_INSTANCE, instance, &result));
251   return result;
252 }
253 
GetViewData(PP_Instance instance)254 const ViewData* PPB_Instance_Proxy::GetViewData(PP_Instance instance) {
255   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
256       GetInstanceData(instance);
257   if (!data)
258     return NULL;
259   return &data->view;
260 }
261 
FlashIsFullscreen(PP_Instance instance)262 PP_Bool PPB_Instance_Proxy::FlashIsFullscreen(PP_Instance instance) {
263   // This function is only used for proxying in the renderer process. It is not
264   // implemented in the plugin process.
265   NOTREACHED();
266   return PP_FALSE;
267 }
268 
GetWindowObject(PP_Instance instance)269 PP_Var PPB_Instance_Proxy::GetWindowObject(PP_Instance instance) {
270   ReceiveSerializedVarReturnValue result;
271   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetWindowObject(
272       API_ID_PPB_INSTANCE, instance, &result));
273   return result.Return(dispatcher());
274 }
275 
GetOwnerElementObject(PP_Instance instance)276 PP_Var PPB_Instance_Proxy::GetOwnerElementObject(PP_Instance instance) {
277   ReceiveSerializedVarReturnValue result;
278   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetOwnerElementObject(
279       API_ID_PPB_INSTANCE, instance, &result));
280   return result.Return(dispatcher());
281 }
282 
ExecuteScript(PP_Instance instance,PP_Var script,PP_Var * exception)283 PP_Var PPB_Instance_Proxy::ExecuteScript(PP_Instance instance,
284                                          PP_Var script,
285                                          PP_Var* exception) {
286   ReceiveSerializedException se(dispatcher(), exception);
287   if (se.IsThrown())
288     return PP_MakeUndefined();
289 
290   ReceiveSerializedVarReturnValue result;
291   dispatcher()->Send(new PpapiHostMsg_PPBInstance_ExecuteScript(
292       API_ID_PPB_INSTANCE, instance,
293       SerializedVarSendInput(dispatcher(), script), &se, &result));
294   return result.Return(dispatcher());
295 }
296 
GetAudioHardwareOutputSampleRate(PP_Instance instance)297 uint32_t PPB_Instance_Proxy::GetAudioHardwareOutputSampleRate(
298     PP_Instance instance) {
299   uint32_t result = PP_AUDIOSAMPLERATE_NONE;
300   dispatcher()->Send(
301       new PpapiHostMsg_PPBInstance_GetAudioHardwareOutputSampleRate(
302           API_ID_PPB_INSTANCE, instance, &result));
303   return result;
304 }
305 
GetAudioHardwareOutputBufferSize(PP_Instance instance)306 uint32_t PPB_Instance_Proxy::GetAudioHardwareOutputBufferSize(
307     PP_Instance instance) {
308   uint32_t result = 0;
309   dispatcher()->Send(
310       new PpapiHostMsg_PPBInstance_GetAudioHardwareOutputBufferSize(
311           API_ID_PPB_INSTANCE, instance, &result));
312   return result;
313 }
314 
GetDefaultCharSet(PP_Instance instance)315 PP_Var PPB_Instance_Proxy::GetDefaultCharSet(PP_Instance instance) {
316   PluginDispatcher* dispatcher = PluginDispatcher::GetForInstance(instance);
317   if (!dispatcher)
318     return PP_MakeUndefined();
319 
320   ReceiveSerializedVarReturnValue result;
321   dispatcher->Send(new PpapiHostMsg_PPBInstance_GetDefaultCharSet(
322       API_ID_PPB_INSTANCE, instance, &result));
323   return result.Return(dispatcher);
324 }
325 
NumberOfFindResultsChanged(PP_Instance instance,int32_t total,PP_Bool final_result)326 void PPB_Instance_Proxy::NumberOfFindResultsChanged(PP_Instance instance,
327                                                     int32_t total,
328                                                     PP_Bool final_result) {
329   NOTIMPLEMENTED();  // Not proxied yet.
330 }
331 
SelectedFindResultChanged(PP_Instance instance,int32_t index)332 void PPB_Instance_Proxy::SelectedFindResultChanged(PP_Instance instance,
333                                                    int32_t index) {
334   NOTIMPLEMENTED();  // Not proxied yet.
335 }
336 
IsFullscreen(PP_Instance instance)337 PP_Bool PPB_Instance_Proxy::IsFullscreen(PP_Instance instance) {
338   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
339       GetInstanceData(instance);
340   if (!data)
341     return PP_FALSE;
342   return PP_FromBool(data->view.is_fullscreen);
343 }
344 
SetFullscreen(PP_Instance instance,PP_Bool fullscreen)345 PP_Bool PPB_Instance_Proxy::SetFullscreen(PP_Instance instance,
346                                           PP_Bool fullscreen) {
347   PP_Bool result = PP_FALSE;
348   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SetFullscreen(
349       API_ID_PPB_INSTANCE, instance, fullscreen, &result));
350   return result;
351 }
352 
GetScreenSize(PP_Instance instance,PP_Size * size)353 PP_Bool PPB_Instance_Proxy::GetScreenSize(PP_Instance instance,
354                                           PP_Size* size) {
355   PP_Bool result = PP_FALSE;
356   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetScreenSize(
357       API_ID_PPB_INSTANCE, instance, &result, size));
358   return result;
359 }
360 
GetSingletonResource(PP_Instance instance,SingletonResourceID id)361 Resource* PPB_Instance_Proxy::GetSingletonResource(PP_Instance instance,
362                                                    SingletonResourceID id) {
363   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
364       GetInstanceData(instance);
365 
366   InstanceData::SingletonResourceMap::iterator it =
367       data->singleton_resources.find(id);
368   if (it != data->singleton_resources.end())
369     return it->second.get();
370 
371   scoped_refptr<Resource> new_singleton;
372   Connection connection(PluginGlobals::Get()->GetBrowserSender(), dispatcher());
373 
374   switch (id) {
375     case BROKER_SINGLETON_ID:
376       new_singleton = new BrokerResource(connection, instance);
377       break;
378     case EXTENSIONS_COMMON_SINGLETON_ID:
379       new_singleton = new ExtensionsCommonResource(connection, instance);
380       break;
381     case GAMEPAD_SINGLETON_ID:
382       new_singleton = new GamepadResource(connection, instance);
383       break;
384     case ISOLATED_FILESYSTEM_SINGLETON_ID:
385       new_singleton =
386           new IsolatedFileSystemPrivateResource(connection, instance);
387       break;
388     case NETWORK_PROXY_SINGLETON_ID:
389       new_singleton = new NetworkProxyResource(connection, instance);
390       break;
391     case TRUETYPE_FONT_SINGLETON_ID:
392       new_singleton = new TrueTypeFontSingletonResource(connection, instance);
393       break;
394 // Flash/trusted resources aren't needed for NaCl.
395 #if !defined(OS_NACL) && !defined(NACL_WIN64)
396     case BROWSER_FONT_SINGLETON_ID:
397       new_singleton = new BrowserFontSingletonResource(connection, instance);
398       break;
399     case FLASH_CLIPBOARD_SINGLETON_ID:
400       new_singleton = new FlashClipboardResource(connection, instance);
401       break;
402     case FLASH_FILE_SINGLETON_ID:
403       new_singleton = new FlashFileResource(connection, instance);
404       break;
405     case FLASH_FULLSCREEN_SINGLETON_ID:
406       new_singleton = new FlashFullscreenResource(connection, instance);
407       break;
408     case FLASH_SINGLETON_ID:
409       new_singleton = new FlashResource(connection, instance,
410           static_cast<PluginDispatcher*>(dispatcher()));
411       break;
412     case PDF_SINGLETON_ID:
413       new_singleton = new PDFResource(connection, instance);
414       break;
415 #else
416     case BROWSER_FONT_SINGLETON_ID:
417     case FLASH_CLIPBOARD_SINGLETON_ID:
418     case FLASH_FILE_SINGLETON_ID:
419     case FLASH_FULLSCREEN_SINGLETON_ID:
420     case FLASH_SINGLETON_ID:
421     case PDF_SINGLETON_ID:
422       NOTREACHED();
423       break;
424 #endif  // !defined(OS_NACL) && !defined(NACL_WIN64)
425   }
426 
427   if (!new_singleton.get()) {
428     // Getting here implies that a constructor is missing in the above switch.
429     NOTREACHED();
430     return NULL;
431   }
432 
433   data->singleton_resources[id] = new_singleton;
434   return new_singleton.get();
435 }
436 
RequestInputEvents(PP_Instance instance,uint32_t event_classes)437 int32_t PPB_Instance_Proxy::RequestInputEvents(PP_Instance instance,
438                                                uint32_t event_classes) {
439   dispatcher()->Send(new PpapiHostMsg_PPBInstance_RequestInputEvents(
440       API_ID_PPB_INSTANCE, instance, false, event_classes));
441 
442   // We always register for the classes we can handle, this function validates
443   // the flags so we can notify it if anything was invalid, without requiring
444   // a sync reply.
445   return ValidateRequestInputEvents(false, event_classes);
446 }
447 
RequestFilteringInputEvents(PP_Instance instance,uint32_t event_classes)448 int32_t PPB_Instance_Proxy::RequestFilteringInputEvents(
449     PP_Instance instance,
450     uint32_t event_classes) {
451   dispatcher()->Send(new PpapiHostMsg_PPBInstance_RequestInputEvents(
452       API_ID_PPB_INSTANCE, instance, true, event_classes));
453 
454   // We always register for the classes we can handle, this function validates
455   // the flags so we can notify it if anything was invalid, without requiring
456   // a sync reply.
457   return ValidateRequestInputEvents(true, event_classes);
458 }
459 
ClearInputEventRequest(PP_Instance instance,uint32_t event_classes)460 void PPB_Instance_Proxy::ClearInputEventRequest(PP_Instance instance,
461                                                 uint32_t event_classes) {
462   dispatcher()->Send(new PpapiHostMsg_PPBInstance_ClearInputEvents(
463       API_ID_PPB_INSTANCE, instance, event_classes));
464 }
465 
ZoomChanged(PP_Instance instance,double factor)466 void PPB_Instance_Proxy::ZoomChanged(PP_Instance instance,
467                                      double factor) {
468   // Not proxied yet.
469   NOTIMPLEMENTED();
470 }
471 
ZoomLimitsChanged(PP_Instance instance,double minimum_factor,double maximium_factor)472 void PPB_Instance_Proxy::ZoomLimitsChanged(PP_Instance instance,
473                                            double minimum_factor,
474                                            double maximium_factor) {
475   // Not proxied yet.
476   NOTIMPLEMENTED();
477 }
478 
GetDocumentURL(PP_Instance instance,PP_URLComponents_Dev * components)479 PP_Var PPB_Instance_Proxy::GetDocumentURL(PP_Instance instance,
480                                           PP_URLComponents_Dev* components) {
481   ReceiveSerializedVarReturnValue result;
482   PP_URLComponents_Dev url_components;
483   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetDocumentURL(
484       API_ID_PPB_INSTANCE, instance, &url_components, &result));
485   if (components)
486     *components = url_components;
487   return result.Return(dispatcher());
488 }
489 
490 #if !defined(OS_NACL)
ResolveRelativeToDocument(PP_Instance instance,PP_Var relative,PP_URLComponents_Dev * components)491 PP_Var PPB_Instance_Proxy::ResolveRelativeToDocument(
492     PP_Instance instance,
493     PP_Var relative,
494     PP_URLComponents_Dev* components) {
495   ReceiveSerializedVarReturnValue result;
496   dispatcher()->Send(new PpapiHostMsg_PPBInstance_ResolveRelativeToDocument(
497       API_ID_PPB_INSTANCE, instance,
498       SerializedVarSendInput(dispatcher(), relative),
499       &result));
500   return PPB_URLUtil_Shared::ConvertComponentsAndReturnURL(
501       result.Return(dispatcher()),
502       components);
503 }
504 
DocumentCanRequest(PP_Instance instance,PP_Var url)505 PP_Bool PPB_Instance_Proxy::DocumentCanRequest(PP_Instance instance,
506                                                PP_Var url) {
507   PP_Bool result = PP_FALSE;
508   dispatcher()->Send(new PpapiHostMsg_PPBInstance_DocumentCanRequest(
509       API_ID_PPB_INSTANCE, instance,
510       SerializedVarSendInput(dispatcher(), url),
511       &result));
512   return result;
513 }
514 
DocumentCanAccessDocument(PP_Instance instance,PP_Instance target)515 PP_Bool PPB_Instance_Proxy::DocumentCanAccessDocument(PP_Instance instance,
516                                                       PP_Instance target) {
517   PP_Bool result = PP_FALSE;
518   dispatcher()->Send(new PpapiHostMsg_PPBInstance_DocumentCanAccessDocument(
519       API_ID_PPB_INSTANCE, instance, target, &result));
520   return result;
521 }
522 
GetPluginInstanceURL(PP_Instance instance,PP_URLComponents_Dev * components)523 PP_Var PPB_Instance_Proxy::GetPluginInstanceURL(
524       PP_Instance instance,
525       PP_URLComponents_Dev* components) {
526   ReceiveSerializedVarReturnValue result;
527   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetPluginInstanceURL(
528       API_ID_PPB_INSTANCE, instance, &result));
529   return PPB_URLUtil_Shared::ConvertComponentsAndReturnURL(
530       result.Return(dispatcher()),
531       components);
532 }
533 
GetPluginReferrerURL(PP_Instance instance,PP_URLComponents_Dev * components)534 PP_Var PPB_Instance_Proxy::GetPluginReferrerURL(
535       PP_Instance instance,
536       PP_URLComponents_Dev* components) {
537   ReceiveSerializedVarReturnValue result;
538   dispatcher()->Send(new PpapiHostMsg_PPBInstance_GetPluginReferrerURL(
539       API_ID_PPB_INSTANCE, instance, &result));
540   return PPB_URLUtil_Shared::ConvertComponentsAndReturnURL(
541       result.Return(dispatcher()),
542       components);
543 }
544 
SessionCreated(PP_Instance instance,uint32_t session_id,PP_Var web_session_id)545 void PPB_Instance_Proxy::SessionCreated(PP_Instance instance,
546                                         uint32_t session_id,
547                                         PP_Var web_session_id) {
548   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SessionCreated(
549       API_ID_PPB_INSTANCE,
550       instance,
551       session_id,
552       SerializedVarSendInput(dispatcher(), web_session_id)));
553 }
554 
SessionMessage(PP_Instance instance,uint32_t session_id,PP_Var message,PP_Var destination_url)555 void PPB_Instance_Proxy::SessionMessage(PP_Instance instance,
556                                         uint32_t session_id,
557                                         PP_Var message,
558                                         PP_Var destination_url) {
559   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SessionMessage(
560       API_ID_PPB_INSTANCE,
561       instance,
562       session_id,
563       SerializedVarSendInput(dispatcher(), message),
564       SerializedVarSendInput(dispatcher(), destination_url)));
565 }
566 
SessionReady(PP_Instance instance,uint32_t session_id)567 void PPB_Instance_Proxy::SessionReady(PP_Instance instance,
568                                       uint32_t session_id) {
569   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SessionReady(
570       API_ID_PPB_INSTANCE, instance, session_id));
571 }
572 
SessionClosed(PP_Instance instance,uint32_t session_id)573 void PPB_Instance_Proxy::SessionClosed(PP_Instance instance,
574                                        uint32_t session_id) {
575   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SessionClosed(
576       API_ID_PPB_INSTANCE, instance, session_id));
577 }
578 
SessionError(PP_Instance instance,uint32_t session_id,int32_t media_error,int32_t system_code)579 void PPB_Instance_Proxy::SessionError(PP_Instance instance,
580                                       uint32_t session_id,
581                                       int32_t media_error,
582                                       int32_t system_code) {
583   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SessionError(
584       API_ID_PPB_INSTANCE, instance, session_id, media_error, system_code));
585 }
586 
DeliverBlock(PP_Instance instance,PP_Resource decrypted_block,const PP_DecryptedBlockInfo * block_info)587 void PPB_Instance_Proxy::DeliverBlock(PP_Instance instance,
588                                       PP_Resource decrypted_block,
589                                       const PP_DecryptedBlockInfo* block_info) {
590   PP_Resource decrypted_block_host_resource = 0;
591 
592   if (decrypted_block) {
593     Resource* object =
594         PpapiGlobals::Get()->GetResourceTracker()->GetResource(decrypted_block);
595     if (!object || object->pp_instance() != instance) {
596       NOTREACHED();
597       return;
598     }
599     decrypted_block_host_resource = object->host_resource().host_resource();
600   }
601 
602   std::string serialized_block_info;
603   if (!SerializeBlockInfo(*block_info, &serialized_block_info)) {
604     NOTREACHED();
605     return;
606   }
607 
608   dispatcher()->Send(
609       new PpapiHostMsg_PPBInstance_DeliverBlock(API_ID_PPB_INSTANCE,
610           instance,
611           decrypted_block_host_resource,
612           serialized_block_info));
613 }
614 
DecoderInitializeDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id,PP_Bool success)615 void PPB_Instance_Proxy::DecoderInitializeDone(
616     PP_Instance instance,
617     PP_DecryptorStreamType decoder_type,
618     uint32_t request_id,
619     PP_Bool success) {
620   dispatcher()->Send(
621       new PpapiHostMsg_PPBInstance_DecoderInitializeDone(
622           API_ID_PPB_INSTANCE,
623           instance,
624           decoder_type,
625           request_id,
626           success));
627 }
628 
DecoderDeinitializeDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id)629 void PPB_Instance_Proxy::DecoderDeinitializeDone(
630     PP_Instance instance,
631     PP_DecryptorStreamType decoder_type,
632     uint32_t request_id) {
633   dispatcher()->Send(
634       new PpapiHostMsg_PPBInstance_DecoderDeinitializeDone(
635           API_ID_PPB_INSTANCE,
636           instance,
637           decoder_type,
638           request_id));
639 }
640 
DecoderResetDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id)641 void PPB_Instance_Proxy::DecoderResetDone(PP_Instance instance,
642                                           PP_DecryptorStreamType decoder_type,
643                                           uint32_t request_id) {
644   dispatcher()->Send(
645       new PpapiHostMsg_PPBInstance_DecoderResetDone(
646           API_ID_PPB_INSTANCE,
647           instance,
648           decoder_type,
649           request_id));
650 }
651 
DeliverFrame(PP_Instance instance,PP_Resource decrypted_frame,const PP_DecryptedFrameInfo * frame_info)652 void PPB_Instance_Proxy::DeliverFrame(PP_Instance instance,
653                                       PP_Resource decrypted_frame,
654                                       const PP_DecryptedFrameInfo* frame_info) {
655   PP_Resource host_resource = 0;
656   if (decrypted_frame != 0) {
657     ResourceTracker* tracker = PpapiGlobals::Get()->GetResourceTracker();
658     Resource* object = tracker->GetResource(decrypted_frame);
659 
660     if (!object || object->pp_instance() != instance) {
661       NOTREACHED();
662       return;
663     }
664 
665     host_resource = object->host_resource().host_resource();
666   }
667 
668   std::string serialized_frame_info;
669   if (!SerializeBlockInfo(*frame_info, &serialized_frame_info)) {
670     NOTREACHED();
671     return;
672   }
673 
674   dispatcher()->Send(
675       new PpapiHostMsg_PPBInstance_DeliverFrame(API_ID_PPB_INSTANCE,
676                                                 instance,
677                                                 host_resource,
678                                                 serialized_frame_info));
679 }
680 
DeliverSamples(PP_Instance instance,PP_Resource decrypted_samples,const PP_DecryptedSampleInfo * sample_info)681 void PPB_Instance_Proxy::DeliverSamples(
682     PP_Instance instance,
683     PP_Resource decrypted_samples,
684     const PP_DecryptedSampleInfo* sample_info) {
685   PP_Resource host_resource = 0;
686   if (decrypted_samples != 0) {
687     ResourceTracker* tracker = PpapiGlobals::Get()->GetResourceTracker();
688     Resource* object = tracker->GetResource(decrypted_samples);
689 
690     if (!object || object->pp_instance() != instance) {
691       NOTREACHED();
692       return;
693     }
694 
695     host_resource = object->host_resource().host_resource();
696   }
697 
698   std::string serialized_sample_info;
699   if (!SerializeBlockInfo(*sample_info, &serialized_sample_info)) {
700     NOTREACHED();
701     return;
702   }
703 
704   dispatcher()->Send(
705       new PpapiHostMsg_PPBInstance_DeliverSamples(API_ID_PPB_INSTANCE,
706                                                   instance,
707                                                   host_resource,
708                                                   serialized_sample_info));
709 }
710 #endif  // !defined(OS_NACL)
711 
PostMessage(PP_Instance instance,PP_Var message)712 void PPB_Instance_Proxy::PostMessage(PP_Instance instance,
713                                      PP_Var message) {
714   dispatcher()->Send(new PpapiHostMsg_PPBInstance_PostMessage(
715       API_ID_PPB_INSTANCE,
716       instance, SerializedVarSendInputShmem(dispatcher(), message,
717                                             instance)));
718 }
719 
SetCursor(PP_Instance instance,PP_MouseCursor_Type type,PP_Resource image,const PP_Point * hot_spot)720 PP_Bool PPB_Instance_Proxy::SetCursor(PP_Instance instance,
721                                       PP_MouseCursor_Type type,
722                                       PP_Resource image,
723                                       const PP_Point* hot_spot) {
724   // Some of these parameters are important for security. This check is in the
725   // plugin process just for the convenience of the caller (since we don't
726   // bother returning errors from the other process with a sync message). The
727   // parameters will be validated again in the renderer.
728   if (!ValidateSetCursorParams(type, image, hot_spot))
729     return PP_FALSE;
730 
731   HostResource image_host_resource;
732   if (image) {
733     Resource* cursor_image =
734         PpapiGlobals::Get()->GetResourceTracker()->GetResource(image);
735     if (!cursor_image || cursor_image->pp_instance() != instance)
736       return PP_FALSE;
737     image_host_resource = cursor_image->host_resource();
738   }
739 
740   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SetCursor(
741       API_ID_PPB_INSTANCE, instance, static_cast<int32_t>(type),
742       image_host_resource, hot_spot ? *hot_spot : PP_MakePoint(0, 0)));
743   return PP_TRUE;
744 }
745 
LockMouse(PP_Instance instance,scoped_refptr<TrackedCallback> callback)746 int32_t PPB_Instance_Proxy::LockMouse(PP_Instance instance,
747                                       scoped_refptr<TrackedCallback> callback) {
748   // Save the mouse callback on the instance data.
749   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
750       GetInstanceData(instance);
751   if (!data)
752     return PP_ERROR_BADARGUMENT;
753   if (TrackedCallback::IsPending(data->mouse_lock_callback))
754     return PP_ERROR_INPROGRESS;  // Already have a pending callback.
755   data->mouse_lock_callback = callback;
756 
757   dispatcher()->Send(new PpapiHostMsg_PPBInstance_LockMouse(
758       API_ID_PPB_INSTANCE, instance));
759   return PP_OK_COMPLETIONPENDING;
760 }
761 
UnlockMouse(PP_Instance instance)762 void PPB_Instance_Proxy::UnlockMouse(PP_Instance instance) {
763   dispatcher()->Send(new PpapiHostMsg_PPBInstance_UnlockMouse(
764       API_ID_PPB_INSTANCE, instance));
765 }
766 
SetTextInputType(PP_Instance instance,PP_TextInput_Type type)767 void PPB_Instance_Proxy::SetTextInputType(PP_Instance instance,
768                                           PP_TextInput_Type type) {
769   CancelAnyPendingRequestSurroundingText(instance);
770   dispatcher()->Send(new PpapiHostMsg_PPBInstance_SetTextInputType(
771       API_ID_PPB_INSTANCE, instance, type));
772 }
773 
UpdateCaretPosition(PP_Instance instance,const PP_Rect & caret,const PP_Rect & bounding_box)774 void PPB_Instance_Proxy::UpdateCaretPosition(PP_Instance instance,
775                                              const PP_Rect& caret,
776                                              const PP_Rect& bounding_box) {
777   dispatcher()->Send(new PpapiHostMsg_PPBInstance_UpdateCaretPosition(
778       API_ID_PPB_INSTANCE, instance, caret, bounding_box));
779 }
780 
CancelCompositionText(PP_Instance instance)781 void PPB_Instance_Proxy::CancelCompositionText(PP_Instance instance) {
782   CancelAnyPendingRequestSurroundingText(instance);
783   dispatcher()->Send(new PpapiHostMsg_PPBInstance_CancelCompositionText(
784       API_ID_PPB_INSTANCE, instance));
785 }
786 
SelectionChanged(PP_Instance instance)787 void PPB_Instance_Proxy::SelectionChanged(PP_Instance instance) {
788   // The "right" way to do this is to send the message to the host. However,
789   // all it will do is call RequestSurroundingText with a hardcoded number of
790   // characters in response, which is an entire IPC round-trip.
791   //
792   // We can avoid this round-trip by just implementing the
793   // RequestSurroundingText logic in the plugin process. If the logic in the
794   // host becomes more complex (like a more adaptive number of characters),
795   // we'll need to reevanuate whether we want to do the round trip instead.
796   //
797   // Be careful to post a task to avoid reentering the plugin.
798 
799   InstanceData* data =
800       static_cast<PluginDispatcher*>(dispatcher())->GetInstanceData(instance);
801   if (!data)
802     return;
803   data->should_do_request_surrounding_text = true;
804 
805   if (!data->is_request_surrounding_text_pending) {
806     base::MessageLoop::current()->PostTask(
807         FROM_HERE,
808         RunWhileLocked(base::Bind(&RequestSurroundingText, instance)));
809     data->is_request_surrounding_text_pending = true;
810   }
811 }
812 
UpdateSurroundingText(PP_Instance instance,const char * text,uint32_t caret,uint32_t anchor)813 void PPB_Instance_Proxy::UpdateSurroundingText(PP_Instance instance,
814                                                const char* text,
815                                                uint32_t caret,
816                                                uint32_t anchor) {
817   dispatcher()->Send(new PpapiHostMsg_PPBInstance_UpdateSurroundingText(
818       API_ID_PPB_INSTANCE, instance, text, caret, anchor));
819 }
820 
821 #if !defined(OS_NACL)
OnHostMsgGetWindowObject(PP_Instance instance,SerializedVarReturnValue result)822 void PPB_Instance_Proxy::OnHostMsgGetWindowObject(
823     PP_Instance instance,
824     SerializedVarReturnValue result) {
825   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
826     return;
827   EnterInstanceNoLock enter(instance);
828   if (enter.succeeded())
829     result.Return(dispatcher(), enter.functions()->GetWindowObject(instance));
830 }
831 
OnHostMsgGetOwnerElementObject(PP_Instance instance,SerializedVarReturnValue result)832 void PPB_Instance_Proxy::OnHostMsgGetOwnerElementObject(
833     PP_Instance instance,
834     SerializedVarReturnValue result) {
835   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
836     return;
837   EnterInstanceNoLock enter(instance);
838   if (enter.succeeded()) {
839     result.Return(dispatcher(),
840                   enter.functions()->GetOwnerElementObject(instance));
841   }
842 }
843 
OnHostMsgBindGraphics(PP_Instance instance,PP_Resource device)844 void PPB_Instance_Proxy::OnHostMsgBindGraphics(PP_Instance instance,
845                                                PP_Resource device) {
846   // Note that we ignroe the return value here. Otherwise, this would need to
847   // be a slow sync call, and the plugin side of the proxy will have already
848   // validated the resources, so we shouldn't see errors here that weren't
849   // already caught.
850   EnterInstanceNoLock enter(instance);
851   if (enter.succeeded())
852     enter.functions()->BindGraphics(instance, device);
853 }
854 
OnHostMsgGetAudioHardwareOutputSampleRate(PP_Instance instance,uint32_t * result)855 void PPB_Instance_Proxy::OnHostMsgGetAudioHardwareOutputSampleRate(
856     PP_Instance instance, uint32_t* result) {
857   EnterInstanceNoLock enter(instance);
858   if (enter.succeeded())
859     *result = enter.functions()->GetAudioHardwareOutputSampleRate(instance);
860 }
861 
OnHostMsgGetAudioHardwareOutputBufferSize(PP_Instance instance,uint32_t * result)862 void PPB_Instance_Proxy::OnHostMsgGetAudioHardwareOutputBufferSize(
863     PP_Instance instance, uint32_t* result) {
864   EnterInstanceNoLock enter(instance);
865   if (enter.succeeded())
866     *result = enter.functions()->GetAudioHardwareOutputBufferSize(instance);
867 }
868 
OnHostMsgIsFullFrame(PP_Instance instance,PP_Bool * result)869 void PPB_Instance_Proxy::OnHostMsgIsFullFrame(PP_Instance instance,
870                                               PP_Bool* result) {
871   EnterInstanceNoLock enter(instance);
872   if (enter.succeeded())
873     *result = enter.functions()->IsFullFrame(instance);
874 }
875 
OnHostMsgExecuteScript(PP_Instance instance,SerializedVarReceiveInput script,SerializedVarOutParam out_exception,SerializedVarReturnValue result)876 void PPB_Instance_Proxy::OnHostMsgExecuteScript(
877     PP_Instance instance,
878     SerializedVarReceiveInput script,
879     SerializedVarOutParam out_exception,
880     SerializedVarReturnValue result) {
881   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
882     return;
883   EnterInstanceNoLock enter(instance);
884   if (enter.failed())
885     return;
886 
887   if (dispatcher()->IsPlugin())
888     NOTREACHED();
889   else
890     static_cast<HostDispatcher*>(dispatcher())->set_allow_plugin_reentrancy();
891 
892   result.Return(dispatcher(), enter.functions()->ExecuteScript(
893       instance,
894       script.Get(dispatcher()),
895       out_exception.OutParam(dispatcher())));
896 }
897 
OnHostMsgGetDefaultCharSet(PP_Instance instance,SerializedVarReturnValue result)898 void PPB_Instance_Proxy::OnHostMsgGetDefaultCharSet(
899     PP_Instance instance,
900     SerializedVarReturnValue result) {
901   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
902     return;
903   EnterInstanceNoLock enter(instance);
904   if (enter.succeeded())
905     result.Return(dispatcher(), enter.functions()->GetDefaultCharSet(instance));
906 }
907 
OnHostMsgSetFullscreen(PP_Instance instance,PP_Bool fullscreen,PP_Bool * result)908 void PPB_Instance_Proxy::OnHostMsgSetFullscreen(PP_Instance instance,
909                                                 PP_Bool fullscreen,
910                                                 PP_Bool* result) {
911   EnterInstanceNoLock enter(instance);
912   if (enter.succeeded())
913     *result = enter.functions()->SetFullscreen(instance, fullscreen);
914 }
915 
916 
OnHostMsgGetScreenSize(PP_Instance instance,PP_Bool * result,PP_Size * size)917 void PPB_Instance_Proxy::OnHostMsgGetScreenSize(PP_Instance instance,
918                                                 PP_Bool* result,
919                                                 PP_Size* size) {
920   EnterInstanceNoLock enter(instance);
921   if (enter.succeeded())
922     *result = enter.functions()->GetScreenSize(instance, size);
923 }
924 
OnHostMsgRequestInputEvents(PP_Instance instance,bool is_filtering,uint32_t event_classes)925 void PPB_Instance_Proxy::OnHostMsgRequestInputEvents(PP_Instance instance,
926                                                      bool is_filtering,
927                                                      uint32_t event_classes) {
928   EnterInstanceNoLock enter(instance);
929   if (enter.succeeded()) {
930     if (is_filtering)
931       enter.functions()->RequestFilteringInputEvents(instance, event_classes);
932     else
933       enter.functions()->RequestInputEvents(instance, event_classes);
934   }
935 }
936 
OnHostMsgClearInputEvents(PP_Instance instance,uint32_t event_classes)937 void PPB_Instance_Proxy::OnHostMsgClearInputEvents(PP_Instance instance,
938                                                    uint32_t event_classes) {
939   EnterInstanceNoLock enter(instance);
940   if (enter.succeeded())
941     enter.functions()->ClearInputEventRequest(instance, event_classes);
942 }
943 
OnHostMsgPostMessage(PP_Instance instance,SerializedVarReceiveInput message)944 void PPB_Instance_Proxy::OnHostMsgPostMessage(
945     PP_Instance instance,
946     SerializedVarReceiveInput message) {
947   EnterInstanceNoLock enter(instance);
948   if (!message.is_valid_var()) {
949     PpapiGlobals::Get()->LogWithSource(
950         instance, PP_LOGLEVEL_ERROR, std::string(), kSerializationError);
951     return;
952   }
953 
954   if (enter.succeeded())
955     enter.functions()->PostMessage(instance,
956                                    message.GetForInstance(dispatcher(),
957                                                           instance));
958 }
959 
OnHostMsgLockMouse(PP_Instance instance)960 void PPB_Instance_Proxy::OnHostMsgLockMouse(PP_Instance instance) {
961   // Need to be careful to always issue the callback.
962   pp::CompletionCallback cb = callback_factory_.NewCallback(
963       &PPB_Instance_Proxy::MouseLockCompleteInHost, instance);
964 
965   EnterInstanceNoLock enter(instance, cb.pp_completion_callback());
966   if (enter.succeeded())
967     enter.SetResult(enter.functions()->LockMouse(instance, enter.callback()));
968 }
969 
OnHostMsgUnlockMouse(PP_Instance instance)970 void PPB_Instance_Proxy::OnHostMsgUnlockMouse(PP_Instance instance) {
971   EnterInstanceNoLock enter(instance);
972   if (enter.succeeded())
973     enter.functions()->UnlockMouse(instance);
974 }
975 
OnHostMsgGetDocumentURL(PP_Instance instance,PP_URLComponents_Dev * components,SerializedVarReturnValue result)976 void PPB_Instance_Proxy::OnHostMsgGetDocumentURL(
977     PP_Instance instance,
978     PP_URLComponents_Dev* components,
979     SerializedVarReturnValue result) {
980   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
981     return;
982   EnterInstanceNoLock enter(instance);
983   if (enter.succeeded()) {
984     PP_Var document_url = enter.functions()->GetDocumentURL(instance,
985                                                             components);
986     result.Return(dispatcher(), document_url);
987   }
988 }
989 
OnHostMsgResolveRelativeToDocument(PP_Instance instance,SerializedVarReceiveInput relative,SerializedVarReturnValue result)990 void PPB_Instance_Proxy::OnHostMsgResolveRelativeToDocument(
991     PP_Instance instance,
992     SerializedVarReceiveInput relative,
993     SerializedVarReturnValue result) {
994   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
995     return;
996   EnterInstanceNoLock enter(instance);
997   if (enter.succeeded()) {
998     result.Return(dispatcher(),
999                   enter.functions()->ResolveRelativeToDocument(
1000                       instance, relative.Get(dispatcher()), NULL));
1001   }
1002 }
1003 
OnHostMsgDocumentCanRequest(PP_Instance instance,SerializedVarReceiveInput url,PP_Bool * result)1004 void PPB_Instance_Proxy::OnHostMsgDocumentCanRequest(
1005     PP_Instance instance,
1006     SerializedVarReceiveInput url,
1007     PP_Bool* result) {
1008   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1009     return;
1010   EnterInstanceNoLock enter(instance);
1011   if (enter.succeeded()) {
1012     *result = enter.functions()->DocumentCanRequest(instance,
1013                                                     url.Get(dispatcher()));
1014   }
1015 }
1016 
OnHostMsgDocumentCanAccessDocument(PP_Instance active,PP_Instance target,PP_Bool * result)1017 void PPB_Instance_Proxy::OnHostMsgDocumentCanAccessDocument(PP_Instance active,
1018                                                             PP_Instance target,
1019                                                             PP_Bool* result) {
1020   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1021     return;
1022   EnterInstanceNoLock enter(active);
1023   if (enter.succeeded())
1024     *result = enter.functions()->DocumentCanAccessDocument(active, target);
1025 }
1026 
OnHostMsgGetPluginInstanceURL(PP_Instance instance,SerializedVarReturnValue result)1027 void PPB_Instance_Proxy::OnHostMsgGetPluginInstanceURL(
1028     PP_Instance instance,
1029     SerializedVarReturnValue result) {
1030   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1031     return;
1032   EnterInstanceNoLock enter(instance);
1033   if (enter.succeeded()) {
1034     result.Return(dispatcher(),
1035                   enter.functions()->GetPluginInstanceURL(instance, NULL));
1036   }
1037 }
1038 
OnHostMsgGetPluginReferrerURL(PP_Instance instance,SerializedVarReturnValue result)1039 void PPB_Instance_Proxy::OnHostMsgGetPluginReferrerURL(
1040     PP_Instance instance,
1041     SerializedVarReturnValue result) {
1042   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1043     return;
1044   EnterInstanceNoLock enter(instance);
1045   if (enter.succeeded()) {
1046     result.Return(dispatcher(),
1047                   enter.functions()->GetPluginReferrerURL(instance, NULL));
1048   }
1049 }
1050 
OnHostMsgSessionCreated(PP_Instance instance,uint32_t session_id,SerializedVarReceiveInput web_session_id)1051 void PPB_Instance_Proxy::OnHostMsgSessionCreated(
1052     PP_Instance instance,
1053     uint32_t session_id,
1054     SerializedVarReceiveInput web_session_id) {
1055   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1056     return;
1057   EnterInstanceNoLock enter(instance);
1058   if (enter.succeeded()) {
1059     enter.functions()->SessionCreated(
1060         instance, session_id, web_session_id.Get(dispatcher()));
1061   }
1062 }
1063 
OnHostMsgSessionMessage(PP_Instance instance,uint32_t session_id,SerializedVarReceiveInput message,SerializedVarReceiveInput destination_url)1064 void PPB_Instance_Proxy::OnHostMsgSessionMessage(
1065     PP_Instance instance,
1066     uint32_t session_id,
1067     SerializedVarReceiveInput message,
1068     SerializedVarReceiveInput destination_url) {
1069   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1070     return;
1071   EnterInstanceNoLock enter(instance);
1072   if (enter.succeeded()) {
1073     enter.functions()->SessionMessage(instance,
1074                                       session_id,
1075                                       message.Get(dispatcher()),
1076                                       destination_url.Get(dispatcher()));
1077   }
1078 }
1079 
OnHostMsgSessionReady(PP_Instance instance,uint32_t session_id)1080 void PPB_Instance_Proxy::OnHostMsgSessionReady(PP_Instance instance,
1081                                                uint32_t session_id) {
1082   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1083     return;
1084   EnterInstanceNoLock enter(instance);
1085   if (enter.succeeded()) {
1086     enter.functions()->SessionReady(instance, session_id);
1087   }
1088 }
1089 
OnHostMsgSessionClosed(PP_Instance instance,uint32_t session_id)1090 void PPB_Instance_Proxy::OnHostMsgSessionClosed(PP_Instance instance,
1091                                                 uint32_t session_id) {
1092   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1093     return;
1094   EnterInstanceNoLock enter(instance);
1095   if (enter.succeeded()) {
1096     enter.functions()->SessionClosed(instance, session_id);
1097   }
1098 }
1099 
OnHostMsgSessionError(PP_Instance instance,uint32_t session_id,int32_t media_error,int32_t system_error)1100 void PPB_Instance_Proxy::OnHostMsgSessionError(PP_Instance instance,
1101                                                uint32_t session_id,
1102                                                int32_t media_error,
1103                                                int32_t system_error) {
1104   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1105     return;
1106   EnterInstanceNoLock enter(instance);
1107   if (enter.succeeded()) {
1108     enter.functions()->SessionError(
1109         instance, session_id, media_error, system_error);
1110   }
1111 }
1112 
OnHostMsgDeliverBlock(PP_Instance instance,PP_Resource decrypted_block,const std::string & serialized_block_info)1113 void PPB_Instance_Proxy::OnHostMsgDeliverBlock(
1114     PP_Instance instance,
1115     PP_Resource decrypted_block,
1116     const std::string& serialized_block_info) {
1117   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1118     return;
1119   PP_DecryptedBlockInfo block_info;
1120   if (!DeserializeBlockInfo(serialized_block_info, &block_info))
1121     return;
1122 
1123   EnterInstanceNoLock enter(instance);
1124   if (enter.succeeded())
1125     enter.functions()->DeliverBlock(instance, decrypted_block, &block_info);
1126 }
1127 
OnHostMsgDecoderInitializeDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id,PP_Bool success)1128 void PPB_Instance_Proxy::OnHostMsgDecoderInitializeDone(
1129     PP_Instance instance,
1130     PP_DecryptorStreamType decoder_type,
1131     uint32_t request_id,
1132     PP_Bool success) {
1133   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1134     return;
1135   EnterInstanceNoLock enter(instance);
1136   if (enter.succeeded()) {
1137     enter.functions()->DecoderInitializeDone(instance,
1138                                              decoder_type,
1139                                              request_id,
1140                                              success);
1141   }
1142 }
1143 
OnHostMsgDecoderDeinitializeDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id)1144 void PPB_Instance_Proxy::OnHostMsgDecoderDeinitializeDone(
1145     PP_Instance instance,
1146     PP_DecryptorStreamType decoder_type,
1147     uint32_t request_id) {
1148   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1149     return;
1150   EnterInstanceNoLock enter(instance);
1151   if (enter.succeeded())
1152     enter.functions()->DecoderDeinitializeDone(instance,
1153                                                decoder_type,
1154                                                request_id);
1155 }
1156 
OnHostMsgDecoderResetDone(PP_Instance instance,PP_DecryptorStreamType decoder_type,uint32_t request_id)1157 void PPB_Instance_Proxy::OnHostMsgDecoderResetDone(
1158     PP_Instance instance,
1159     PP_DecryptorStreamType decoder_type,
1160     uint32_t request_id) {
1161   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1162     return;
1163   EnterInstanceNoLock enter(instance);
1164   if (enter.succeeded())
1165     enter.functions()->DecoderResetDone(instance, decoder_type, request_id);
1166 }
1167 
OnHostMsgDeliverFrame(PP_Instance instance,PP_Resource decrypted_frame,const std::string & serialized_frame_info)1168 void PPB_Instance_Proxy::OnHostMsgDeliverFrame(
1169     PP_Instance instance,
1170     PP_Resource decrypted_frame,
1171     const std::string& serialized_frame_info) {
1172   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1173     return;
1174   PP_DecryptedFrameInfo frame_info;
1175   if (!DeserializeBlockInfo(serialized_frame_info, &frame_info))
1176     return;
1177 
1178   EnterInstanceNoLock enter(instance);
1179   if (enter.succeeded())
1180     enter.functions()->DeliverFrame(instance, decrypted_frame, &frame_info);
1181 }
1182 
OnHostMsgDeliverSamples(PP_Instance instance,PP_Resource audio_frames,const std::string & serialized_sample_info)1183 void PPB_Instance_Proxy::OnHostMsgDeliverSamples(
1184     PP_Instance instance,
1185     PP_Resource audio_frames,
1186     const std::string& serialized_sample_info) {
1187   if (!dispatcher()->permissions().HasPermission(PERMISSION_PRIVATE))
1188     return;
1189   PP_DecryptedSampleInfo sample_info;
1190   if (!DeserializeBlockInfo(serialized_sample_info, &sample_info))
1191     return;
1192 
1193   EnterInstanceNoLock enter(instance);
1194   if (enter.succeeded())
1195     enter.functions()->DeliverSamples(instance, audio_frames, &sample_info);
1196 }
1197 
OnHostMsgSetCursor(PP_Instance instance,int32_t type,const ppapi::HostResource & custom_image,const PP_Point & hot_spot)1198 void PPB_Instance_Proxy::OnHostMsgSetCursor(
1199     PP_Instance instance,
1200     int32_t type,
1201     const ppapi::HostResource& custom_image,
1202     const PP_Point& hot_spot) {
1203   // This API serves PPB_CursorControl_Dev and PPB_MouseCursor, so is public.
1204   EnterInstanceNoLock enter(instance);
1205   if (enter.succeeded()) {
1206     enter.functions()->SetCursor(
1207         instance, static_cast<PP_MouseCursor_Type>(type),
1208         custom_image.host_resource(), &hot_spot);
1209   }
1210 }
1211 
OnHostMsgSetTextInputType(PP_Instance instance,PP_TextInput_Type type)1212 void PPB_Instance_Proxy::OnHostMsgSetTextInputType(PP_Instance instance,
1213                                                    PP_TextInput_Type type) {
1214   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1215     return;
1216   EnterInstanceNoLock enter(instance);
1217   if (enter.succeeded())
1218     enter.functions()->SetTextInputType(instance, type);
1219 }
1220 
OnHostMsgUpdateCaretPosition(PP_Instance instance,const PP_Rect & caret,const PP_Rect & bounding_box)1221 void PPB_Instance_Proxy::OnHostMsgUpdateCaretPosition(
1222     PP_Instance instance,
1223     const PP_Rect& caret,
1224     const PP_Rect& bounding_box) {
1225   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1226     return;
1227   EnterInstanceNoLock enter(instance);
1228   if (enter.succeeded())
1229     enter.functions()->UpdateCaretPosition(instance, caret, bounding_box);
1230 }
1231 
OnHostMsgCancelCompositionText(PP_Instance instance)1232 void PPB_Instance_Proxy::OnHostMsgCancelCompositionText(PP_Instance instance) {
1233   EnterInstanceNoLock enter(instance);
1234   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1235     return;
1236   if (enter.succeeded())
1237     enter.functions()->CancelCompositionText(instance);
1238 }
1239 
OnHostMsgUpdateSurroundingText(PP_Instance instance,const std::string & text,uint32_t caret,uint32_t anchor)1240 void PPB_Instance_Proxy::OnHostMsgUpdateSurroundingText(
1241     PP_Instance instance,
1242     const std::string& text,
1243     uint32_t caret,
1244     uint32_t anchor) {
1245   if (!dispatcher()->permissions().HasPermission(PERMISSION_DEV))
1246     return;
1247   EnterInstanceNoLock enter(instance);
1248   if (enter.succeeded()) {
1249     enter.functions()->UpdateSurroundingText(instance, text.c_str(), caret,
1250                                              anchor);
1251   }
1252 }
1253 #endif  // !defined(OS_NACL)
1254 
OnPluginMsgMouseLockComplete(PP_Instance instance,int32_t result)1255 void PPB_Instance_Proxy::OnPluginMsgMouseLockComplete(PP_Instance instance,
1256                                                       int32_t result) {
1257   if (!dispatcher()->IsPlugin())
1258     return;
1259 
1260   // Save the mouse callback on the instance data.
1261   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
1262       GetInstanceData(instance);
1263   if (!data)
1264     return;  // Instance was probably deleted.
1265   if (!TrackedCallback::IsPending(data->mouse_lock_callback)) {
1266     NOTREACHED();
1267     return;
1268   }
1269   data->mouse_lock_callback->Run(result);
1270 }
1271 
1272 #if !defined(OS_NACL)
MouseLockCompleteInHost(int32_t result,PP_Instance instance)1273 void PPB_Instance_Proxy::MouseLockCompleteInHost(int32_t result,
1274                                                  PP_Instance instance) {
1275   dispatcher()->Send(new PpapiMsg_PPBInstance_MouseLockComplete(
1276       API_ID_PPB_INSTANCE, instance, result));
1277 }
1278 #endif  // !defined(OS_NACL)
1279 
CancelAnyPendingRequestSurroundingText(PP_Instance instance)1280 void PPB_Instance_Proxy::CancelAnyPendingRequestSurroundingText(
1281     PP_Instance instance) {
1282   InstanceData* data = static_cast<PluginDispatcher*>(dispatcher())->
1283       GetInstanceData(instance);
1284   if (!data)
1285     return;  // Instance was probably deleted.
1286   data->should_do_request_surrounding_text = false;
1287 }
1288 
1289 }  // namespace proxy
1290 }  // namespace ppapi
1291