Index: sandbox/win/src/process_thread_dispatcher.cc |
diff --git a/sandbox/win/src/process_thread_dispatcher.cc b/sandbox/win/src/process_thread_dispatcher.cc |
deleted file mode 100644 |
index 886017c9a2cd26a30cc93759274c8730c078d87d..0000000000000000000000000000000000000000 |
--- a/sandbox/win/src/process_thread_dispatcher.cc |
+++ /dev/null |
@@ -1,278 +0,0 @@ |
-// Copyright (c) 2013 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "sandbox/win/src/process_thread_dispatcher.h" |
- |
-#include <stddef.h> |
-#include <stdint.h> |
- |
-#include "base/logging.h" |
-#include "sandbox/win/src/crosscall_client.h" |
-#include "sandbox/win/src/interception.h" |
-#include "sandbox/win/src/interceptors.h" |
-#include "sandbox/win/src/ipc_tags.h" |
-#include "sandbox/win/src/policy_broker.h" |
-#include "sandbox/win/src/policy_params.h" |
-#include "sandbox/win/src/process_thread_interception.h" |
-#include "sandbox/win/src/process_thread_policy.h" |
-#include "sandbox/win/src/sandbox.h" |
- |
-namespace { |
- |
-// Extracts the application name from a command line. |
-// |
-// The application name is the first element of the command line. If |
-// there is no quotes, the first element is delimited by the first space. |
-// If there are quotes, the first element is delimited by the quotes. |
-// |
-// The create process call is smarter than us. It tries really hard to launch |
-// the process even if the command line is wrong. For example: |
-// "c:\program files\test param" will first try to launch c:\program.exe then |
-// c:\program files\test.exe. We don't do that, we stop after at the first |
-// space when there is no quotes. |
-base::string16 GetPathFromCmdLine(const base::string16 &cmd_line) { |
- base::string16 exe_name; |
- // Check if it starts with '"'. |
- if (cmd_line[0] == L'\"') { |
- // Find the position of the second '"', this terminates the path. |
- base::string16::size_type pos = cmd_line.find(L'\"', 1); |
- if (base::string16::npos == pos) |
- return cmd_line; |
- exe_name = cmd_line.substr(1, pos - 1); |
- } else { |
- // There is no '"', that means that the appname is terminated at the |
- // first space. |
- base::string16::size_type pos = cmd_line.find(L' '); |
- if (base::string16::npos == pos) { |
- // There is no space, the cmd_line contains only the app_name |
- exe_name = cmd_line; |
- } else { |
- exe_name = cmd_line.substr(0, pos); |
- } |
- } |
- |
- return exe_name; |
-} |
- |
-// Returns true is the path in parameter is relative. False if it's |
-// absolute. |
-bool IsPathRelative(const base::string16 &path) { |
- // A path is Relative if it's not a UNC path beginnning with \\ or a |
- // path beginning with a drive. (i.e. X:\) |
- if (path.find(L"\\\\") == 0 || path.find(L":\\") == 1) |
- return false; |
- return true; |
-} |
- |
-// Converts a relative path to an absolute path. |
-bool ConvertToAbsolutePath(const base::string16& child_current_directory, |
- bool use_env_path, base::string16 *path) { |
- wchar_t file_buffer[MAX_PATH]; |
- wchar_t *file_part = NULL; |
- |
- // Here we should start by looking at the path where the child application was |
- // started. We don't have this information yet. |
- DWORD result = 0; |
- if (use_env_path) { |
- // Try with the complete path |
- result = ::SearchPath(NULL, path->c_str(), NULL, MAX_PATH, file_buffer, |
- &file_part); |
- } |
- |
- if (0 == result) { |
- // Try with the current directory of the child |
- result = ::SearchPath(child_current_directory.c_str(), path->c_str(), NULL, |
- MAX_PATH, file_buffer, &file_part); |
- } |
- |
- if (0 == result || result >= MAX_PATH) |
- return false; |
- |
- *path = file_buffer; |
- return true; |
-} |
- |
-} // namespace |
-namespace sandbox { |
- |
-ThreadProcessDispatcher::ThreadProcessDispatcher(PolicyBase* policy_base) |
- : policy_base_(policy_base) { |
- static const IPCCall open_thread = { |
- {IPC_NTOPENTHREAD_TAG, {UINT32_TYPE, UINT32_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::NtOpenThread)}; |
- |
- static const IPCCall open_process = { |
- {IPC_NTOPENPROCESS_TAG, {UINT32_TYPE, UINT32_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::NtOpenProcess)}; |
- |
- static const IPCCall process_token = { |
- {IPC_NTOPENPROCESSTOKEN_TAG, {VOIDPTR_TYPE, UINT32_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::NtOpenProcessToken)}; |
- |
- static const IPCCall process_tokenex = { |
- {IPC_NTOPENPROCESSTOKENEX_TAG, {VOIDPTR_TYPE, UINT32_TYPE, UINT32_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::NtOpenProcessTokenEx)}; |
- |
- static const IPCCall create_params = { |
- {IPC_CREATEPROCESSW_TAG, |
- {WCHAR_TYPE, WCHAR_TYPE, WCHAR_TYPE, INOUTPTR_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::CreateProcessW)}; |
- |
- // NOTE(liamjm): 2nd param is size_t: Using VOIDPTR_TYPE as they are |
- // the same size on windows. |
- static_assert(sizeof(size_t) == sizeof(void*), |
- "VOIDPTR_TYPE not same size as size_t"); |
- static const IPCCall create_thread_params = { |
- {IPC_CREATETHREAD_TAG, |
- {VOIDPTR_TYPE, VOIDPTR_TYPE, VOIDPTR_TYPE, UINT32_TYPE}}, |
- reinterpret_cast<CallbackGeneric>( |
- &ThreadProcessDispatcher::CreateThread)}; |
- |
- ipc_calls_.push_back(open_thread); |
- ipc_calls_.push_back(open_process); |
- ipc_calls_.push_back(process_token); |
- ipc_calls_.push_back(process_tokenex); |
- ipc_calls_.push_back(create_params); |
- ipc_calls_.push_back(create_thread_params); |
-} |
- |
-bool ThreadProcessDispatcher::SetupService(InterceptionManager* manager, |
- int service) { |
- switch (service) { |
- case IPC_NTOPENTHREAD_TAG: |
- case IPC_NTOPENPROCESS_TAG: |
- case IPC_NTOPENPROCESSTOKEN_TAG: |
- case IPC_NTOPENPROCESSTOKENEX_TAG: |
- case IPC_CREATETHREAD_TAG: |
- // There is no explicit policy for these services. |
- NOTREACHED(); |
- return false; |
- |
- case IPC_CREATEPROCESSW_TAG: |
- return INTERCEPT_EAT(manager, kKerneldllName, CreateProcessW, |
- CREATE_PROCESSW_ID, 44) && |
- INTERCEPT_EAT(manager, L"kernel32.dll", CreateProcessA, |
- CREATE_PROCESSA_ID, 44); |
- |
- default: |
- return false; |
- } |
-} |
- |
-bool ThreadProcessDispatcher::NtOpenThread(IPCInfo* ipc, |
- uint32_t desired_access, |
- uint32_t thread_id) { |
- HANDLE handle; |
- NTSTATUS ret = ProcessPolicy::OpenThreadAction(*ipc->client_info, |
- desired_access, thread_id, |
- &handle); |
- ipc->return_info.nt_status = ret; |
- ipc->return_info.handle = handle; |
- return true; |
-} |
- |
-bool ThreadProcessDispatcher::NtOpenProcess(IPCInfo* ipc, |
- uint32_t desired_access, |
- uint32_t process_id) { |
- HANDLE handle; |
- NTSTATUS ret = ProcessPolicy::OpenProcessAction(*ipc->client_info, |
- desired_access, process_id, |
- &handle); |
- ipc->return_info.nt_status = ret; |
- ipc->return_info.handle = handle; |
- return true; |
-} |
- |
-bool ThreadProcessDispatcher::NtOpenProcessToken(IPCInfo* ipc, |
- HANDLE process, |
- uint32_t desired_access) { |
- HANDLE handle; |
- NTSTATUS ret = ProcessPolicy::OpenProcessTokenAction(*ipc->client_info, |
- process, desired_access, |
- &handle); |
- ipc->return_info.nt_status = ret; |
- ipc->return_info.handle = handle; |
- return true; |
-} |
- |
-bool ThreadProcessDispatcher::NtOpenProcessTokenEx(IPCInfo* ipc, |
- HANDLE process, |
- uint32_t desired_access, |
- uint32_t attributes) { |
- HANDLE handle; |
- NTSTATUS ret = ProcessPolicy::OpenProcessTokenExAction(*ipc->client_info, |
- process, |
- desired_access, |
- attributes, &handle); |
- ipc->return_info.nt_status = ret; |
- ipc->return_info.handle = handle; |
- return true; |
-} |
- |
-bool ThreadProcessDispatcher::CreateProcessW(IPCInfo* ipc, base::string16* name, |
- base::string16* cmd_line, |
- base::string16* cur_dir, |
- CountedBuffer* info) { |
- if (sizeof(PROCESS_INFORMATION) != info->Size()) |
- return false; |
- |
- // Check if there is an application name. |
- base::string16 exe_name; |
- if (!name->empty()) |
- exe_name = *name; |
- else |
- exe_name = GetPathFromCmdLine(*cmd_line); |
- |
- if (IsPathRelative(exe_name)) { |
- if (!ConvertToAbsolutePath(*cur_dir, name->empty(), &exe_name)) { |
- // Cannot find the path. Maybe the file does not exist. |
- ipc->return_info.win32_result = ERROR_FILE_NOT_FOUND; |
- return true; |
- } |
- } |
- |
- const wchar_t* const_exe_name = exe_name.c_str(); |
- CountedParameterSet<NameBased> params; |
- params[NameBased::NAME] = ParamPickerMake(const_exe_name); |
- |
- EvalResult eval = policy_base_->EvalPolicy(IPC_CREATEPROCESSW_TAG, |
- params.GetBase()); |
- |
- PROCESS_INFORMATION* proc_info = |
- reinterpret_cast<PROCESS_INFORMATION*>(info->Buffer()); |
- // Here we force the app_name to be the one we used for the policy lookup. |
- // If our logic was wrong, at least we wont allow create a random process. |
- DWORD ret = ProcessPolicy::CreateProcessWAction(eval, *ipc->client_info, |
- exe_name, *cmd_line, |
- proc_info); |
- |
- ipc->return_info.win32_result = ret; |
- return true; |
-} |
- |
-bool ThreadProcessDispatcher::CreateThread(IPCInfo* ipc, |
- SIZE_T stack_size, |
- LPTHREAD_START_ROUTINE start_address, |
- LPVOID parameter, |
- DWORD creation_flags) { |
- if (!start_address) { |
- return false; |
- } |
- |
- HANDLE handle; |
- DWORD ret = ProcessPolicy::CreateThreadAction(*ipc->client_info, stack_size, |
- start_address, parameter, |
- creation_flags, NULL, &handle); |
- |
- ipc->return_info.nt_status = ret; |
- ipc->return_info.handle = handle; |
- return true; |
-} |
- |
-} // namespace sandbox |