1 // Copyright (c) 2013 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 "chrome/renderer/pepper/pepper_extensions_common_host.h" 6 7 #include "base/logging.h" 8 #include "base/memory/scoped_ptr.h" 9 #include "base/values.h" 10 #include "chrome/renderer/extensions/chrome_v8_context.h" 11 #include "chrome/renderer/extensions/dispatcher.h" 12 #include "chrome/renderer/extensions/extension_helper.h" 13 #include "content/public/renderer/render_view.h" 14 #include "content/public/renderer/renderer_ppapi_host.h" 15 #include "ppapi/c/pp_errors.h" 16 #include "ppapi/host/dispatch_host_message.h" 17 #include "ppapi/host/host_message_context.h" 18 #include "ppapi/host/ppapi_host.h" 19 #include "ppapi/proxy/ppapi_messages.h" 20 #include "third_party/WebKit/public/web/WebDocument.h" 21 #include "third_party/WebKit/public/web/WebElement.h" 22 #include "third_party/WebKit/public/web/WebFrame.h" 23 #include "third_party/WebKit/public/web/WebPluginContainer.h" 24 25 namespace { 26 void DoNothing(bool success, 27 const base::ListValue& response, 28 const std::string& error) {} 29 } 30 31 PepperExtensionsCommonHost::PepperExtensionsCommonHost( 32 content::RendererPpapiHost* host, 33 PP_Instance instance, 34 PP_Resource resource, 35 extensions::PepperRequestProxy* pepper_request_proxy) 36 : ResourceHost(host->GetPpapiHost(), instance, resource), 37 renderer_ppapi_host_(host), 38 pepper_request_proxy_(pepper_request_proxy), 39 weak_factory_(this) {} 40 41 PepperExtensionsCommonHost::~PepperExtensionsCommonHost() {} 42 43 // static 44 PepperExtensionsCommonHost* PepperExtensionsCommonHost::Create( 45 content::RendererPpapiHost* host, 46 PP_Instance instance, 47 PP_Resource resource) { 48 content::RenderView* render_view = host->GetRenderViewForInstance(instance); 49 if (!render_view) 50 return NULL; 51 extensions::ExtensionHelper* extension_helper = 52 extensions::ExtensionHelper::Get(render_view); 53 if (!extension_helper) 54 return NULL; 55 extensions::Dispatcher* dispatcher = extension_helper->dispatcher(); 56 if (!dispatcher) 57 return NULL; 58 blink::WebPluginContainer* container = 59 host->GetContainerForInstance(instance); 60 if (!container) 61 return NULL; 62 blink::WebFrame* frame = container->element().document().frame(); 63 if (!frame) 64 return NULL; 65 v8::HandleScope scope(v8::Isolate::GetCurrent()); 66 extensions::ChromeV8Context* context = 67 dispatcher->v8_context_set().GetByV8Context( 68 frame->mainWorldScriptContext()); 69 if (!context) 70 return NULL; 71 72 return new PepperExtensionsCommonHost( 73 host, instance, resource, context->pepper_request_proxy()); 74 } 75 76 int32_t PepperExtensionsCommonHost::OnResourceMessageReceived( 77 const IPC::Message& msg, 78 ppapi::host::HostMessageContext* context) { 79 IPC_BEGIN_MESSAGE_MAP(PepperExtensionsCommonHost, msg) 80 PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_ExtensionsCommon_Post, 81 OnPost) 82 PPAPI_DISPATCH_HOST_RESOURCE_CALL(PpapiHostMsg_ExtensionsCommon_Call, 83 OnCall) 84 IPC_END_MESSAGE_MAP() 85 return PP_ERROR_FAILED; 86 } 87 88 void PepperExtensionsCommonHost::OnResponseReceived( 89 scoped_ptr<ppapi::host::ReplyMessageContext> context, 90 bool success, 91 const base::ListValue& response, 92 const std::string& /* error */) { 93 context->params.set_result(success ? PP_OK : PP_ERROR_FAILED); 94 SendReply(*context, PpapiPluginMsg_ExtensionsCommon_CallReply(response)); 95 } 96 97 int32_t PepperExtensionsCommonHost::OnPost( 98 ppapi::host::HostMessageContext* context, 99 const std::string& request_name, 100 const base::ListValue& args) { 101 std::string error; 102 bool success = pepper_request_proxy_->StartRequest( 103 base::Bind(&DoNothing), request_name, args, &error); 104 return success ? PP_OK : PP_ERROR_FAILED; 105 } 106 107 int32_t PepperExtensionsCommonHost::OnCall( 108 ppapi::host::HostMessageContext* context, 109 const std::string& request_name, 110 const base::ListValue& args) { 111 std::string error; 112 scoped_ptr<ppapi::host::ReplyMessageContext> message_context( 113 new ppapi::host::ReplyMessageContext(context->MakeReplyMessageContext())); 114 bool success = pepper_request_proxy_->StartRequest( 115 base::Bind(&PepperExtensionsCommonHost::OnResponseReceived, 116 weak_factory_.GetWeakPtr(), 117 base::Passed(&message_context)), 118 request_name, 119 args, 120 &error); 121 return success ? PP_OK_COMPLETIONPENDING : PP_ERROR_FAILED; 122 } 123