Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(560)

Unified Diff: sandbox/src/interception.cc

Issue 10666018: Add eight more bits of entropy to the sandbox intercept trampoline (Closed) Base URL: https://src.chromium.org/svn/trunk/src/
Patch Set: Created 8 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | sandbox/src/target_process.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: sandbox/src/interception.cc
===================================================================
--- sandbox/src/interception.cc (revision 143815)
+++ sandbox/src/interception.cc (working copy)
@@ -27,6 +27,28 @@
const char kMapViewOfSectionName[] = "NtMapViewOfSection";
const char kUnmapViewOfSectionName[] = "NtUnmapViewOfSection";
+// Standard allocation granularity and page size for Windows.
+const size_t kAllocGranularity = 65536;
+const size_t kPageSize = 4096;
+
+// Find a random offset within 64k and aligned to ceil(log2(size)).
+size_t GetGranularAlignedRandomOffset(size_t size) {
+ CHECK_LE(size, kAllocGranularity);
+ unsigned int offset;
+
+ do {
+ rand_s(&offset);
+ offset &= (kAllocGranularity - 1);
+ } while (offset > (kAllocGranularity - size));
+
+ // Find an alignment between 64 and the page size (4096).
+ size_t align_size = kPageSize;
+ for (size_t new_size = align_size / 2; new_size >= size; new_size /= 2) {
+ align_size = new_size;
+ }
+ return offset & ~(align_size - 1);
+}
+
} // namespace
namespace sandbox {
@@ -360,15 +382,29 @@
ADD_NT_INTERCEPTION(NtUnmapViewOfSection, UNMAP_VIEW_OF_SECTION_ID, 12);
}
+ // Reserve a full 64k memory range in the child process.
+ HANDLE child = child_->Process();
+ BYTE* thunk_base = reinterpret_cast<BYTE*>(
+ ::VirtualAllocEx(child, NULL, kAllocGranularity,
+ MEM_RESERVE, PAGE_NOACCESS));
+
+ // Find an aligned, random location within the reserved range.
size_t thunk_bytes = interceptions_.size() * sizeof(ThunkData) +
sizeof(DllInterceptionData);
+ size_t thunk_offset = GetGranularAlignedRandomOffset(thunk_bytes);
- // Allocate memory on the child, without specifying the desired address
- HANDLE child = child_->Process();
+ // Split the base and offset along page boundaries.
+ thunk_base += thunk_offset & ~(kPageSize - 1);
+ thunk_offset &= kPageSize - 1;
+
+ // Make an aligned, padded allocation, and move the pointer to our chunk.
+ size_t thunk_bytes_padded = (thunk_bytes + kPageSize - 1) & kPageSize;
+ thunk_base = reinterpret_cast<BYTE*>(
+ ::VirtualAllocEx(child, thunk_base, thunk_bytes_padded,
+ MEM_COMMIT, PAGE_EXECUTE_READWRITE));
+ CHECK(thunk_base); // If this fails we'd crash anyway on an invalid access.
DllInterceptionData* thunks = reinterpret_cast<DllInterceptionData*>(
- ::VirtualAllocEx(child, NULL, thunk_bytes,
- MEM_COMMIT,
- PAGE_EXECUTE_READWRITE));
+ thunk_base + thunk_offset);
DllInterceptionData dll_data;
dll_data.data_bytes = thunk_bytes;
« no previous file with comments | « no previous file | sandbox/src/target_process.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698