Fix heapapi ownership checks

`mi_heap_check_owned` does not work for allocations that span
multiple blocks; `mi_is_in_heap_region` is a less precise but
working way for us to check if a pointer is in our heap.

See https://github.com/microsoft/mimalloc/issues/298
This commit is contained in:
2025-10-27 15:18:38 -06:00
parent 27860f0300
commit 8bd15bd272
2 changed files with 7 additions and 3 deletions

View File

@@ -175,7 +175,7 @@ LPVOID WIN_FUNC HeapReAlloc(HANDLE hHeap, DWORD dwFlags, LPVOID lpMem, SIZE_T dw
VERBOSE_LOG("-> %p (alloc)\n", alloc); VERBOSE_LOG("-> %p (alloc)\n", alloc);
return alloc; return alloc;
} }
if (!mi_heap_check_owned(record->heap, lpMem)) { if (!mi_is_in_heap_region(lpMem)) {
VERBOSE_LOG("-> NULL (not owned)\n"); VERBOSE_LOG("-> NULL (not owned)\n");
wibo::lastError = ERROR_INVALID_PARAMETER; wibo::lastError = ERROR_INVALID_PARAMETER;
return nullptr; return nullptr;
@@ -244,7 +244,7 @@ SIZE_T WIN_FUNC HeapSize(HANDLE hHeap, DWORD dwFlags, LPCVOID lpMem) {
wibo::lastError = ERROR_INVALID_PARAMETER; wibo::lastError = ERROR_INVALID_PARAMETER;
return static_cast<SIZE_T>(-1); return static_cast<SIZE_T>(-1);
} }
if (!mi_heap_check_owned(record->heap, lpMem)) { if (!mi_is_in_heap_region(lpMem)) {
VERBOSE_LOG("-> ERROR_INVALID_PARAMETER (not owned)\n"); VERBOSE_LOG("-> ERROR_INVALID_PARAMETER (not owned)\n");
wibo::lastError = ERROR_INVALID_PARAMETER; wibo::lastError = ERROR_INVALID_PARAMETER;
return static_cast<SIZE_T>(-1); return static_cast<SIZE_T>(-1);
@@ -266,7 +266,7 @@ BOOL WIN_FUNC HeapFree(HANDLE hHeap, DWORD dwFlags, LPVOID lpMem) {
wibo::lastError = ERROR_INVALID_HANDLE; wibo::lastError = ERROR_INVALID_HANDLE;
return FALSE; return FALSE;
} }
if (!mi_heap_check_owned(record->heap, lpMem)) { if (!mi_is_in_heap_region(lpMem)) {
VERBOSE_LOG("-> ERROR_INVALID_PARAMETER (not owned)\n"); VERBOSE_LOG("-> ERROR_INVALID_PARAMETER (not owned)\n");
wibo::lastError = ERROR_INVALID_PARAMETER; wibo::lastError = ERROR_INVALID_PARAMETER;
return FALSE; return FALSE;

View File

@@ -42,8 +42,12 @@ int main(void) {
TEST_CHECK(privateBlock != NULL); TEST_CHECK(privateBlock != NULL);
SetLastError(0); SetLastError(0);
// Disabled temporarily; no good way to detect individual heap allocations
// in mimalloc currently. See https://github.com/microsoft/mimalloc/issues/298
#if 0
TEST_CHECK(!HeapFree(processHeap, 0, privateBlock)); TEST_CHECK(!HeapFree(processHeap, 0, privateBlock));
TEST_CHECK_EQ(ERROR_INVALID_PARAMETER, GetLastError()); TEST_CHECK_EQ(ERROR_INVALID_PARAMETER, GetLastError());
#endif
TEST_CHECK(HeapFree(privateHeap, 0, privateBlock)); TEST_CHECK(HeapFree(privateHeap, 0, privateBlock));
TEST_CHECK(HeapDestroy(privateHeap)); TEST_CHECK(HeapDestroy(privateHeap));