| 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/common/sandbox_win.h" | 5 #include "content/common/sandbox_win.h" |
| 6 | 6 |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "base/base_switches.h" | 9 #include "base/base_switches.h" |
| 10 #include "base/command_line.h" | 10 #include "base/command_line.h" |
| (...skipping 449 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 460 // We're not worried about broker handles or not crossing process boundaries. | 460 // We're not worried about broker handles or not crossing process boundaries. |
| 461 if (source_process_handle == target_process_handle || | 461 if (source_process_handle == target_process_handle || |
| 462 target_process_handle == ::GetCurrentProcess()) | 462 target_process_handle == ::GetCurrentProcess()) |
| 463 return TRUE; | 463 return TRUE; |
| 464 | 464 |
| 465 // Only sandboxed children are placed in jobs, so just check them. | 465 // Only sandboxed children are placed in jobs, so just check them. |
| 466 BOOL is_in_job = FALSE; | 466 BOOL is_in_job = FALSE; |
| 467 if (!::IsProcessInJob(target_process_handle, NULL, &is_in_job)) { | 467 if (!::IsProcessInJob(target_process_handle, NULL, &is_in_job)) { |
| 468 // We need a handle with permission to check the job object. | 468 // We need a handle with permission to check the job object. |
| 469 if (ERROR_ACCESS_DENIED == ::GetLastError()) { | 469 if (ERROR_ACCESS_DENIED == ::GetLastError()) { |
| 470 HANDLE temp_handle; | 470 base::win::ScopedHandle process; |
| 471 CHECK(g_iat_orig_duplicate_handle(::GetCurrentProcess(), | 471 CHECK(g_iat_orig_duplicate_handle(::GetCurrentProcess(), |
| 472 target_process_handle, | 472 target_process_handle, |
| 473 ::GetCurrentProcess(), | 473 ::GetCurrentProcess(), |
| 474 &temp_handle, | 474 process.Receive(), |
| 475 PROCESS_QUERY_INFORMATION, | 475 PROCESS_QUERY_INFORMATION, |
| 476 FALSE, 0)); | 476 FALSE, 0)); |
| 477 base::win::ScopedHandle process(temp_handle); | |
| 478 CHECK(::IsProcessInJob(process, NULL, &is_in_job)); | 477 CHECK(::IsProcessInJob(process, NULL, &is_in_job)); |
| 479 } | 478 } |
| 480 } | 479 } |
| 481 | 480 |
| 482 if (is_in_job) { | 481 if (is_in_job) { |
| 483 // We never allow inheritable child handles. | 482 // We never allow inheritable child handles. |
| 484 CHECK(!inherit_handle) << kDuplicateHandleWarning; | 483 CHECK(!inherit_handle) << kDuplicateHandleWarning; |
| 485 | 484 |
| 486 // Duplicate the handle again, to get the final permissions. | 485 // Duplicate the handle again, to get the final permissions. |
| 487 HANDLE temp_handle; | 486 base::win::ScopedHandle handle; |
| 488 CHECK(g_iat_orig_duplicate_handle(target_process_handle, *target_handle, | 487 CHECK(g_iat_orig_duplicate_handle(target_process_handle, *target_handle, |
| 489 ::GetCurrentProcess(), &temp_handle, | 488 ::GetCurrentProcess(), handle.Receive(), |
| 490 0, FALSE, DUPLICATE_SAME_ACCESS)); | 489 0, FALSE, DUPLICATE_SAME_ACCESS)); |
| 491 base::win::ScopedHandle handle(temp_handle); | |
| 492 | 490 |
| 493 // Callers use CHECK macro to make sure we get the right stack. | 491 // Callers use CHECK macro to make sure we get the right stack. |
| 494 CheckDuplicateHandle(handle); | 492 CheckDuplicateHandle(handle); |
| 495 } | 493 } |
| 496 | 494 |
| 497 return TRUE; | 495 return TRUE; |
| 498 } | 496 } |
| 499 #endif | 497 #endif |
| 500 | 498 |
| 501 } // namespace | 499 } // namespace |
| (...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 595 // to create separate pretetch settings for browser, renderer etc. | 593 // to create separate pretetch settings for browser, renderer etc. |
| 596 cmd_line->AppendArg(base::StringPrintf("/prefetch:%d", base::Hash(type_str))); | 594 cmd_line->AppendArg(base::StringPrintf("/prefetch:%d", base::Hash(type_str))); |
| 597 | 595 |
| 598 if (!in_sandbox) { | 596 if (!in_sandbox) { |
| 599 base::ProcessHandle process = 0; | 597 base::ProcessHandle process = 0; |
| 600 base::LaunchProcess(*cmd_line, base::LaunchOptions(), &process); | 598 base::LaunchProcess(*cmd_line, base::LaunchOptions(), &process); |
| 601 g_broker_services->AddTargetPeer(process); | 599 g_broker_services->AddTargetPeer(process); |
| 602 return process; | 600 return process; |
| 603 } | 601 } |
| 604 | 602 |
| 603 base::win::ScopedProcessInformation target; |
| 605 sandbox::TargetPolicy* policy = g_broker_services->CreatePolicy(); | 604 sandbox::TargetPolicy* policy = g_broker_services->CreatePolicy(); |
| 606 | 605 |
| 607 sandbox::MitigationFlags mitigations = sandbox::MITIGATION_HEAP_TERMINATE | | 606 sandbox::MitigationFlags mitigations = sandbox::MITIGATION_HEAP_TERMINATE | |
| 608 sandbox::MITIGATION_BOTTOM_UP_ASLR | | 607 sandbox::MITIGATION_BOTTOM_UP_ASLR | |
| 609 sandbox::MITIGATION_DEP | | 608 sandbox::MITIGATION_DEP | |
| 610 sandbox::MITIGATION_DEP_NO_ATL_THUNK | | 609 sandbox::MITIGATION_DEP_NO_ATL_THUNK | |
| 611 sandbox::MITIGATION_SEHOP; | 610 sandbox::MITIGATION_SEHOP; |
| 612 | 611 |
| 613 if (policy->SetProcessMitigations(mitigations) != sandbox::SBOX_ALL_OK) | 612 if (policy->SetProcessMitigations(mitigations) != sandbox::SBOX_ALL_OK) |
| 614 return 0; | 613 return 0; |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 666 | 665 |
| 667 if (delegate) { | 666 if (delegate) { |
| 668 bool success = true; | 667 bool success = true; |
| 669 delegate->PreSpawnTarget(policy, &success); | 668 delegate->PreSpawnTarget(policy, &success); |
| 670 if (!success) | 669 if (!success) |
| 671 return 0; | 670 return 0; |
| 672 } | 671 } |
| 673 | 672 |
| 674 TRACE_EVENT_BEGIN_ETW("StartProcessWithAccess::LAUNCHPROCESS", 0, 0); | 673 TRACE_EVENT_BEGIN_ETW("StartProcessWithAccess::LAUNCHPROCESS", 0, 0); |
| 675 | 674 |
| 676 PROCESS_INFORMATION temp_process_info = {}; | |
| 677 result = g_broker_services->SpawnTarget( | 675 result = g_broker_services->SpawnTarget( |
| 678 cmd_line->GetProgram().value().c_str(), | 676 cmd_line->GetProgram().value().c_str(), |
| 679 cmd_line->GetCommandLineString().c_str(), | 677 cmd_line->GetCommandLineString().c_str(), |
| 680 policy, &temp_process_info); | 678 policy, target.Receive()); |
| 681 policy->Release(); | 679 policy->Release(); |
| 682 base::win::ScopedProcessInformation target(temp_process_info); | |
| 683 | 680 |
| 684 TRACE_EVENT_END_ETW("StartProcessWithAccess::LAUNCHPROCESS", 0, 0); | 681 TRACE_EVENT_END_ETW("StartProcessWithAccess::LAUNCHPROCESS", 0, 0); |
| 685 | 682 |
| 686 if (sandbox::SBOX_ALL_OK != result) { | 683 if (sandbox::SBOX_ALL_OK != result) { |
| 687 if (result == sandbox::SBOX_ERROR_GENERIC) | 684 if (result == sandbox::SBOX_ERROR_GENERIC) |
| 688 DPLOG(ERROR) << "Failed to launch process"; | 685 DPLOG(ERROR) << "Failed to launch process"; |
| 689 else | 686 else |
| 690 DLOG(ERROR) << "Failed to launch process. Error: " << result; | 687 DLOG(ERROR) << "Failed to launch process. Error: " << result; |
| 691 return 0; | 688 return 0; |
| 692 } | 689 } |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 736 } | 733 } |
| 737 | 734 |
| 738 return false; | 735 return false; |
| 739 } | 736 } |
| 740 | 737 |
| 741 bool BrokerAddTargetPeer(HANDLE peer_process) { | 738 bool BrokerAddTargetPeer(HANDLE peer_process) { |
| 742 return g_broker_services->AddTargetPeer(peer_process) == sandbox::SBOX_ALL_OK; | 739 return g_broker_services->AddTargetPeer(peer_process) == sandbox::SBOX_ALL_OK; |
| 743 } | 740 } |
| 744 | 741 |
| 745 } // namespace content | 742 } // namespace content |
| OLD | NEW |