diff --git a/dlls/kernel32/heap.c b/dlls/kernel32/heap.c index b526af0..5abe2d4 100644 --- a/dlls/kernel32/heap.c +++ b/dlls/kernel32/heap.c @@ -809,34 +809,47 @@ SIZE_T WINAPI GlobalSize(HGLOBAL hmem) if (!hmem) return 0; - if(ISPOINTER(hmem)) - { - retval=HeapSize(GetProcessHeap(), 0, (LPVOID) hmem); - } - else - { - RtlLockHeap(GetProcessHeap()); - pintern=HANDLE_TO_INTERN(hmem); + RtlLockHeap(GetProcessHeap()); - if(pintern->Magic==MAGIC_GLOBAL_USED) + __TRY + { + if(ISPOINTER(hmem)) { - if (!pintern->Pointer) /* handle case of GlobalAlloc( ??,0) */ - retval = 0; - else - { - retval = HeapSize(GetProcessHeap(), 0, - (char *)(pintern->Pointer) - HGLOBAL_STORAGE ); - if (retval != (DWORD)-1) retval -= HGLOBAL_STORAGE; - } + retval=HeapSize(GetProcessHeap(), 0, (LPVOID) hmem); } else { - WARN("invalid handle %p (Magic: 0x%04x)\n", hmem, pintern->Magic); - SetLastError(ERROR_INVALID_HANDLE); - retval=0; + pintern=HANDLE_TO_INTERN(hmem); + + if(pintern->Magic==MAGIC_GLOBAL_USED) + { + if (!pintern->Pointer) /* handle case of GlobalAlloc( ??,0) */ + retval = 0; + else + { + retval = HeapSize(GetProcessHeap(), 0, + (char *)(pintern->Pointer) - HGLOBAL_STORAGE ); + if (retval != (DWORD)-1) retval -= HGLOBAL_STORAGE; + } + } + else + { + WARN("invalid handle %p (Magic: 0x%04x)\n", hmem, pintern->Magic); + SetLastError(ERROR_INVALID_HANDLE); + retval=0; + } } - RtlUnlockHeap(GetProcessHeap()); } + __EXCEPT_PAGE_FAULT + { + /* handle was invalid, crashed on access to pintern->Magic */ + SetLastError(ERROR_INVALID_HANDLE); + retval = 0; + } + __ENDTRY + + RtlUnlockHeap(GetProcessHeap()); + /* HeapSize returns 0xffffffff on failure */ if (retval == 0xffffffff) retval = 0; return retval; diff --git a/dlls/kernel32/tests/heap.c b/dlls/kernel32/tests/heap.c old mode 100644 new mode 100755 index 34393e8..2939862 --- a/dlls/kernel32/tests/heap.c +++ b/dlls/kernel32/tests/heap.c @@ -197,6 +197,13 @@ START_TEST(heap) res = GlobalUnlock(gbl); ok(res == 1, "Expected 1, got %d\n", res); + /* GlobalSize on an invalid handle */ + SetLastError(MAGIC_DEAD); + size = GlobalSize((HGLOBAL)0xc042); + ok(size == 0, "Expected 0, got %ld\n", size); + ok(GetLastError() == ERROR_INVALID_HANDLE, + "Expected ERROR_INVALID_HANDLE, got %d\n", GetLastError()); + /* ####################################### */ /* Local*() functions */ gbl = LocalAlloc(LMEM_MOVEABLE, 0); -- 1.4.4.2