OLD | NEW |
| (Empty) |
1 // Copyright (c) 2006-2010 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/eat_resolver.h" | |
6 | |
7 #include <stddef.h> | |
8 | |
9 #include "base/win/pe_image.h" | |
10 #include "sandbox/win/src/sandbox_nt_util.h" | |
11 | |
12 namespace sandbox { | |
13 | |
14 NTSTATUS EatResolverThunk::Setup(const void* target_module, | |
15 const void* interceptor_module, | |
16 const char* target_name, | |
17 const char* interceptor_name, | |
18 const void* interceptor_entry_point, | |
19 void* thunk_storage, | |
20 size_t storage_bytes, | |
21 size_t* storage_used) { | |
22 NTSTATUS ret = Init(target_module, interceptor_module, target_name, | |
23 interceptor_name, interceptor_entry_point, | |
24 thunk_storage, storage_bytes); | |
25 if (!NT_SUCCESS(ret)) | |
26 return ret; | |
27 | |
28 if (!eat_entry_) | |
29 return STATUS_INVALID_PARAMETER; | |
30 | |
31 #if defined(_WIN64) | |
32 // We have two thunks, in order: the return path and the forward path. | |
33 if (!SetInternalThunk(thunk_storage, storage_bytes, NULL, target_)) | |
34 return STATUS_BUFFER_TOO_SMALL; | |
35 | |
36 size_t thunk_bytes = GetInternalThunkSize(); | |
37 storage_bytes -= thunk_bytes; | |
38 thunk_storage = reinterpret_cast<char*>(thunk_storage) + thunk_bytes; | |
39 #endif | |
40 | |
41 if (!SetInternalThunk(thunk_storage, storage_bytes, target_, interceptor_)) | |
42 return STATUS_BUFFER_TOO_SMALL; | |
43 | |
44 AutoProtectMemory memory; | |
45 ret = memory.ChangeProtection(eat_entry_, sizeof(DWORD), PAGE_READWRITE); | |
46 if (!NT_SUCCESS(ret)) | |
47 return ret; | |
48 | |
49 // Perform the patch. | |
50 *eat_entry_ = static_cast<DWORD>(reinterpret_cast<uintptr_t>(thunk_storage)) - | |
51 static_cast<DWORD>(reinterpret_cast<uintptr_t>(target_module)); | |
52 | |
53 if (NULL != storage_used) | |
54 *storage_used = GetThunkSize(); | |
55 | |
56 return ret; | |
57 } | |
58 | |
59 NTSTATUS EatResolverThunk::ResolveTarget(const void* module, | |
60 const char* function_name, | |
61 void** address) { | |
62 DCHECK_NT(address); | |
63 if (!module) | |
64 return STATUS_INVALID_PARAMETER; | |
65 | |
66 base::win::PEImage pe(module); | |
67 if (!pe.VerifyMagic()) | |
68 return STATUS_INVALID_IMAGE_FORMAT; | |
69 | |
70 eat_entry_ = pe.GetExportEntry(function_name); | |
71 | |
72 if (!eat_entry_) | |
73 return STATUS_PROCEDURE_NOT_FOUND; | |
74 | |
75 *address = pe.RVAToAddr(*eat_entry_); | |
76 | |
77 return STATUS_SUCCESS; | |
78 } | |
79 | |
80 size_t EatResolverThunk::GetThunkSize() const { | |
81 #if defined(_WIN64) | |
82 return GetInternalThunkSize() * 2; | |
83 #else | |
84 return GetInternalThunkSize(); | |
85 #endif | |
86 } | |
87 | |
88 } // namespace sandbox | |
OLD | NEW |