OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/common/npobject_proxy.h" | 5 #include "content/common/npobject_proxy.h" |
6 | 6 |
7 #include "content/common/np_channel_base.h" | 7 #include "content/common/np_channel_base.h" |
8 #include "content/common/npobject_util.h" | 8 #include "content/common/npobject_util.h" |
9 #include "content/common/plugin_messages.h" | 9 #include "content/common/plugin_messages.h" |
10 #include "third_party/WebKit/Source/WebKit/chromium/public/WebBindings.h" | 10 #include "third_party/WebKit/Source/WebKit/chromium/public/WebBindings.h" |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
55 } | 55 } |
56 | 56 |
57 NPObjectProxy::NPObjectProxy( | 57 NPObjectProxy::NPObjectProxy( |
58 NPChannelBase* channel, | 58 NPChannelBase* channel, |
59 int route_id, | 59 int route_id, |
60 gfx::NativeViewId containing_window, | 60 gfx::NativeViewId containing_window, |
61 const GURL& page_url) | 61 const GURL& page_url) |
62 : channel_(channel), | 62 : channel_(channel), |
63 route_id_(route_id), | 63 route_id_(route_id), |
64 containing_window_(containing_window), | 64 containing_window_(containing_window), |
65 page_url_(page_url) { | 65 page_url_(page_url), |
| 66 has_exception_thrown_(false) { |
66 channel_->AddRoute(route_id, this, this); | 67 channel_->AddRoute(route_id, this, this); |
67 } | 68 } |
68 | 69 |
69 NPObjectProxy::~NPObjectProxy() { | 70 NPObjectProxy::~NPObjectProxy() { |
70 if (channel_.get()) { | 71 if (channel_.get()) { |
71 // This NPObjectProxy instance is now invalid and should not be reused for | 72 // This NPObjectProxy instance is now invalid and should not be reused for |
72 // requests initiated by plugins. We may receive requests for the | 73 // requests initiated by plugins. We may receive requests for the |
73 // same NPObject in the context of the outgoing NPObjectMsg_Release call. | 74 // same NPObject in the context of the outgoing NPObjectMsg_Release call. |
74 // We should be creating new NPObjectProxy instances to wrap these | 75 // We should be creating new NPObjectProxy instances to wrap these |
75 // NPObjects. | 76 // NPObjects. |
(...skipping 27 matching lines...) Expand all Loading... |
103 return reinterpret_cast<NPObject*>(new NPObjectWrapper); | 104 return reinterpret_cast<NPObject*>(new NPObjectWrapper); |
104 } | 105 } |
105 | 106 |
106 void NPObjectProxy::NPDeallocate(NPObject* npObj) { | 107 void NPObjectProxy::NPDeallocate(NPObject* npObj) { |
107 NPObjectWrapper* obj = reinterpret_cast<NPObjectWrapper*>(npObj); | 108 NPObjectWrapper* obj = reinterpret_cast<NPObjectWrapper*>(npObj); |
108 delete obj->proxy; | 109 delete obj->proxy; |
109 delete obj; | 110 delete obj; |
110 } | 111 } |
111 | 112 |
112 bool NPObjectProxy::OnMessageReceived(const IPC::Message& msg) { | 113 bool NPObjectProxy::OnMessageReceived(const IPC::Message& msg) { |
113 NOTREACHED(); | 114 bool handled = true; |
114 return false; | 115 |
| 116 IPC_BEGIN_MESSAGE_MAP(NPObjectProxy, msg) |
| 117 IPC_MESSAGE_HANDLER(NPObjectMsg_SetException, OnSetException) |
| 118 IPC_MESSAGE_UNHANDLED(handled = false) |
| 119 IPC_END_MESSAGE_MAP() |
| 120 |
| 121 DCHECK(handled); |
| 122 return true; |
115 } | 123 } |
116 | 124 |
117 void NPObjectProxy::OnChannelError() { | 125 void NPObjectProxy::OnChannelError() { |
118 // Release our ref count of the plugin channel object, as it addrefs the | 126 // Release our ref count of the plugin channel object, as it addrefs the |
119 // process. | 127 // process. |
120 channel_ = NULL; | 128 channel_ = NULL; |
121 } | 129 } |
122 | 130 |
| 131 void NPObjectProxy::OnSetException(const std::string& msg) { |
| 132 if (IsPluginProcess()) { |
| 133 NOTREACHED() << "Should be only called from renderer process!"; |
| 134 return; |
| 135 } |
| 136 |
| 137 has_exception_thrown_ = true; |
| 138 |
| 139 NPObject* obj = NULL; |
| 140 |
| 141 if (channel()) { |
| 142 obj = channel()->GetExistingNPObjectProxy(route_id_); |
| 143 } |
| 144 |
| 145 WebKit::WebBindings::setException(obj, msg.c_str()); |
| 146 } |
| 147 |
123 bool NPObjectProxy::NPHasMethod(NPObject *obj, | 148 bool NPObjectProxy::NPHasMethod(NPObject *obj, |
124 NPIdentifier name) { | 149 NPIdentifier name) { |
125 if (obj == NULL) | 150 if (obj == NULL) |
126 return false; | 151 return false; |
127 | 152 |
128 bool result = false; | 153 bool result = false; |
129 NPObjectProxy* proxy = GetProxy(obj); | 154 NPObjectProxy* proxy = GetProxy(obj); |
130 | 155 |
131 if (!proxy) { | 156 if (!proxy) { |
132 return obj->_class->hasMethod(obj, name); | 157 return obj->_class->hasMethod(obj, name); |
133 } | 158 } |
134 | 159 |
135 NPIdentifier_Param name_param; | 160 NPIdentifier_Param name_param; |
136 CreateNPIdentifierParam(name, &name_param); | 161 CreateNPIdentifierParam(name, &name_param); |
137 | 162 |
138 proxy->Send(new NPObjectMsg_HasMethod(proxy->route_id(), name_param, | 163 proxy->Send(new NPObjectMsg_HasMethod(proxy->route_id(), name_param, |
139 &result)); | 164 &result)); |
| 165 |
140 return result; | 166 return result; |
141 } | 167 } |
142 | 168 |
143 bool NPObjectProxy::NPInvoke(NPObject *obj, | 169 bool NPObjectProxy::NPInvoke(NPObject *obj, |
144 NPIdentifier name, | 170 NPIdentifier name, |
145 const NPVariant *args, | 171 const NPVariant *args, |
146 uint32_t arg_count, | 172 uint32_t arg_count, |
147 NPVariant *result) { | 173 NPVariant *result) { |
148 return NPInvokePrivate(0, obj, false, name, args, arg_count, result); | 174 return NPInvokePrivate(0, obj, false, name, args, arg_count, result); |
149 } | 175 } |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
208 // happens when everything runs in-process (while calling MessageBox window | 234 // happens when everything runs in-process (while calling MessageBox window |
209 // messages are pumped). | 235 // messages are pumped). |
210 if (IsPluginProcess() && proxy->channel()) { | 236 if (IsPluginProcess() && proxy->channel()) { |
211 msg->set_pump_messages_event( | 237 msg->set_pump_messages_event( |
212 proxy->channel()->GetModalDialogEvent(containing_window)); | 238 proxy->channel()->GetModalDialogEvent(containing_window)); |
213 } | 239 } |
214 | 240 |
215 GURL page_url = proxy->page_url_; | 241 GURL page_url = proxy->page_url_; |
216 proxy->Send(msg); | 242 proxy->Send(msg); |
217 | 243 |
| 244 // In case of returning result is false and the NPObjectProxy instance |
| 245 // has exception thrown, it means that NPN_SetException is called from |
| 246 // NPAPI plugin during the process of invoking native method. |
| 247 if (!result && proxy->HasExceptionThrown()) { |
| 248 // Tell v8 engine that an exception has been already thrown via np_result |
| 249 BOOLEAN_TO_NPVARIANT(true, *np_result); |
| 250 proxy->SetExceptionThrown(false); |
| 251 } |
218 // Send may delete proxy. | 252 // Send may delete proxy. |
219 proxy = NULL; | 253 proxy = NULL; |
220 | 254 |
221 if (!result) | 255 if (!result) |
222 return false; | 256 return false; |
223 | 257 |
224 CreateNPVariant( | 258 CreateNPVariant( |
225 param_result, channel_copy, np_result, containing_window, page_url); | 259 param_result, channel_copy, np_result, containing_window, page_url); |
226 return true; | 260 return true; |
227 } | 261 } |
(...skipping 200 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
428 | 462 |
429 // See comment in NPObjectProxy::NPInvokePrivate. | 463 // See comment in NPObjectProxy::NPInvokePrivate. |
430 if (IsPluginProcess() && proxy->channel()) { | 464 if (IsPluginProcess() && proxy->channel()) { |
431 msg->set_pump_messages_event( | 465 msg->set_pump_messages_event( |
432 proxy->channel()->GetModalDialogEvent(proxy->containing_window_)); | 466 proxy->channel()->GetModalDialogEvent(proxy->containing_window_)); |
433 } | 467 } |
434 | 468 |
435 GURL page_url = proxy->page_url_; | 469 GURL page_url = proxy->page_url_; |
436 proxy->Send(msg); | 470 proxy->Send(msg); |
437 | 471 |
| 472 // An exception has been occurred during the process of handling |
| 473 // NPObjectMsg_Construct on the peer side |
| 474 if (!result && proxy->HasExceptionThrown()) { |
| 475 BOOLEAN_TO_NPVARIANT(true, *np_result); |
| 476 proxy->SetExceptionThrown(false); |
| 477 } |
| 478 |
438 // Send may delete proxy. | 479 // Send may delete proxy. |
439 proxy = NULL; | 480 proxy = NULL; |
440 | 481 |
441 if (!result) | 482 if (!result) |
442 return false; | 483 return false; |
443 | 484 |
444 CreateNPVariant( | 485 CreateNPVariant( |
445 param_result, channel_copy, np_result, containing_window, page_url); | 486 param_result, channel_copy, np_result, containing_window, page_url); |
446 return true; | 487 return true; |
447 } | 488 } |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
487 proxy->Send(msg); | 528 proxy->Send(msg); |
488 // Send may delete proxy. | 529 // Send may delete proxy. |
489 proxy = NULL; | 530 proxy = NULL; |
490 if (!result) | 531 if (!result) |
491 return false; | 532 return false; |
492 | 533 |
493 CreateNPVariant( | 534 CreateNPVariant( |
494 result_param, channel.get(), result_var, containing_window, page_url); | 535 result_param, channel.get(), result_var, containing_window, page_url); |
495 return true; | 536 return true; |
496 } | 537 } |
OLD | NEW |