mmap, but ehh virtualquery...

This commit is contained in:
Ben Vanik 2014-08-01 21:43:52 -07:00
parent 4ad7662ef7
commit 3f2baafb4b
1 changed files with 34 additions and 15 deletions

View File

@ -158,12 +158,19 @@ int XenonMemory::Initialize() {
// Create main page file-backed mapping. This is all reserved but // Create main page file-backed mapping. This is all reserved but
// uncommitted (so it shouldn't expand page file). // uncommitted (so it shouldn't expand page file).
#if XE_PLATFORM_WIN32
mapping_ = CreateFileMapping( mapping_ = CreateFileMapping(
INVALID_HANDLE_VALUE, INVALID_HANDLE_VALUE,
NULL, NULL,
PAGE_READWRITE | SEC_RESERVE, PAGE_READWRITE | SEC_RESERVE,
1, 0, // entire 4gb space 1, 0, // entire 4gb space
NULL); NULL);
#else
char mapping_path[] = "/xenia/mapping/XXXXXX";
mktemp(mapping_path);
mapping_ = shm_open(mapping_path, O_CREAT, 0);
ftruncate(mapping_, 0x100000000);
#endif // XE_PLATFORM_WIN32
if (!mapping_) { if (!mapping_) {
XELOGE("Unable to reserve the 4gb guest address space."); XELOGE("Unable to reserve the 4gb guest address space.");
assert_not_null(mapping_); assert_not_null(mapping_);
@ -221,27 +228,34 @@ XECLEANUP:
return result; return result;
} }
const static struct {
uint64_t virtual_address_start;
uint64_t virtual_address_end;
uint64_t target_address;
} map_info[] = {
0x00000000, 0x3FFFFFFF, 0x00000000, // (1024mb) - virtual 4k pages
0x40000000, 0x7FFFFFFF, 0x40000000, // (1024mb) - virtual 64k pages
0x80000000, 0x9FFFFFFF, 0x80000000, // (512mb) - xex pages
0xA0000000, 0xBFFFFFFF, 0x00000000, // (512mb) - physical 64k pages
0xC0000000, 0xDFFFFFFF, 0x00000000, // - physical 16mb pages
0xE0000000, 0xFFFFFFFF, 0x00000000, // - physical 4k pages
};
int XenonMemory::MapViews(uint8_t* mapping_base) { int XenonMemory::MapViews(uint8_t* mapping_base) {
static struct {
uint64_t virtual_address_start;
uint64_t virtual_address_end;
uint64_t target_address;
} map_info[] = {
0x00000000, 0x3FFFFFFF, 0x00000000, // (1024mb) - virtual 4k pages
0x40000000, 0x7FFFFFFF, 0x40000000, // (1024mb) - virtual 64k pages
0x80000000, 0x9FFFFFFF, 0x80000000, // (512mb) - xex pages
0xA0000000, 0xBFFFFFFF, 0x00000000, // (512mb) - physical 64k pages
0xC0000000, 0xDFFFFFFF, 0x00000000, // - physical 16mb pages
0xE0000000, 0xFFFFFFFF, 0x00000000, // - physical 4k pages
};
assert_true(XECOUNT(map_info) == XECOUNT(views_.all_views)); assert_true(XECOUNT(map_info) == XECOUNT(views_.all_views));
for (size_t n = 0; n < XECOUNT(map_info); n++) { for (size_t n = 0; n < XECOUNT(map_info); n++) {
views_.all_views[n] = (uint8_t*)MapViewOfFileEx( #if XE_PLATFORM_WIN32
views_.all_views[n] = reinterpret_cast<uint8_t*>(MapViewOfFileEx(
mapping_, mapping_,
FILE_MAP_ALL_ACCESS, FILE_MAP_ALL_ACCESS,
0x00000000, (DWORD)map_info[n].target_address, 0x00000000, (DWORD)map_info[n].target_address,
map_info[n].virtual_address_end - map_info[n].virtual_address_start + 1, map_info[n].virtual_address_end - map_info[n].virtual_address_start + 1,
mapping_base + map_info[n].virtual_address_start); mapping_base + map_info[n].virtual_address_start));
#else
views_.all_views[n] = reinterpret_cast<uint8_t*>(mmap(
map_info[n].virtual_address_start + mapping_base,
map_info[n].virtual_address_end - map_info[n].virtual_address_start + 1,
PROT_NONE, MAP_SHARED | MAP_FIXED, mapping_, map_info[n].target_address));
#endif // XE_PLATFORM_WIN32
XEEXPECTNOTNULL(views_.all_views[n]); XEEXPECTNOTNULL(views_.all_views[n]);
} }
return 0; return 0;
@ -254,7 +268,12 @@ XECLEANUP:
void XenonMemory::UnmapViews() { void XenonMemory::UnmapViews() {
for (size_t n = 0; n < XECOUNT(views_.all_views); n++) { for (size_t n = 0; n < XECOUNT(views_.all_views); n++) {
if (views_.all_views[n]) { if (views_.all_views[n]) {
#if XE_PLATFORM_WIN32
UnmapViewOfFile(views_.all_views[n]); UnmapViewOfFile(views_.all_views[n]);
#else
size_t length = map_info[n].virtual_address_end - map_info[n].virtual_address_start + 1;
munmap(views_.all_views[n], length);
#endif // XE_PLATFORM_WIN32
} }
} }
} }
@ -404,7 +423,7 @@ size_t XenonMemory::QuerySize(uint64_t base_address) {
base_address < XENON_MEMORY_PHYSICAL_HEAP_HIGH) { base_address < XENON_MEMORY_PHYSICAL_HEAP_HIGH) {
return physical_heap_->QuerySize(base_address); return physical_heap_->QuerySize(base_address);
} else { } else {
// A placed address. Decommit. // A placed address.
uint8_t* p = Translate(base_address); uint8_t* p = Translate(base_address);
MEMORY_BASIC_INFORMATION mem_info; MEMORY_BASIC_INFORMATION mem_info;
if (VirtualQuery(p, &mem_info, sizeof(mem_info))) { if (VirtualQuery(p, &mem_info, sizeof(mem_info))) {