mirror of
https://github.com/holub/mame
synced 2025-06-07 13:23:50 +03:00
Align memory with MALLOC_DEBUG (nw)
This commit is contained in:
parent
454895659e
commit
eb38a7ad25
@ -36,6 +36,16 @@
|
|||||||
// align allocations to start or end of the page?
|
// align allocations to start or end of the page?
|
||||||
#define GUARD_ALIGN_START 0
|
#define GUARD_ALIGN_START 0
|
||||||
|
|
||||||
|
#if defined(__BIGGEST_ALIGNMENT__)
|
||||||
|
#define MAX_ALIGNMENT __BIGGEST_ALIGNMENT__
|
||||||
|
#elif defined(__AVX__)
|
||||||
|
#define MAX_ALIGNMENT 32
|
||||||
|
#elif defined(__SSE__) || defined(__x86_64__) || defined(_M_X64)
|
||||||
|
#define MAX_ALIGNMENT 16
|
||||||
|
#else
|
||||||
|
#define MAX_ALIGNMENT sizeof(INT64)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// GLOBAL VARIABLES
|
// GLOBAL VARIABLES
|
||||||
@ -114,15 +124,20 @@ void *osd_malloc(size_t size)
|
|||||||
#ifndef MALLOC_DEBUG
|
#ifndef MALLOC_DEBUG
|
||||||
return malloc(size);
|
return malloc(size);
|
||||||
#else
|
#else
|
||||||
// add in space for the size
|
// add in space for the size and offset
|
||||||
size += sizeof(size_t);
|
size += MAX_ALIGNMENT + sizeof(size_t) + 2;
|
||||||
|
size &= ~size_t(1);
|
||||||
|
|
||||||
// basic objects just come from the heap
|
// basic objects just come from the heap
|
||||||
void *result = HeapAlloc(GetProcessHeap(), 0, size);
|
UINT8 *const block = reinterpret_cast<UINT8 *>(HeapAlloc(GetProcessHeap(), 0, size));
|
||||||
|
if (block == NULL)
|
||||||
|
return NULL;
|
||||||
|
UINT8 *const result = reinterpret_cast<UINT8 *>(reinterpret_cast<FPTR>(block + sizeof(size_t) + MAX_ALIGNMENT) & ~(FPTR(MAX_ALIGNMENT) - 1));
|
||||||
|
|
||||||
// store the size and return and pointer to the data afterward
|
// store the size and return and pointer to the data afterward
|
||||||
*reinterpret_cast<size_t *>(result) = size;
|
*reinterpret_cast<size_t *>(block) = size;
|
||||||
return reinterpret_cast<UINT8 *>(result) + sizeof(size_t);
|
*(result - 1) = result - block;
|
||||||
|
return result;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -136,11 +151,12 @@ void *osd_malloc_array(size_t size)
|
|||||||
#ifndef MALLOC_DEBUG
|
#ifndef MALLOC_DEBUG
|
||||||
return malloc(size);
|
return malloc(size);
|
||||||
#else
|
#else
|
||||||
// add in space for the size
|
// add in space for the size and offset
|
||||||
size += sizeof(size_t);
|
size += MAX_ALIGNMENT + sizeof(size_t) + 2;
|
||||||
|
size &= ~size_t(1);
|
||||||
|
|
||||||
// round the size up to a page boundary
|
// round the size up to a page boundary
|
||||||
size_t rounded_size = ((size + sizeof(void *) + PAGE_SIZE - 1) / PAGE_SIZE) * PAGE_SIZE;
|
size_t const rounded_size = ((size + sizeof(void *) + PAGE_SIZE - 1) / PAGE_SIZE) * PAGE_SIZE;
|
||||||
|
|
||||||
// reserve that much memory, plus two guard pages
|
// reserve that much memory, plus two guard pages
|
||||||
void *page_base = VirtualAlloc(NULL, rounded_size + 2 * PAGE_SIZE, MEM_RESERVE, PAGE_NOACCESS);
|
void *page_base = VirtualAlloc(NULL, rounded_size + 2 * PAGE_SIZE, MEM_RESERVE, PAGE_NOACCESS);
|
||||||
@ -153,11 +169,13 @@ void *osd_malloc_array(size_t size)
|
|||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
// work backwards from the page base to get to the block base
|
// 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);
|
UINT8 *const block = GUARD_ALIGN_START ? reinterpret_cast<UINT8 *>(page_base) : (reinterpret_cast<UINT8 *>(page_base) + rounded_size - size);
|
||||||
|
UINT8 *const result = reinterpret_cast<UINT8 *>(reinterpret_cast<FPTR>(block + sizeof(size_t) + MAX_ALIGNMENT) & ~(FPTR(MAX_ALIGNMENT) - 1));
|
||||||
|
|
||||||
// store the size at the start with a flag indicating it has a guard page
|
// store the size at the start with a flag indicating it has a guard page
|
||||||
*reinterpret_cast<size_t *>(result) = size | 0x80000000;
|
*reinterpret_cast<size_t *>(block) = size | 1;
|
||||||
return reinterpret_cast<UINT8 *>(result) + sizeof(size_t);
|
*(result - 1) = result - block;
|
||||||
|
return result;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -171,16 +189,19 @@ void osd_free(void *ptr)
|
|||||||
#ifndef MALLOC_DEBUG
|
#ifndef MALLOC_DEBUG
|
||||||
free(ptr);
|
free(ptr);
|
||||||
#else
|
#else
|
||||||
size_t size = reinterpret_cast<size_t *>(ptr)[-1];
|
UINT8 const offset = *(reinterpret_cast<UINT8 *>(ptr) - 1);
|
||||||
|
UINT8 *const block = reinterpret_cast<UINT8 *>(ptr) - offset;
|
||||||
|
size_t const size = *reinterpret_cast<size_t *>(block);
|
||||||
|
|
||||||
// if no guard page, just free the pointer
|
if ((size & 0x1) == 0)
|
||||||
if ((size & 0x80000000) == 0)
|
{
|
||||||
HeapFree(GetProcessHeap(), 0, reinterpret_cast<UINT8 *>(ptr) - sizeof(size_t));
|
// if no guard page, just free the pointer
|
||||||
|
HeapFree(GetProcessHeap(), 0, block);
|
||||||
// large items need more care
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ULONG_PTR page_base = (reinterpret_cast<ULONG_PTR>(ptr) - sizeof(size_t)) & ~(PAGE_SIZE - 1);
|
// large items need more care
|
||||||
|
ULONG_PTR const page_base = reinterpret_cast<ULONG_PTR>(block) & ~(PAGE_SIZE - 1);
|
||||||
VirtualFree(reinterpret_cast<void *>(page_base - PAGE_SIZE), 0, MEM_RELEASE);
|
VirtualFree(reinterpret_cast<void *>(page_base - PAGE_SIZE), 0, MEM_RELEASE);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
Reference in New Issue
Block a user