diff options
Diffstat (limited to 'src/osd/sdl/sdlos_win32.c')
-rw-r--r-- | src/osd/sdl/sdlos_win32.c | 71 |
1 files changed, 42 insertions, 29 deletions
diff --git a/src/osd/sdl/sdlos_win32.c b/src/osd/sdl/sdlos_win32.c index 31be832703b..2ffee467d11 100644 --- a/src/osd/sdl/sdlos_win32.c +++ b/src/osd/sdl/sdlos_win32.c @@ -180,36 +180,49 @@ void *osd_malloc(size_t size) #ifndef MALLOC_DEBUG return HeapAlloc(GetProcessHeap(), 0, size); #else - // add in space for the base pointer + // add in space for the size size += sizeof(size_t); - // small items just come from the heap - void *result; - if (size < GUARD_PAGE_THRESH) - result = HeapAlloc(GetProcessHeap(), 0, size); + // basic objects just come from the heap + void *result = HeapAlloc(GetProcessHeap(), 0, size); - // large items get guard pages - else - { - // round the size up to a page boundary - size_t rounded_size = ((size + sizeof(void *) + PAGE_SIZE - 1) / PAGE_SIZE) * PAGE_SIZE; + // store the size and return and pointer to the data afterward + *reinterpret_cast<size_t *>(result) = size; + return reinterpret_cast<UINT8 *>(result) + sizeof(size_t); +#endif +} - // reserve that much memory, plus two guard pages - void *page_base = VirtualAlloc(NULL, rounded_size + 2 * PAGE_SIZE, MEM_RESERVE, PAGE_NOACCESS); - if (page_base == NULL) - return NULL; - // now allow access to everything but the first and last pages - page_base = VirtualAlloc(reinterpret_cast<UINT8 *>(page_base) + PAGE_SIZE, rounded_size, MEM_COMMIT, PAGE_READWRITE); - if (page_base == NULL) - return NULL; +//============================================================ +// osd_malloc_array +//============================================================ - // work backwards from the page base to get to the block base - result = GUARD_ALIGN_START ? page_base : (reinterpret_cast<UINT8 *>(page_base) + rounded_size - size); - } +void *osd_malloc_array(size_t size) +{ +#ifndef MALLOC_DEBUG + return HeapAlloc(GetProcessHeap(), 0, size); +#else + // add in space for the size + size += sizeof(size_t); - // store the page_base at the start - *reinterpret_cast<size_t *>(result) = size; + // round the size up to a page boundary + size_t rounded_size = ((size + sizeof(void *) + PAGE_SIZE - 1) / PAGE_SIZE) * PAGE_SIZE; + + // reserve that much memory, plus two guard pages + void *page_base = VirtualAlloc(NULL, rounded_size + 2 * PAGE_SIZE, MEM_RESERVE, PAGE_NOACCESS); + if (page_base == NULL) + return NULL; + + // now allow access to everything but the first and last pages + page_base = VirtualAlloc(reinterpret_cast<UINT8 *>(page_base) + PAGE_SIZE, rounded_size, MEM_COMMIT, PAGE_READWRITE); + if (page_base == NULL) + return NULL; + + // work backwards from the page base to get to the block base + void *result = GUARD_ALIGN_START ? page_base : (reinterpret_cast<UINT8 *>(page_base) + rounded_size - size); + + // store the size at the start with a flag indicating it has a guard page + *reinterpret_cast<size_t *>(result) = size | 0x80000000; return reinterpret_cast<UINT8 *>(result) + sizeof(size_t); #endif } @@ -226,14 +239,14 @@ void osd_free(void *ptr) #else size_t size = reinterpret_cast<size_t *>(ptr)[-1]; - // small items just get freed - if (size < GUARD_PAGE_THRESH) + // if no guard page, just free the pointer + if ((size & 0x80000000) == 0) HeapFree(GetProcessHeap(), 0, reinterpret_cast<UINT8 *>(ptr) - sizeof(size_t)); // large items need more care else { - FPTR page_base = (reinterpret_cast<FPTR>(ptr) - sizeof(size_t)) & ~(PAGE_SIZE - 1); + ULONG_PTR page_base = (reinterpret_cast<ULONG_PTR>(ptr) - sizeof(size_t)) & ~(PAGE_SIZE - 1); VirtualFree(reinterpret_cast<void *>(page_base - PAGE_SIZE), 0, MEM_RELEASE); } #endif @@ -262,7 +275,7 @@ int osd_setenv(const char *name, const char *value, int overwrite) if (osd_getenv(name) != NULL) return 0; } - buf = (char *) osd_malloc(strlen(name)+strlen(value)+2); + buf = (char *) osd_malloc_array(strlen(name)+strlen(value)+2); sprintf(buf, "%s=%s", name, value); result = putenv(buf); @@ -371,7 +384,7 @@ CHAR *astring_from_utf8(const char *utf8string) // convert UTF-16 to "ANSI code page" string char_count = WideCharToMultiByte(CP_ACP, 0, wstring, -1, NULL, 0, NULL, NULL); - result = (CHAR *)osd_malloc(char_count * sizeof(*result)); + result = (CHAR *)osd_malloc_array(char_count * sizeof(*result)); if (result != NULL) WideCharToMultiByte(CP_ACP, 0, wstring, -1, result, char_count, NULL, NULL); @@ -389,7 +402,7 @@ WCHAR *wstring_from_utf8(const char *utf8string) // convert MAME string (UTF-8) to UTF-16 char_count = MultiByteToWideChar(CP_UTF8, 0, utf8string, -1, NULL, 0); - result = (WCHAR *)osd_malloc(char_count * sizeof(*result)); + result = (WCHAR *)osd_malloc_array(char_count * sizeof(*result)); if (result != NULL) MultiByteToWideChar(CP_UTF8, 0, utf8string, -1, result, char_count); |