| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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 "components/nacl/renderer/ppb_nacl_private_impl.h" | 5 #include "components/nacl/renderer/ppb_nacl_private_impl.h" |
| 6 | 6 |
| 7 #include <numeric> | 7 #include <numeric> |
| 8 #include <string> | 8 #include <string> |
| 9 #include <vector> | 9 #include <vector> |
| 10 | 10 |
| (...skipping 367 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 378 void* imc_handle, | 378 void* imc_handle, |
| 379 PP_CompletionCallback callback) { | 379 PP_CompletionCallback callback) { |
| 380 CHECK(ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()-> | 380 CHECK(ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()-> |
| 381 BelongsToCurrentThread()); | 381 BelongsToCurrentThread()); |
| 382 NaClAppProcessType process_type = PP_ToNaClAppProcessType(pp_process_type); | 382 NaClAppProcessType process_type = PP_ToNaClAppProcessType(pp_process_type); |
| 383 // Create the manifest service proxy here, so on error case, it will be | 383 // Create the manifest service proxy here, so on error case, it will be |
| 384 // destructed (without passing it to ManifestServiceChannel). | 384 // destructed (without passing it to ManifestServiceChannel). |
| 385 scoped_ptr<ManifestServiceChannel::Delegate> manifest_service_proxy( | 385 scoped_ptr<ManifestServiceChannel::Delegate> manifest_service_proxy( |
| 386 new ManifestServiceProxy(instance, process_type)); | 386 new ManifestServiceProxy(instance, process_type)); |
| 387 | 387 |
| 388 FileDescriptor result_socket; | |
| 389 IPC::Sender* sender = content::RenderThread::Get(); | 388 IPC::Sender* sender = content::RenderThread::Get(); |
| 390 DCHECK(sender); | 389 DCHECK(sender); |
| 391 int routing_id = GetRoutingID(instance); | 390 int routing_id = GetRoutingID(instance); |
| 392 NexeLoadManager* load_manager = GetNexeLoadManager(instance); | 391 NexeLoadManager* load_manager = GetNexeLoadManager(instance); |
| 393 DCHECK(load_manager); | 392 DCHECK(load_manager); |
| 394 content::PepperPluginInstance* plugin_instance = | 393 content::PepperPluginInstance* plugin_instance = |
| 395 content::PepperPluginInstance::Get(instance); | 394 content::PepperPluginInstance::Get(instance); |
| 396 DCHECK(plugin_instance); | 395 DCHECK(plugin_instance); |
| 397 if (!routing_id || !load_manager || !plugin_instance) { | 396 if (!routing_id || !load_manager || !plugin_instance) { |
| 398 if (nexe_file_info->handle != PP_kInvalidFileHandle) { | 397 if (nexe_file_info->handle != PP_kInvalidFileHandle) { |
| 399 base::File closer(nexe_file_info->handle); | 398 base::File closer(nexe_file_info->handle); |
| 400 } | 399 } |
| 401 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( | 400 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( |
| 402 FROM_HERE, base::Bind(callback.func, callback.user_data, | 401 FROM_HERE, base::Bind(callback.func, callback.user_data, |
| 403 static_cast<int32_t>(PP_ERROR_FAILED))); | 402 static_cast<int32_t>(PP_ERROR_FAILED))); |
| 404 return; | 403 return; |
| 405 } | 404 } |
| 406 | 405 |
| 407 InstanceInfo instance_info; | 406 InstanceInfo instance_info; |
| 408 instance_info.url = GURL(alleged_url); | 407 instance_info.url = GURL(alleged_url); |
| 409 | 408 |
| 410 uint32_t perm_bits = ppapi::PERMISSION_NONE; | 409 uint32_t perm_bits = ppapi::PERMISSION_NONE; |
| 411 // Conditionally block 'Dev' interfaces. We do this for the NaCl process, so | 410 // Conditionally block 'Dev' interfaces. We do this for the NaCl process, so |
| 412 // it's clearer to developers when they are using 'Dev' inappropriately. We | 411 // it's clearer to developers when they are using 'Dev' inappropriately. We |
| 413 // must also check on the trusted side of the proxy. | 412 // must also check on the trusted side of the proxy. |
| 414 if (load_manager->DevInterfacesEnabled()) | 413 if (load_manager->DevInterfacesEnabled()) |
| 415 perm_bits |= ppapi::PERMISSION_DEV; | 414 perm_bits |= ppapi::PERMISSION_DEV; |
| 416 instance_info.permissions = | 415 instance_info.permissions = |
| 417 ppapi::PpapiPermissions::GetForCommandLine(perm_bits); | 416 ppapi::PpapiPermissions::GetForCommandLine(perm_bits); |
| 418 std::string error_message_string; | |
| 419 NaClLaunchResult launch_result; | |
| 420 | |
| 421 IPC::PlatformFileForTransit nexe_for_transit = | |
| 422 IPC::InvalidPlatformFileForTransit(); | |
| 423 | 417 |
| 424 std::vector<NaClResourcePrefetchRequest> resource_prefetch_request_list; | 418 std::vector<NaClResourcePrefetchRequest> resource_prefetch_request_list; |
| 425 if (process_type == kNativeNaClProcessType) { | 419 if (process_type == kNativeNaClProcessType) { |
| 426 JsonManifest* manifest = GetJsonManifest(instance); | 420 JsonManifest* manifest = GetJsonManifest(instance); |
| 427 if (manifest) { | 421 if (manifest) { |
| 428 manifest->GetPrefetchableFiles(&resource_prefetch_request_list); | 422 manifest->GetPrefetchableFiles(&resource_prefetch_request_list); |
| 429 | 423 |
| 430 for (size_t i = 0; i < resource_prefetch_request_list.size(); ++i) { | 424 for (size_t i = 0; i < resource_prefetch_request_list.size(); ++i) { |
| 431 const GURL gurl(resource_prefetch_request_list[i].resource_url); | 425 const GURL gurl(resource_prefetch_request_list[i].resource_url); |
| 432 // Important security check. Do not remove. | 426 // Important security check. Do not remove. |
| 433 if (!CanOpenViaFastPath(plugin_instance, gurl)) { | 427 if (!CanOpenViaFastPath(plugin_instance, gurl)) { |
| 434 resource_prefetch_request_list.clear(); | 428 resource_prefetch_request_list.clear(); |
| 435 break; | 429 break; |
| 436 } | 430 } |
| 437 } | 431 } |
| 438 } | 432 } |
| 439 } | 433 } |
| 440 | 434 |
| 435 IPC::PlatformFileForTransit nexe_for_transit = |
| 436 IPC::InvalidPlatformFileForTransit(); |
| 441 #if defined(OS_POSIX) | 437 #if defined(OS_POSIX) |
| 442 if (nexe_file_info->handle != PP_kInvalidFileHandle) | 438 if (nexe_file_info->handle != PP_kInvalidFileHandle) |
| 443 nexe_for_transit = base::FileDescriptor(nexe_file_info->handle, true); | 439 nexe_for_transit = base::FileDescriptor(nexe_file_info->handle, true); |
| 444 #elif defined(OS_WIN) | 440 #elif defined(OS_WIN) |
| 445 // Duplicate the handle on the browser side instead of the renderer. | 441 // Duplicate the handle on the browser side instead of the renderer. |
| 446 // This is because BrokerGetFileForProcess isn't part of content/public, and | 442 // This is because BrokerGetFileForProcess isn't part of content/public, and |
| 447 // it's simpler to do the duplication in the browser anyway. | 443 // it's simpler to do the duplication in the browser anyway. |
| 448 nexe_for_transit = nexe_file_info->handle; | 444 nexe_for_transit = nexe_file_info->handle; |
| 449 #else | 445 #else |
| 450 #error Unsupported target platform. | 446 # error Unsupported target platform. |
| 451 #endif | 447 #endif |
| 448 |
| 449 std::string error_message_string; |
| 450 NaClLaunchResult launch_result; |
| 452 if (!sender->Send(new NaClHostMsg_LaunchNaCl( | 451 if (!sender->Send(new NaClHostMsg_LaunchNaCl( |
| 453 NaClLaunchParams( | 452 NaClLaunchParams( |
| 454 instance_info.url.spec(), | 453 instance_info.url.spec(), |
| 455 nexe_for_transit, | 454 nexe_for_transit, |
| 456 nexe_file_info->token_lo, | 455 nexe_file_info->token_lo, |
| 457 nexe_file_info->token_hi, | 456 nexe_file_info->token_hi, |
| 458 resource_prefetch_request_list, | 457 resource_prefetch_request_list, |
| 459 routing_id, | 458 routing_id, |
| 460 perm_bits, | 459 perm_bits, |
| 461 PP_ToBool(uses_nonsfi_mode), | 460 PP_ToBool(uses_nonsfi_mode), |
| 462 process_type), | 461 process_type), |
| 463 &launch_result, | 462 &launch_result, |
| 464 &error_message_string))) { | 463 &error_message_string))) { |
| 465 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( | 464 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( |
| 466 FROM_HERE, | 465 FROM_HERE, |
| 467 base::Bind(callback.func, callback.user_data, | 466 base::Bind(callback.func, callback.user_data, |
| 468 static_cast<int32_t>(PP_ERROR_FAILED))); | 467 static_cast<int32_t>(PP_ERROR_FAILED))); |
| 469 return; | 468 return; |
| 470 } | 469 } |
| 471 | 470 |
| 472 load_manager->set_nonsfi(PP_ToBool(uses_nonsfi_mode)); | 471 load_manager->set_nonsfi(PP_ToBool(uses_nonsfi_mode)); |
| 473 | 472 |
| 474 if (!error_message_string.empty()) { | 473 if (!error_message_string.empty()) { |
| 474 // Even on error, some FDs/handles may be passed to here. |
| 475 // We must release those resources. |
| 476 // See also nacl_process_host.cc. |
| 477 IPC::PlatformFileForTransitToFile(launch_result.imc_channel_handle); |
| 478 base::SharedMemory::CloseHandle(launch_result.crash_info_shmem_handle); |
| 479 |
| 475 if (PP_ToBool(main_service_runtime)) { | 480 if (PP_ToBool(main_service_runtime)) { |
| 476 load_manager->ReportLoadError(PP_NACL_ERROR_SEL_LDR_LAUNCH, | 481 load_manager->ReportLoadError(PP_NACL_ERROR_SEL_LDR_LAUNCH, |
| 477 "ServiceRuntime: failed to start", | 482 "ServiceRuntime: failed to start", |
| 478 error_message_string); | 483 error_message_string); |
| 479 } | 484 } |
| 480 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( | 485 ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( |
| 481 FROM_HERE, | 486 FROM_HERE, |
| 482 base::Bind(callback.func, callback.user_data, | 487 base::Bind(callback.func, callback.user_data, |
| 483 static_cast<int32_t>(PP_ERROR_FAILED))); | 488 static_cast<int32_t>(PP_ERROR_FAILED))); |
| 484 return; | 489 return; |
| 485 } | 490 } |
| 486 result_socket = launch_result.imc_channel_handle; | 491 |
| 487 instance_info.channel_handle = launch_result.ppapi_ipc_channel_handle; | 492 instance_info.channel_handle = launch_result.ppapi_ipc_channel_handle; |
| 488 instance_info.plugin_pid = launch_result.plugin_pid; | 493 instance_info.plugin_pid = launch_result.plugin_pid; |
| 489 instance_info.plugin_child_id = launch_result.plugin_child_id; | 494 instance_info.plugin_child_id = launch_result.plugin_child_id; |
| 490 | 495 |
| 491 // Don't save instance_info if channel handle is invalid. | 496 // Don't save instance_info if channel handle is invalid. |
| 492 if (IsValidChannelHandle(instance_info.channel_handle)) { | 497 if (IsValidChannelHandle(instance_info.channel_handle)) { |
| 493 NaClPluginInstance* nacl_plugin_instance = GetNaClPluginInstance(instance); | 498 NaClPluginInstance* nacl_plugin_instance = GetNaClPluginInstance(instance); |
| 494 nacl_plugin_instance->instance_info.reset(new InstanceInfo(instance_info)); | 499 nacl_plugin_instance->instance_info.reset(new InstanceInfo(instance_info)); |
| 495 } | 500 } |
| 496 | 501 |
| 497 *(static_cast<NaClHandle*>(imc_handle)) = ToNativeHandle(result_socket); | 502 *(static_cast<NaClHandle*>(imc_handle)) = |
| 503 IPC::PlatformFileForTransitToPlatformFile( |
| 504 launch_result.imc_channel_handle); |
| 498 | 505 |
| 499 // Store the crash information shared memory handle. | 506 // Store the crash information shared memory handle. |
| 500 load_manager->set_crash_info_shmem_handle( | 507 load_manager->set_crash_info_shmem_handle( |
| 501 launch_result.crash_info_shmem_handle); | 508 launch_result.crash_info_shmem_handle); |
| 502 | 509 |
| 503 // Create the trusted plugin channel. | 510 // Create the trusted plugin channel. |
| 504 if (IsValidChannelHandle(launch_result.trusted_ipc_channel_handle)) { | 511 if (IsValidChannelHandle(launch_result.trusted_ipc_channel_handle)) { |
| 505 bool is_helper_nexe = !PP_ToBool(main_service_runtime); | 512 bool is_helper_nexe = !PP_ToBool(main_service_runtime); |
| 506 scoped_ptr<TrustedPluginChannel> trusted_plugin_channel( | 513 scoped_ptr<TrustedPluginChannel> trusted_plugin_channel( |
| 507 new TrustedPluginChannel( | 514 new TrustedPluginChannel( |
| (...skipping 1201 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1709 &StreamPexe | 1716 &StreamPexe |
| 1710 }; | 1717 }; |
| 1711 | 1718 |
| 1712 } // namespace | 1719 } // namespace |
| 1713 | 1720 |
| 1714 const PPB_NaCl_Private* GetNaClPrivateInterface() { | 1721 const PPB_NaCl_Private* GetNaClPrivateInterface() { |
| 1715 return &nacl_interface; | 1722 return &nacl_interface; |
| 1716 } | 1723 } |
| 1717 | 1724 |
| 1718 } // namespace nacl | 1725 } // namespace nacl |
| OLD | NEW |