| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 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/child/npapi/plugin_instance.h" | 5 #include "content/child/npapi/plugin_instance.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/command_line.h" | 8 #include "base/command_line.h" |
| 9 #include "base/files/file_util.h" | 9 #include "base/files/file_util.h" |
| 10 #include "base/location.h" | 10 #include "base/location.h" |
| 11 #include "base/single_thread_task_runner.h" | 11 #include "base/single_thread_task_runner.h" |
| 12 #include "base/strings/string_number_conversions.h" | 12 #include "base/strings/string_number_conversions.h" |
| 13 #include "base/strings/utf_string_conversions.h" | 13 #include "base/strings/utf_string_conversions.h" |
| 14 #include "base/thread_task_runner_handle.h" | 14 #include "base/thread_task_runner_handle.h" |
| 15 #include "build/build_config.h" | 15 #include "build/build_config.h" |
| 16 #include "content/child/npapi/plugin_host.h" | 16 #include "content/child/npapi/plugin_host.h" |
| 17 #include "content/child/npapi/plugin_lib.h" | 17 #include "content/child/npapi/plugin_lib.h" |
| 18 #include "content/child/npapi/plugin_stream_url.h" | |
| 19 #include "content/child/npapi/plugin_string_stream.h" | |
| 20 #include "content/child/npapi/webplugin.h" | 18 #include "content/child/npapi/webplugin.h" |
| 21 #include "content/child/npapi/webplugin_delegate.h" | 19 #include "content/child/npapi/webplugin_delegate.h" |
| 22 #include "content/child/npapi/webplugin_resource_client.h" | 20 #include "content/child/npapi/webplugin_resource_client.h" |
| 23 #include "content/public/common/content_constants.h" | 21 #include "content/public/common/content_constants.h" |
| 24 #include "content/public/common/content_switches.h" | 22 #include "content/public/common/content_switches.h" |
| 25 #include "net/base/escape.h" | 23 #include "net/base/escape.h" |
| 26 | 24 |
| 27 #if defined(OS_MACOSX) | 25 #if defined(OS_MACOSX) |
| 28 #include <ApplicationServices/ApplicationServices.h> | 26 #include <ApplicationServices/ApplicationServices.h> |
| 29 #endif | 27 #endif |
| 30 | 28 |
| 31 namespace content { | 29 namespace content { |
| 32 | 30 |
| 33 PluginInstance::PluginInstance(PluginLib* plugin, const std::string& mime_type) | 31 PluginInstance::PluginInstance(PluginLib* plugin, const std::string& mime_type) |
| 34 : plugin_(plugin), | 32 : plugin_(plugin), |
| 35 npp_(0), | 33 npp_(0), |
| 36 host_(PluginHost::Singleton()), | 34 host_(PluginHost::Singleton()), |
| 37 npp_functions_(plugin->functions()), | 35 npp_functions_(plugin->functions()), |
| 38 window_handle_(0), | 36 window_handle_(0), |
| 39 windowless_(false), | 37 windowless_(false), |
| 40 transparent_(true), | 38 transparent_(true), |
| 41 webplugin_(0), | 39 webplugin_(0), |
| 42 mime_type_(mime_type), | 40 mime_type_(mime_type), |
| 43 get_notify_data_(0), | |
| 44 use_mozilla_user_agent_(false), | 41 use_mozilla_user_agent_(false), |
| 45 #if defined (OS_MACOSX) | 42 #if defined (OS_MACOSX) |
| 46 #ifdef NP_NO_QUICKDRAW | 43 #ifdef NP_NO_QUICKDRAW |
| 47 drawing_model_(NPDrawingModelCoreGraphics), | 44 drawing_model_(NPDrawingModelCoreGraphics), |
| 48 #else | 45 #else |
| 49 drawing_model_(NPDrawingModelQuickDraw), | 46 drawing_model_(NPDrawingModelQuickDraw), |
| 50 #endif | 47 #endif |
| 51 #ifdef NP_NO_CARBON | 48 #ifdef NP_NO_CARBON |
| 52 event_model_(NPEventModelCocoa), | 49 event_model_(NPEventModelCocoa), |
| 53 #else | 50 #else |
| 54 event_model_(NPEventModelCarbon), | 51 event_model_(NPEventModelCarbon), |
| 55 #endif | 52 #endif |
| 56 currently_handled_event_(NULL), | 53 currently_handled_event_(NULL), |
| 57 #endif | 54 #endif |
| 58 task_runner_(base::ThreadTaskRunnerHandle::Get()), | 55 task_runner_(base::ThreadTaskRunnerHandle::Get()), |
| 59 load_manually_(false), | 56 load_manually_(false), |
| 60 in_close_streams_(false), | 57 next_timer_id_(1) { |
| 61 next_timer_id_(1), | |
| 62 next_notify_id_(0), | |
| 63 next_range_request_id_(0), | |
| 64 handles_url_redirects_(false) { | |
| 65 npp_ = new NPP_t(); | 58 npp_ = new NPP_t(); |
| 66 npp_->ndata = 0; | 59 npp_->ndata = 0; |
| 67 npp_->pdata = 0; | 60 npp_->pdata = 0; |
| 68 | 61 |
| 69 if (mime_type_ == kFlashPluginSwfMimeType) | 62 if (mime_type_ == kFlashPluginSwfMimeType) |
| 70 transparent_ = false; | 63 transparent_ = false; |
| 71 | 64 |
| 72 memset(&zero_padding_, 0, sizeof(zero_padding_)); | 65 memset(&zero_padding_, 0, sizeof(zero_padding_)); |
| 73 } | 66 } |
| 74 | 67 |
| 75 PluginInstance::~PluginInstance() { | 68 PluginInstance::~PluginInstance() { |
| 76 CloseStreams(); | |
| 77 | |
| 78 if (npp_ != 0) { | 69 if (npp_ != 0) { |
| 79 delete npp_; | 70 delete npp_; |
| 80 npp_ = 0; | 71 npp_ = 0; |
| 81 } | 72 } |
| 82 | 73 |
| 83 if (plugin_.get()) | 74 if (plugin_.get()) |
| 84 plugin_->CloseInstance(); | 75 plugin_->CloseInstance(); |
| 85 } | 76 } |
| 86 | 77 |
| 87 PluginStreamUrl* PluginInstance::CreateStream(unsigned long resource_id, | |
| 88 const GURL& url, | |
| 89 const std::string& mime_type, | |
| 90 int notify_id) { | |
| 91 | |
| 92 bool notify; | |
| 93 void* notify_data; | |
| 94 GetNotifyData(notify_id, ¬ify, ¬ify_data); | |
| 95 PluginStreamUrl* stream = new PluginStreamUrl( | |
| 96 resource_id, url, this, notify, notify_data); | |
| 97 | |
| 98 AddStream(stream); | |
| 99 return stream; | |
| 100 } | |
| 101 | |
| 102 void PluginInstance::AddStream(PluginStream* stream) { | |
| 103 open_streams_.push_back(make_scoped_refptr(stream)); | |
| 104 } | |
| 105 | |
| 106 void PluginInstance::RemoveStream(PluginStream* stream) { | |
| 107 if (in_close_streams_) | |
| 108 return; | |
| 109 | |
| 110 std::vector<scoped_refptr<PluginStream> >::iterator stream_index; | |
| 111 for (stream_index = open_streams_.begin(); | |
| 112 stream_index != open_streams_.end(); ++stream_index) { | |
| 113 if (stream_index->get() == stream) { | |
| 114 open_streams_.erase(stream_index); | |
| 115 break; | |
| 116 } | |
| 117 } | |
| 118 } | |
| 119 | |
| 120 bool PluginInstance::IsValidStream(const NPStream* stream) { | |
| 121 std::vector<scoped_refptr<PluginStream> >::iterator stream_index; | |
| 122 for (stream_index = open_streams_.begin(); | |
| 123 stream_index != open_streams_.end(); ++stream_index) { | |
| 124 if ((*stream_index)->stream() == stream) | |
| 125 return true; | |
| 126 } | |
| 127 | |
| 128 return false; | |
| 129 } | |
| 130 | |
| 131 void PluginInstance::CloseStreams() { | |
| 132 in_close_streams_ = true; | |
| 133 for (unsigned int index = 0; index < open_streams_.size(); ++index) { | |
| 134 // Close all streams on the way down. | |
| 135 open_streams_[index]->Close(NPRES_USER_BREAK); | |
| 136 } | |
| 137 open_streams_.clear(); | |
| 138 in_close_streams_ = false; | |
| 139 } | |
| 140 | |
| 141 WebPluginResourceClient* PluginInstance::GetRangeRequest( | |
| 142 int id) { | |
| 143 PendingRangeRequestMap::iterator iter = pending_range_requests_.find(id); | |
| 144 if (iter == pending_range_requests_.end()) { | |
| 145 NOTREACHED(); | |
| 146 return NULL; | |
| 147 } | |
| 148 | |
| 149 WebPluginResourceClient* rv = iter->second->AsResourceClient(); | |
| 150 pending_range_requests_.erase(iter); | |
| 151 return rv; | |
| 152 } | |
| 153 | |
| 154 bool PluginInstance::Start(const GURL& url, | 78 bool PluginInstance::Start(const GURL& url, |
| 155 char** const param_names, | 79 char** const param_names, |
| 156 char** const param_values, | 80 char** const param_values, |
| 157 int param_count, | 81 int param_count, |
| 158 bool load_manually) { | 82 bool load_manually) { |
| 159 load_manually_ = load_manually; | 83 load_manually_ = load_manually; |
| 160 unsigned short mode = load_manually_ ? NP_FULL : NP_EMBED; | 84 unsigned short mode = load_manually_ ? NP_FULL : NP_EMBED; |
| 161 npp_->ndata = this; | 85 npp_->ndata = this; |
| 162 | 86 |
| 163 NPError err = NPP_New(mode, param_count, | 87 NPError err = NPP_New(mode, param_count, |
| 164 const_cast<char **>(param_names), const_cast<char **>(param_values)); | 88 const_cast<char **>(param_names), const_cast<char **>(param_values)); |
| 165 | |
| 166 if (err == NPERR_NO_ERROR) { | |
| 167 handles_url_redirects_ = | |
| 168 ((npp_functions_->version >= NPVERS_HAS_URL_REDIRECT_HANDLING) && | |
| 169 (npp_functions_->urlredirectnotify)); | |
| 170 } | |
| 171 return err == NPERR_NO_ERROR; | 89 return err == NPERR_NO_ERROR; |
| 172 } | 90 } |
| 173 | 91 |
| 174 NPObject *PluginInstance::GetPluginScriptableObject() { | 92 NPObject *PluginInstance::GetPluginScriptableObject() { |
| 175 NPObject *value = NULL; | 93 NPObject *value = NULL; |
| 176 NPError error = NPP_GetValue(NPPVpluginScriptableNPObject, &value); | 94 NPError error = NPP_GetValue(NPPVpluginScriptableNPObject, &value); |
| 177 if (error != NPERR_NO_ERROR || value == NULL) | 95 if (error != NPERR_NO_ERROR || value == NULL) |
| 178 return NULL; | 96 return NULL; |
| 179 return value; | 97 return value; |
| 180 } | 98 } |
| 181 | 99 |
| 182 bool PluginInstance::GetFormValue(base::string16* value) { | 100 bool PluginInstance::GetFormValue(base::string16* value) { |
| 183 // Plugins will allocate memory for the return value by using NPN_MemAlloc(). | 101 // Plugins will allocate memory for the return value by using NPN_MemAlloc(). |
| 184 char *plugin_value = NULL; | 102 char *plugin_value = NULL; |
| 185 NPError error = NPP_GetValue(NPPVformValue, &plugin_value); | 103 NPError error = NPP_GetValue(NPPVformValue, &plugin_value); |
| 186 if (error != NPERR_NO_ERROR || !plugin_value) { | 104 if (error != NPERR_NO_ERROR || !plugin_value) { |
| 187 return false; | 105 return false; |
| 188 } | 106 } |
| 189 // Assumes the result is UTF8 text, as Firefox does. | 107 // Assumes the result is UTF8 text, as Firefox does. |
| 190 *value = base::UTF8ToUTF16(plugin_value); | 108 *value = base::UTF8ToUTF16(plugin_value); |
| 191 host_->host_functions()->memfree(plugin_value); | 109 host_->host_functions()->memfree(plugin_value); |
| 192 return true; | 110 return true; |
| 193 } | 111 } |
| 194 | 112 |
| 195 // WebPluginLoadDelegate methods | |
| 196 void PluginInstance::DidFinishLoadWithReason(const GURL& url, | |
| 197 NPReason reason, | |
| 198 int notify_id) { | |
| 199 bool notify; | |
| 200 void* notify_data; | |
| 201 GetNotifyData(notify_id, ¬ify, ¬ify_data); | |
| 202 if (!notify) { | |
| 203 NOTREACHED(); | |
| 204 return; | |
| 205 } | |
| 206 | |
| 207 NPP_URLNotify(url.spec().c_str(), reason, notify_data); | |
| 208 } | |
| 209 | |
| 210 unsigned PluginInstance::GetBackingTextureId() { | 113 unsigned PluginInstance::GetBackingTextureId() { |
| 211 // By default the plugin instance is not backed by an OpenGL texture. | 114 // By default the plugin instance is not backed by an OpenGL texture. |
| 212 return 0; | 115 return 0; |
| 213 } | 116 } |
| 214 | 117 |
| 215 // NPAPI methods | 118 // NPAPI methods |
| 216 NPError PluginInstance::NPP_New(unsigned short mode, | 119 NPError PluginInstance::NPP_New(unsigned short mode, |
| 217 short argc, | 120 short argc, |
| 218 char* argn[], | 121 char* argn[], |
| 219 char* argv[]) { | 122 char* argv[]) { |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 273 if (npp_functions_->newstream != 0) { | 176 if (npp_functions_->newstream != 0) { |
| 274 return npp_functions_->newstream(npp_, type, stream, seekable, stype); | 177 return npp_functions_->newstream(npp_, type, stream, seekable, stype); |
| 275 } | 178 } |
| 276 return NPERR_INVALID_FUNCTABLE_ERROR; | 179 return NPERR_INVALID_FUNCTABLE_ERROR; |
| 277 } | 180 } |
| 278 | 181 |
| 279 NPError PluginInstance::NPP_DestroyStream(NPStream* stream, NPReason reason) { | 182 NPError PluginInstance::NPP_DestroyStream(NPStream* stream, NPReason reason) { |
| 280 DCHECK(npp_functions_ != 0); | 183 DCHECK(npp_functions_ != 0); |
| 281 DCHECK(npp_functions_->destroystream != 0); | 184 DCHECK(npp_functions_->destroystream != 0); |
| 282 | 185 |
| 283 if (stream == NULL || !IsValidStream(stream) || (stream->ndata == NULL)) | 186 if (stream == NULL || (stream->ndata == NULL)) |
| 284 return NPERR_INVALID_INSTANCE_ERROR; | 187 return NPERR_INVALID_INSTANCE_ERROR; |
| 285 | 188 |
| 286 if (npp_functions_->destroystream != 0) { | 189 if (npp_functions_->destroystream != 0) { |
| 287 NPError result = npp_functions_->destroystream(npp_, stream, reason); | 190 NPError result = npp_functions_->destroystream(npp_, stream, reason); |
| 288 stream->ndata = NULL; | 191 stream->ndata = NULL; |
| 289 return result; | 192 return result; |
| 290 } | 193 } |
| 291 return NPERR_INVALID_FUNCTABLE_ERROR; | 194 return NPERR_INVALID_FUNCTABLE_ERROR; |
| 292 } | 195 } |
| 293 | 196 |
| (...skipping 25 matching lines...) Expand all Loading... |
| 319 npp_functions_->asfile(npp_, stream, fname); | 222 npp_functions_->asfile(npp_, stream, fname); |
| 320 } | 223 } |
| 321 | 224 |
| 322 // Creating a temporary FilePath instance on the stack as the explicit | 225 // Creating a temporary FilePath instance on the stack as the explicit |
| 323 // FilePath constructor with StringType as an argument causes a compiler | 226 // FilePath constructor with StringType as an argument causes a compiler |
| 324 // error when invoked via vector push back. | 227 // error when invoked via vector push back. |
| 325 base::FilePath file_name = base::FilePath::FromUTF8Unsafe(fname); | 228 base::FilePath file_name = base::FilePath::FromUTF8Unsafe(fname); |
| 326 files_created_.push_back(file_name); | 229 files_created_.push_back(file_name); |
| 327 } | 230 } |
| 328 | 231 |
| 329 void PluginInstance::NPP_URLNotify(const char* url, | |
| 330 NPReason reason, | |
| 331 void* notifyData) { | |
| 332 DCHECK(npp_functions_ != 0); | |
| 333 DCHECK(npp_functions_->urlnotify != 0); | |
| 334 if (npp_functions_->urlnotify != 0) { | |
| 335 npp_functions_->urlnotify(npp_, url, reason, notifyData); | |
| 336 } | |
| 337 } | |
| 338 | |
| 339 NPError PluginInstance::NPP_GetValue(NPPVariable variable, void* value) { | 232 NPError PluginInstance::NPP_GetValue(NPPVariable variable, void* value) { |
| 340 DCHECK(npp_functions_ != 0); | 233 DCHECK(npp_functions_ != 0); |
| 341 // getvalue is NULL for Shockwave | 234 // getvalue is NULL for Shockwave |
| 342 if (npp_functions_->getvalue != 0) { | 235 if (npp_functions_->getvalue != 0) { |
| 343 return npp_functions_->getvalue(npp_, variable, value); | 236 return npp_functions_->getvalue(npp_, variable, value); |
| 344 } | 237 } |
| 345 return NPERR_INVALID_FUNCTABLE_ERROR; | 238 return NPERR_INVALID_FUNCTABLE_ERROR; |
| 346 } | 239 } |
| 347 | 240 |
| 348 NPError PluginInstance::NPP_SetValue(NPNVariable variable, void* value) { | 241 NPError PluginInstance::NPP_SetValue(NPNVariable variable, void* value) { |
| (...skipping 15 matching lines...) Expand all Loading... |
| 364 | 257 |
| 365 bool PluginInstance::NPP_Print(NPPrint* platform_print) { | 258 bool PluginInstance::NPP_Print(NPPrint* platform_print) { |
| 366 DCHECK(npp_functions_ != 0); | 259 DCHECK(npp_functions_ != 0); |
| 367 if (npp_functions_->print != 0) { | 260 if (npp_functions_->print != 0) { |
| 368 npp_functions_->print(npp_, platform_print); | 261 npp_functions_->print(npp_, platform_print); |
| 369 return true; | 262 return true; |
| 370 } | 263 } |
| 371 return false; | 264 return false; |
| 372 } | 265 } |
| 373 | 266 |
| 374 void PluginInstance::NPP_URLRedirectNotify(const char* url, int32_t status, | |
| 375 void* notify_data) { | |
| 376 DCHECK(npp_functions_ != 0); | |
| 377 if (npp_functions_->urlredirectnotify != 0) { | |
| 378 npp_functions_->urlredirectnotify(npp_, url, status, notify_data); | |
| 379 } | |
| 380 } | |
| 381 | |
| 382 void PluginInstance::SendJavaScriptStream(const GURL& url, | |
| 383 const std::string& result, | |
| 384 bool success, | |
| 385 int notify_id) { | |
| 386 bool notify; | |
| 387 void* notify_data; | |
| 388 GetNotifyData(notify_id, ¬ify, ¬ify_data); | |
| 389 | |
| 390 if (success) { | |
| 391 PluginStringStream *stream = | |
| 392 new PluginStringStream(this, url, notify, notify_data); | |
| 393 AddStream(stream); | |
| 394 stream->SendToPlugin(result, "text/html"); | |
| 395 } else { | |
| 396 // NOTE: Sending an empty stream here will crash MacroMedia | |
| 397 // Flash 9. Just send the URL Notify. | |
| 398 if (notify) | |
| 399 NPP_URLNotify(url.spec().c_str(), NPRES_DONE, notify_data); | |
| 400 } | |
| 401 } | |
| 402 | |
| 403 void PluginInstance::DidReceiveManualResponse(const GURL& url, | |
| 404 const std::string& mime_type, | |
| 405 const std::string& headers, | |
| 406 uint32 expected_length, | |
| 407 uint32 last_modified) { | |
| 408 DCHECK(load_manually_); | |
| 409 | |
| 410 plugin_data_stream_ = | |
| 411 CreateStream(static_cast<unsigned long>(-1), url, mime_type, 0); | |
| 412 plugin_data_stream_->DidReceiveResponse(mime_type, headers, expected_length, | |
| 413 last_modified, true); | |
| 414 } | |
| 415 | |
| 416 void PluginInstance::DidReceiveManualData(const char* buffer, int length) { | |
| 417 DCHECK(load_manually_); | |
| 418 if (plugin_data_stream_.get() != NULL) { | |
| 419 plugin_data_stream_->DidReceiveData(buffer, length, 0); | |
| 420 } | |
| 421 } | |
| 422 | |
| 423 void PluginInstance::DidFinishManualLoading() { | |
| 424 DCHECK(load_manually_); | |
| 425 if (plugin_data_stream_.get() != NULL) { | |
| 426 plugin_data_stream_->DidFinishLoading(plugin_data_stream_->ResourceId()); | |
| 427 plugin_data_stream_->Close(NPRES_DONE); | |
| 428 plugin_data_stream_ = NULL; | |
| 429 } | |
| 430 } | |
| 431 | |
| 432 void PluginInstance::DidManualLoadFail() { | |
| 433 DCHECK(load_manually_); | |
| 434 if (plugin_data_stream_.get() != NULL) { | |
| 435 plugin_data_stream_->DidFail(plugin_data_stream_->ResourceId()); | |
| 436 plugin_data_stream_ = NULL; | |
| 437 } | |
| 438 } | |
| 439 | 267 |
| 440 void PluginInstance::PluginThreadAsyncCall(void (*func)(void*), | 268 void PluginInstance::PluginThreadAsyncCall(void (*func)(void*), |
| 441 void* user_data) { | 269 void* user_data) { |
| 442 task_runner_->PostTask( | 270 task_runner_->PostTask( |
| 443 FROM_HERE, base::Bind(&PluginInstance::OnPluginThreadAsyncCall, this, | 271 FROM_HERE, base::Bind(&PluginInstance::OnPluginThreadAsyncCall, this, |
| 444 func, user_data)); | 272 func, user_data)); |
| 445 } | 273 } |
| 446 | 274 |
| 447 void PluginInstance::OnPluginThreadAsyncCall(void (*func)(void*), | 275 void PluginInstance::OnPluginThreadAsyncCall(void (*func)(void*), |
| 448 void* user_data) { | 276 void* user_data) { |
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 519 } | 347 } |
| 520 | 348 |
| 521 void PluginInstance::PushPopupsEnabledState(bool enabled) { | 349 void PluginInstance::PushPopupsEnabledState(bool enabled) { |
| 522 popups_enabled_stack_.push(enabled); | 350 popups_enabled_stack_.push(enabled); |
| 523 } | 351 } |
| 524 | 352 |
| 525 void PluginInstance::PopPopupsEnabledState() { | 353 void PluginInstance::PopPopupsEnabledState() { |
| 526 popups_enabled_stack_.pop(); | 354 popups_enabled_stack_.pop(); |
| 527 } | 355 } |
| 528 | 356 |
| 529 void PluginInstance::RequestRead(NPStream* stream, NPByteRange* range_list) { | |
| 530 std::string range_info = "bytes="; | |
| 531 | |
| 532 while (range_list) { | |
| 533 range_info += base::IntToString(range_list->offset); | |
| 534 range_info.push_back('-'); | |
| 535 range_info += | |
| 536 base::UintToString(range_list->offset + range_list->length - 1); | |
| 537 range_list = range_list->next; | |
| 538 if (range_list) | |
| 539 range_info.push_back(','); | |
| 540 } | |
| 541 | |
| 542 if (plugin_data_stream_.get()) { | |
| 543 if (plugin_data_stream_->stream() == stream) { | |
| 544 webplugin_->CancelDocumentLoad(); | |
| 545 plugin_data_stream_ = NULL; | |
| 546 } | |
| 547 } | |
| 548 | |
| 549 // The lifetime of a NPStream instance depends on the PluginStream instance | |
| 550 // which owns it. When a plugin invokes NPN_RequestRead on a seekable stream, | |
| 551 // we don't want to create a new stream when the corresponding response is | |
| 552 // received. We send over a cookie which represents the PluginStream | |
| 553 // instance which is sent back from the renderer when the response is | |
| 554 // received. | |
| 555 std::vector<scoped_refptr<PluginStream> >::iterator stream_index; | |
| 556 for (stream_index = open_streams_.begin(); | |
| 557 stream_index != open_streams_.end(); ++stream_index) { | |
| 558 PluginStream* plugin_stream = stream_index->get(); | |
| 559 if (plugin_stream->stream() == stream) { | |
| 560 // A stream becomes seekable the first time NPN_RequestRead | |
| 561 // is called on it. | |
| 562 plugin_stream->set_seekable(true); | |
| 563 | |
| 564 if (base::CommandLine::ForCurrentProcess()->HasSwitch( | |
| 565 switches::kDisableDirectNPAPIRequests)) { | |
| 566 pending_range_requests_[++next_range_request_id_] = plugin_stream; | |
| 567 webplugin_->InitiateHTTPRangeRequest( | |
| 568 stream->url, range_info.c_str(), next_range_request_id_); | |
| 569 return; | |
| 570 } else { | |
| 571 PluginStreamUrl* plugin_stream_url = | |
| 572 static_cast<PluginStreamUrl*>(plugin_stream); | |
| 573 plugin_stream_url->FetchRange(range_info); | |
| 574 return; | |
| 575 } | |
| 576 } | |
| 577 } | |
| 578 NOTREACHED(); | |
| 579 } | |
| 580 | |
| 581 void PluginInstance::RequestURL(const char* url, | |
| 582 const char* method, | |
| 583 const char* target, | |
| 584 const char* buf, | |
| 585 unsigned int len, | |
| 586 bool notify, | |
| 587 void* notify_data) { | |
| 588 int notify_id = 0; | |
| 589 if (notify) { | |
| 590 notify_id = ++next_notify_id_; | |
| 591 pending_requests_[notify_id] = notify_data; | |
| 592 } | |
| 593 | |
| 594 webplugin_->HandleURLRequest( | |
| 595 url, method, target, buf, len, notify_id, popups_allowed(), | |
| 596 notify ? handles_url_redirects_ : false); | |
| 597 } | |
| 598 | |
| 599 bool PluginInstance::ConvertPoint(double source_x, double source_y, | 357 bool PluginInstance::ConvertPoint(double source_x, double source_y, |
| 600 NPCoordinateSpace source_space, | 358 NPCoordinateSpace source_space, |
| 601 double* dest_x, double* dest_y, | 359 double* dest_x, double* dest_y, |
| 602 NPCoordinateSpace dest_space) { | 360 NPCoordinateSpace dest_space) { |
| 603 #if defined(OS_MACOSX) | 361 #if defined(OS_MACOSX) |
| 604 CGRect main_display_bounds = CGDisplayBounds(CGMainDisplayID()); | 362 CGRect main_display_bounds = CGDisplayBounds(CGMainDisplayID()); |
| 605 | 363 |
| 606 double flipped_screen_x = source_x; | 364 double flipped_screen_x = source_x; |
| 607 double flipped_screen_y = source_y; | 365 double flipped_screen_y = source_y; |
| 608 switch(source_space) { | 366 switch(source_space) { |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 659 *dest_x = target_x; | 417 *dest_x = target_x; |
| 660 if (dest_y) | 418 if (dest_y) |
| 661 *dest_y = target_y; | 419 *dest_y = target_y; |
| 662 return true; | 420 return true; |
| 663 #else | 421 #else |
| 664 NOTIMPLEMENTED(); | 422 NOTIMPLEMENTED(); |
| 665 return false; | 423 return false; |
| 666 #endif | 424 #endif |
| 667 } | 425 } |
| 668 | 426 |
| 669 void PluginInstance::GetNotifyData(int notify_id, | |
| 670 bool* notify, | |
| 671 void** notify_data) { | |
| 672 PendingRequestMap::iterator iter = pending_requests_.find(notify_id); | |
| 673 if (iter != pending_requests_.end()) { | |
| 674 *notify = true; | |
| 675 *notify_data = iter->second; | |
| 676 pending_requests_.erase(iter); | |
| 677 } else { | |
| 678 *notify = false; | |
| 679 *notify_data = NULL; | |
| 680 } | |
| 681 } | |
| 682 | |
| 683 void PluginInstance::URLRedirectResponse(bool allow, void* notify_data) { | |
| 684 // The notify_data passed in allows us to identify the matching stream. | |
| 685 std::vector<scoped_refptr<PluginStream> >::iterator stream_index; | |
| 686 for (stream_index = open_streams_.begin(); | |
| 687 stream_index != open_streams_.end(); ++stream_index) { | |
| 688 PluginStream* plugin_stream = stream_index->get(); | |
| 689 if (plugin_stream->notify_data() == notify_data) { | |
| 690 PluginStreamUrl* plugin_stream_url = | |
| 691 static_cast<PluginStreamUrl*>(plugin_stream); | |
| 692 plugin_stream_url->URLRedirectResponse(allow); | |
| 693 break; | |
| 694 } | |
| 695 } | |
| 696 } | |
| 697 | |
| 698 } // namespace content | 427 } // namespace content |
| OLD | NEW |