1// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#include "sandbox/win/src/sync_interception.h" 6 7#include "sandbox/win/src/crosscall_client.h" 8#include "sandbox/win/src/ipc_tags.h" 9#include "sandbox/win/src/policy_params.h" 10#include "sandbox/win/src/policy_target.h" 11#include "sandbox/win/src/sandbox_factory.h" 12#include "sandbox/win/src/sandbox_nt_util.h" 13#include "sandbox/win/src/sharedmem_ipc_client.h" 14#include "sandbox/win/src/target_services.h" 15 16namespace sandbox { 17 18ResultCode ProxyCreateEvent(LPCWSTR name, 19 BOOL initial_state, 20 EVENT_TYPE event_type, 21 void* ipc_memory, 22 CrossCallReturn* answer) { 23 CountedParameterSet<NameBased> params; 24 params[NameBased::NAME] = ParamPickerMake(name); 25 26 if (!QueryBroker(IPC_CREATEEVENT_TAG, params.GetBase())) 27 return SBOX_ERROR_GENERIC; 28 29 SharedMemIPCClient ipc(ipc_memory); 30 ResultCode code = CrossCall(ipc, IPC_CREATEEVENT_TAG, name, event_type, 31 initial_state, answer); 32 return code; 33} 34 35ResultCode ProxyOpenEvent(LPCWSTR name, 36 ACCESS_MASK desired_access, 37 void* ipc_memory, 38 CrossCallReturn* answer) { 39 CountedParameterSet<OpenEventParams> params; 40 params[OpenEventParams::NAME] = ParamPickerMake(name); 41 params[OpenEventParams::ACCESS] = ParamPickerMake(desired_access); 42 43 if (!QueryBroker(IPC_OPENEVENT_TAG, params.GetBase())) 44 return SBOX_ERROR_GENERIC; 45 46 SharedMemIPCClient ipc(ipc_memory); 47 ResultCode code = CrossCall(ipc, IPC_OPENEVENT_TAG, name, desired_access, 48 answer); 49 50 return code; 51} 52 53NTSTATUS WINAPI TargetNtCreateEvent(NtCreateEventFunction orig_CreateEvent, 54 PHANDLE event_handle, 55 ACCESS_MASK desired_access, 56 POBJECT_ATTRIBUTES object_attributes, 57 EVENT_TYPE event_type, 58 BOOLEAN initial_state) { 59 NTSTATUS status = orig_CreateEvent(event_handle, desired_access, 60 object_attributes, event_type, 61 initial_state); 62 if (status != STATUS_ACCESS_DENIED || !object_attributes) 63 return status; 64 65 // We don't trust that the IPC can work this early. 66 if (!SandboxFactory::GetTargetServices()->GetState()->InitCalled()) 67 return status; 68 69 do { 70 if (!ValidParameter(event_handle, sizeof(HANDLE), WRITE)) 71 break; 72 73 void* memory = GetGlobalIPCMemory(); 74 if (memory == NULL) 75 break; 76 77 OBJECT_ATTRIBUTES object_attribs_copy = *object_attributes; 78 // The RootDirectory points to BaseNamedObjects. We can ignore it. 79 object_attribs_copy.RootDirectory = NULL; 80 81 wchar_t* name = NULL; 82 uint32 attributes = 0; 83 NTSTATUS ret = AllocAndCopyName(&object_attribs_copy, &name, &attributes, 84 NULL); 85 if (!NT_SUCCESS(ret) || name == NULL) 86 break; 87 88 CrossCallReturn answer = {0}; 89 answer.nt_status = status; 90 ResultCode code = ProxyCreateEvent(name, initial_state, event_type, memory, 91 &answer); 92 operator delete(name, NT_ALLOC); 93 94 if (code != SBOX_ALL_OK) { 95 status = answer.nt_status; 96 break; 97 } 98 __try { 99 *event_handle = answer.handle; 100 status = STATUS_SUCCESS; 101 } __except(EXCEPTION_EXECUTE_HANDLER) { 102 break; 103 } 104 } while (false); 105 106 return status; 107} 108 109NTSTATUS WINAPI TargetNtOpenEvent(NtOpenEventFunction orig_OpenEvent, 110 PHANDLE event_handle, 111 ACCESS_MASK desired_access, 112 POBJECT_ATTRIBUTES object_attributes) { 113 NTSTATUS status = orig_OpenEvent(event_handle, desired_access, 114 object_attributes); 115 if (status != STATUS_ACCESS_DENIED || !object_attributes) 116 return status; 117 118 // We don't trust that the IPC can work this early. 119 if (!SandboxFactory::GetTargetServices()->GetState()->InitCalled()) 120 return status; 121 122 do { 123 if (!ValidParameter(event_handle, sizeof(HANDLE), WRITE)) 124 break; 125 126 void* memory = GetGlobalIPCMemory(); 127 if (memory == NULL) 128 break; 129 130 OBJECT_ATTRIBUTES object_attribs_copy = *object_attributes; 131 // The RootDirectory points to BaseNamedObjects. We can ignore it. 132 object_attribs_copy.RootDirectory = NULL; 133 134 wchar_t* name = NULL; 135 uint32 attributes = 0; 136 NTSTATUS ret = AllocAndCopyName(&object_attribs_copy, &name, &attributes, 137 NULL); 138 if (!NT_SUCCESS(ret) || name == NULL) 139 break; 140 141 CrossCallReturn answer = {0}; 142 answer.nt_status = status; 143 ResultCode code = ProxyOpenEvent(name, desired_access, memory, &answer); 144 operator delete(name, NT_ALLOC); 145 146 if (code != SBOX_ALL_OK) { 147 status = answer.nt_status; 148 break; 149 } 150 __try { 151 *event_handle = answer.handle; 152 status = STATUS_SUCCESS; 153 } __except(EXCEPTION_EXECUTE_HANDLER) { 154 break; 155 } 156 } while (false); 157 158 return status; 159} 160 161} // namespace sandbox 162