Changeset 46739 in vbox for trunk/src/VBox/Runtime
- Timestamp:
- Jun 23, 2013 4:10:25 PM (12 years ago)
- Location:
- trunk/src/VBox/Runtime
- Files:
-
- 1 added
- 3 edited
- 2 copied
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Runtime/Makefile.kmk
r46646 r46739 494 494 r3/alloc-ef.cpp \ 495 495 r3/alloc.cpp \ 496 r3/allocex.cpp \ 496 497 r3/dir.cpp \ 497 498 r3/dir2.cpp \ … … 582 583 generic/RTThreadGetNativeState-generic.cpp \ 583 584 nt/RTErrConvertFromNtStatus.cpp \ 584 r3/generic/allocex-r3-generic.cpp \585 585 r3/posix/env-posix.cpp \ 586 586 r3/win/RTHandleGetStandard-win.cpp \ … … 590 590 r3/win/RTSystemQueryTotalRam-win.cpp \ 591 591 r3/win/alloc-win.cpp \ 592 r3/win/allocex-win.cpp \ 592 593 r3/win/dir-win.cpp \ 593 594 r3/win/errvars-win.cpp \ -
trunk/src/VBox/Runtime/r3/allocex.cpp
r46729 r46739 36 36 #include <iprt/string.h> 37 37 #include "internal/magics.h" 38 39 #include <sys/mman.h> 40 41 42 /******************************************************************************* 43 * Structures and Typedefs * 44 *******************************************************************************/ 45 /** 46 * Heading for extended memory allocations in ring-3. 47 */ 48 typedef struct RTMEMHDRR3 49 { 50 /** Magic (RTMEMHDR_MAGIC). */ 51 uint32_t u32Magic; 52 /** Block flags (RTMEMALLOCEX_FLAGS_*). */ 53 uint32_t fFlags; 54 /** The actual size of the block, header not included. */ 55 uint32_t cb; 56 /** The requested allocation size. */ 57 uint32_t cbReq; 58 } RTMEMHDRR3; 59 /** Pointer to a ring-3 extended memory header. */ 60 typedef RTMEMHDRR3 *PRTMEMHDRR3; 61 62 63 /** 64 * Allocates memory with upper boundrary. 65 * 66 * @returns Pointer to mmap allocation. 67 * @param cbAlloc Number of bytes to alloacate. 68 * @param fFlags Allocation flags. 69 */ 70 static void *rtMemAllocExAllocLow(size_t cbAlloc, uint32_t fFlags) 71 { 72 int fProt = PROT_READ | PROT_WRITE | (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PROT_EXEC : 0); 73 void *pv = NULL; 74 if (fFlags & RTMEMALLOCEX_FLAGS_16BIT_REACH) 75 { 76 AssertReturn(cbAlloc < _64K, NULL); 77 78 /* 79 * Try with every possible address hint since the possible range is very limited. 80 */ 81 uintptr_t uAddr = fFlags & RTMEMALLOCEX_FLAGS_16BIT_REACH ? 0x1000 : _1M; 82 uintptr_t uAddrLast = _64K - uAddr - cbAlloc; 83 while (uAddr <= uAddrLast) 84 { 85 pv = mmap((void *)uAddr, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 86 if (pv && (uintptr_t)pv <= uAddrLast) 87 break; 88 if (pv) 89 { 90 munmap(pv, cbAlloc); 91 pv = NULL; 92 } 93 uAddr += _4K; 94 } 95 } 96 else 97 { 98 #if ARCH_BITS == 32 99 pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 100 101 #elif defined(RT_OS_LINUX) 102 # ifdef MAP_32BIT 103 pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS | MAP_32BIT, -1, 0); 104 if (pv) 105 return pv; 106 # endif 107 108 /** @todo On linux, we need an accurate hint. Since I don't need this branch of 109 * the code right now, I won't bother starting to parse 110 * /proc/curproc/mmap right now... */ 111 pv = NULL; 112 #else 113 pv = NULL; 114 #endif 115 } 116 return pv; 117 } 38 #include "allocex.h" 118 39 119 40 … … 147 68 void *pv; 148 69 if (fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH)) 149 pv = rtMemAllocExAllocLow(cbAligned + sizeof(RTMEMHDRR3), fFlags); 70 { 71 int rc; 72 if (fFlags & RTMEMALLOCEX_FLAGS_16BIT_REACH) 73 rc = rtMemAllocEx16BitReach(cbAligned + sizeof(RTMEMHDRR3), fFlags, &pv); 74 else 75 rc = rtMemAllocEx32BitReach(cbAligned + sizeof(RTMEMHDRR3), fFlags, &pv); 76 if (RT_FAILURE(rc)) 77 return rc; 78 } 150 79 else if (fFlags & RTMEMALLOCEX_FLAGS_EXEC) 151 80 { … … 167 96 pHdr->u32Magic = RTMEMHDR_MAGIC; 168 97 pHdr->fFlags = fFlags; 169 pHdr->cb = cbAligned;170 pHdr->cbReq = cb;98 pHdr->cb = (uint32_t)cbAligned; 99 pHdr->cbReq = (uint32_t)cb; 171 100 172 101 *ppv = pHdr + 1; … … 188 117 189 118 if (pHdr->fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH)) 190 munmap(pHdr, pHdr->cb + sizeof(*pHdr));119 rtMemFreeExYyBitReach(pHdr, pHdr->cb + sizeof(*pHdr), pHdr->fFlags); 191 120 else if (pHdr->fFlags & RTMEMALLOCEX_FLAGS_EXEC) 192 121 RTMemExecFree(pHdr, pHdr->cb + sizeof(*pHdr)); -
trunk/src/VBox/Runtime/r3/generic/allocex-r3-generic.cpp
r46568 r46739 1 1 /* $Id$ */ 2 2 /** @file 3 * IPRT - Memory Allocation, Extended Alloc and Free Functions for Ring-3, generic.3 * IPRT - Memory Allocation, Extended Alloc Workers, generic. 4 4 */ 5 5 … … 34 34 35 35 #include <iprt/assert.h> 36 #include <iprt/string.h> 37 #include "internal/magics.h" 38 39 40 /******************************************************************************* 41 * Structures and Typedefs * 42 *******************************************************************************/ 43 /** 44 * Heading for extended memory allocations in ring-3. 45 */ 46 typedef struct RTMEMHDRR3 47 { 48 /** Magic (RTMEMHDR_MAGIC). */ 49 uint32_t u32Magic; 50 /** Block flags (RTMEMALLOCEX_FLAGS_*). */ 51 uint32_t fFlags; 52 /** The actual size of the block, header not included. */ 53 uint32_t cb; 54 /** The requested allocation size. */ 55 uint32_t cbReq; 56 } RTMEMHDRR3; 57 /** Pointer to a ring-3 extended memory header. */ 58 typedef RTMEMHDRR3 *PRTMEMHDRR3; 36 #include "../allocex-r3.h" 59 37 60 38 61 39 62 RTDECL(int) RTMemAllocExTag(size_t cb, size_t cbAlignment, uint32_t fFlags, const char *pszTag, void **ppv) RT_NO_THROW 40 DECLHIDDEN(int) rtMemAllocEx16BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 63 41 { 64 /* 65 * Validate and adjust input. 66 */ 67 AssertMsgReturn(!(fFlags & ~RTMEMALLOCEX_FLAGS_VALID_MASK), ("%#x\n", fFlags), VERR_INVALID_PARAMETER); 68 AssertReturn(cb > 0, VERR_INVALID_PARAMETER); 69 AssertReturn(RT_IS_POWER_OF_TWO(cbAlignment), VERR_INVALID_PARAMETER); 70 AssertMsgReturn(cbAlignment <= sizeof(void *), ("%zu (%#x)\n", cbAlignment, cbAlignment), VERR_UNSUPPORTED_ALIGNMENT); 71 72 if (fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH | RTMEMALLOCEX_FLAGS_ANY_CTX)) 73 return VERR_NOT_SUPPORTED; 74 75 /* 76 * Align the request. 77 */ 78 size_t cbAligned = cb; 79 if (cbAlignment) 80 cbAligned = RT_ALIGN_Z(cb, cbAlignment); 81 else 82 cbAligned = RT_ALIGN_Z(cb, sizeof(uint64_t)); 83 AssertMsgReturn(cbAligned >= cb && cbAligned <= ~(size_t)0, ("cbAligned=%#zx cb=%#zx", cbAligned, cb), 84 VERR_INVALID_PARAMETER); 85 86 /* 87 * Allocate the requested memory. 88 */ 89 void *pv; 90 if (fFlags & RTMEMALLOCEX_FLAGS_EXEC) 91 { 92 pv = RTMemExecAlloc(cbAligned + sizeof(RTMEMHDRR3)); 93 if ((fFlags & RTMEMALLOCEX_FLAGS_ZEROED) && pv) 94 RT_BZERO(pv, cbAligned + sizeof(RTMEMHDRR3)); 95 } 96 else if (fFlags & RTMEMALLOCEX_FLAGS_ZEROED) 97 pv = RTMemAllocZ(cbAligned + sizeof(RTMEMHDRR3)); 98 else 99 pv = RTMemAlloc(cbAligned + sizeof(RTMEMHDRR3)); 100 if (!pv) 101 return VERR_NO_MEMORY; 102 103 /* 104 * Fill in the header and return. 105 */ 106 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv; 107 pHdr->u32Magic = RTMEMHDR_MAGIC; 108 pHdr->fFlags = fFlags; 109 pHdr->cb = (uint32_t)cbAligned; 110 pHdr->cbReq = (uint32_t)cb; 111 112 *ppv = pHdr + 1; 113 return VINF_SUCCESS; 42 return VERR_NOT_SUPPORTED; 114 43 } 115 RT_EXPORT_SYMBOL(RTMemAllocExTag);116 44 117 45 118 RTDECL(void) RTMemFreeEx(void *pv, size_t cb) RT_NO_THROW 46 DECLHIDDEN(int) rtMemAllocEx32BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 119 47 { 120 if (!pv) 121 return; 122 AssertPtr(pv); 48 return VERR_NOT_SUPPORTED; 49 } 123 50 124 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv - 1;125 AssertMsg(pHdr->u32Magic == RTMEMHDR_MAGIC, ("pHdr->u32Magic=%RX32 pv=%p cb=%#x\n", pHdr->u32Magic, pv, cb));126 pHdr->u32Magic = RTMEMHDR_MAGIC_DEAD;127 Assert(pHdr->cbReq == cb);128 51 129 if (pHdr->fFlags & RTMEMALLOCEX_FLAGS_EXEC) 130 RTMemExecFree(pHdr, pHdr->cb + sizeof(*pHdr)); 131 else 132 RTMemFree(pHdr); 52 DECLHIDDEN(void) rtMemFreeExYyBitReach(void *pv, size_t cb, uint32_t fFlags) 53 { 54 AssertFailed(); 133 55 } 134 RT_EXPORT_SYMBOL(RTMemFreeEx);135 56 -
trunk/src/VBox/Runtime/r3/posix/allocex-r3-posix.cpp
r46729 r46739 1 1 /* $Id$ */ 2 2 /** @file 3 * IPRT - Memory Allocation, Extended Alloc and Free Functions for Ring-3, posix.3 * IPRT - Memory Allocation, Extended Alloc Workers, posix. 4 4 */ 5 5 … … 35 35 #include <iprt/assert.h> 36 36 #include <iprt/string.h> 37 #include " internal/magics.h"37 #include "../allocex.h" 38 38 39 39 #include <sys/mman.h> 40 40 41 41 42 /******************************************************************************* 43 * Structures and Typedefs * 44 *******************************************************************************/ 45 /** 46 * Heading for extended memory allocations in ring-3. 47 */ 48 typedef struct RTMEMHDRR3 42 DECLHIDDEN(int) rtMemAllocEx16BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 49 43 { 50 /** Magic (RTMEMHDR_MAGIC). */ 51 uint32_t u32Magic; 52 /** Block flags (RTMEMALLOCEX_FLAGS_*). */ 53 uint32_t fFlags; 54 /** The actual size of the block, header not included. */ 55 uint32_t cb; 56 /** The requested allocation size. */ 57 uint32_t cbReq; 58 } RTMEMHDRR3; 59 /** Pointer to a ring-3 extended memory header. */ 60 typedef RTMEMHDRR3 *PRTMEMHDRR3; 44 AssertReturn(cbAlloc < _64K, NULL); 45 46 /* 47 * Try with every possible address hint since the possible range is very limited. 48 */ 49 int fProt = PROT_READ | PROT_WRITE | (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PROT_EXEC : 0); 50 uintptr_t uAddr = 0x1000; 51 uintptr_t uAddrLast = _64K - uAddr - cbAlloc; 52 while (uAddr <= uAddrLast) 53 { 54 void *pv = mmap((void *)uAddr, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 55 if (pv && (uintptr_t)pv <= uAddrLast) 56 { 57 *ppv = pv; 58 return VINF_SUCCESS; 59 } 60 61 if (pv) 62 { 63 munmap(pv, cbAlloc); 64 pv = NULL; 65 } 66 uAddr += _4K; 67 } 68 69 return VERR_NO_MEMORY; 70 } 61 71 62 72 63 /** 64 * Allocates memory with upper boundrary. 65 * 66 * @returns Pointer to mmap allocation. 67 * @param cbAlloc Number of bytes to alloacate. 68 * @param fFlags Allocation flags. 69 */ 70 static void *rtMemAllocExAllocLow(size_t cbAlloc, uint32_t fFlags) 73 DECLHIDDEN(int) rtMemAllocEx32BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 71 74 { 72 int fProt = PROT_READ | PROT_WRITE | (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PROT_EXEC : 0); 73 void *pv = NULL; 74 if (fFlags & RTMEMALLOCEX_FLAGS_16BIT_REACH) 75 int fProt = PROT_READ | PROT_WRITE | (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PROT_EXEC : 0); 76 #if ARCH_BITS == 32 77 void *pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 78 if (pv) 75 79 { 76 AssertReturn(cbAlloc < _64K, NULL); 77 78 /* 79 * Try with every possible address hint since the possible range is very limited. 80 */ 81 uintptr_t uAddr = fFlags & RTMEMALLOCEX_FLAGS_16BIT_REACH ? 0x1000 : _1M; 82 uintptr_t uAddrLast = _64K - uAddr - cbAlloc; 83 while (uAddr <= uAddrLast) 84 { 85 pv = mmap((void *)uAddr, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 86 if (pv && (uintptr_t)pv <= uAddrLast) 87 break; 88 if (pv) 89 { 90 munmap(pv, cbAlloc); 91 pv = NULL; 92 } 93 uAddr += _4K; 94 } 80 *ppv = pv; 81 return VINF_SUCCESS; 95 82 } 96 else 97 { 98 #if ARCH_BITS == 32 99 pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 83 return VERR_NO_MEMORY; 100 84 101 85 #elif defined(RT_OS_LINUX) 102 86 # ifdef MAP_32BIT 103 pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS | MAP_32BIT, -1, 0); 104 if (pv) 105 return pv; 87 void *pv = mmap(NULL, cbAlloc, fProt, MAP_PRIVATE | MAP_ANONYMOUS | MAP_32BIT, -1, 0); 88 if (pv) 89 { 90 *ppv = pv; 91 return VINF_SUCCESS; 92 } 106 93 # endif 107 94 108 /** @todo On linux, we need an accurate hint. Since I don't need this branch of 109 * the code right now, I won't bother starting to parse 110 * /proc/curproc/mmap right now... */ 111 pv = NULL; 95 /** @todo On linux, we need an accurate hint. Since I don't need this branch of 96 * the code right now, I won't bother starting to parse 97 * /proc/curproc/mmap right now... */ 112 98 #else 113 pv = NULL;114 99 #endif 115 } 116 return pv; 100 return VERR_NOT_SUPPORTED; 117 101 } 118 102 119 103 120 RTDECL(int) RTMemAllocExTag(size_t cb, size_t cbAlignment, uint32_t fFlags, const char *pszTag, void **ppv) RT_NO_THROW 104 DECLHIDDEN(void) rtMemFreeExYyBitReach(void *pv, size_t cb, uint32_t fFlags) 121 105 { 122 /* 123 * Validate and adjust input. 124 */ 125 AssertMsgReturn(!(fFlags & ~RTMEMALLOCEX_FLAGS_VALID_MASK), ("%#x\n", fFlags), VERR_INVALID_PARAMETER); 126 AssertReturn(cb > 0, VERR_INVALID_PARAMETER); 127 AssertReturn(RT_IS_POWER_OF_TWO(cbAlignment), VERR_INVALID_PARAMETER); 128 AssertMsgReturn(cbAlignment <= sizeof(void *), ("%zu (%#x)\n", cbAlignment, cbAlignment), VERR_UNSUPPORTED_ALIGNMENT); 106 munmap(pv, cb); 107 } 129 108 130 if (fFlags & RTMEMALLOCEX_FLAGS_ANY_CTX)131 return VERR_NOT_SUPPORTED;132 133 /*134 * Align the request.135 */136 size_t cbAligned = cb;137 if (cbAlignment)138 cbAligned = RT_ALIGN_Z(cb, cbAlignment);139 else140 cbAligned = RT_ALIGN_Z(cb, sizeof(uint64_t));141 AssertMsgReturn(cbAligned >= cb && cbAligned <= ~(size_t)0, ("cbAligned=%#zx cb=%#zx", cbAligned, cb),142 VERR_INVALID_PARAMETER);143 144 /*145 * Allocate the requested memory.146 */147 void *pv;148 if (fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH))149 pv = rtMemAllocExAllocLow(cbAligned + sizeof(RTMEMHDRR3), fFlags);150 else if (fFlags & RTMEMALLOCEX_FLAGS_EXEC)151 {152 pv = RTMemExecAlloc(cbAligned + sizeof(RTMEMHDRR3));153 if ((fFlags & RTMEMALLOCEX_FLAGS_ZEROED) && pv)154 RT_BZERO(pv, cbAligned + sizeof(RTMEMHDRR3));155 }156 else if (fFlags & RTMEMALLOCEX_FLAGS_ZEROED)157 pv = RTMemAllocZ(cbAligned + sizeof(RTMEMHDRR3));158 else159 pv = RTMemAlloc(cbAligned + sizeof(RTMEMHDRR3));160 if (!pv)161 return VERR_NO_MEMORY;162 163 /*164 * Fill in the header and return.165 */166 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv;167 pHdr->u32Magic = RTMEMHDR_MAGIC;168 pHdr->fFlags = fFlags;169 pHdr->cb = cbAligned;170 pHdr->cbReq = cb;171 172 *ppv = pHdr + 1;173 return VINF_SUCCESS;174 }175 RT_EXPORT_SYMBOL(RTMemAllocExTag);176 177 178 RTDECL(void) RTMemFreeEx(void *pv, size_t cb) RT_NO_THROW179 {180 if (!pv)181 return;182 AssertPtr(pv);183 184 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv - 1;185 AssertMsg(pHdr->u32Magic == RTMEMHDR_MAGIC, ("pHdr->u32Magic=%RX32 pv=%p cb=%#x\n", pHdr->u32Magic, pv, cb));186 pHdr->u32Magic = RTMEMHDR_MAGIC_DEAD;187 Assert(pHdr->cbReq == cb);188 189 if (pHdr->fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH))190 munmap(pHdr, pHdr->cb + sizeof(*pHdr));191 else if (pHdr->fFlags & RTMEMALLOCEX_FLAGS_EXEC)192 RTMemExecFree(pHdr, pHdr->cb + sizeof(*pHdr));193 else194 RTMemFree(pHdr);195 }196 RT_EXPORT_SYMBOL(RTMemFreeEx);197 -
trunk/src/VBox/Runtime/r3/win/allocex-win.cpp
r46729 r46739 1 1 /* $Id$ */ 2 2 /** @file 3 * IPRT - Memory Allocation, Extended Alloc and Free Functions for Ring-3, generic.3 * IPRT - Memory Allocation, Extended Alloc Workers, Windows. 4 4 */ 5 5 … … 35 35 #include <iprt/assert.h> 36 36 #include <iprt/string.h> 37 #include "internal/magics.h" 37 #include <iprt/param.h> 38 #include "../allocex.h" 39 40 #include <Windows.h> 38 41 39 42 40 /******************************************************************************* 41 * Structures and Typedefs * 42 *******************************************************************************/ 43 /** 44 * Heading for extended memory allocations in ring-3. 45 */ 46 typedef struct RTMEMHDRR3 43 static int rtMemAllocExInRange(size_t cbAlloc, uint32_t fFlags, void **ppv, uintptr_t uAddr, uintptr_t uAddrLast) 47 44 { 48 /** Magic (RTMEMHDR_MAGIC). */ 49 uint32_t u32Magic; 50 /** Block flags (RTMEMALLOCEX_FLAGS_*). */ 51 uint32_t fFlags; 52 /** The actual size of the block, header not included. */ 53 uint32_t cb; 54 /** The requested allocation size. */ 55 uint32_t cbReq; 56 } RTMEMHDRR3; 57 /** Pointer to a ring-3 extended memory header. */ 58 typedef RTMEMHDRR3 *PRTMEMHDRR3; 45 /* 46 * Try with every possible address hint since the possible range is very limited. 47 */ 48 DWORD fPageProt = (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PAGE_EXECUTE_READWRITE : PAGE_READWRITE); 49 while (uAddr <= uAddrLast) 50 { 51 MEMORY_BASIC_INFORMATION MemInfo; 52 SIZE_T cbRange = VirtualQuery((void *)uAddr, &MemInfo, sizeof(MemInfo)); 53 AssertReturn(cbRange == sizeof(MemInfo), VERR_NOT_SUPPORTED); 54 Assert(MemInfo.RegionSize > 0); 55 56 if ( MemInfo.State == MEM_FREE 57 && MemInfo.RegionSize >= cbAlloc) 58 { 59 void *pv = VirtualAlloc((void *)uAddr, cbAlloc, MEM_RESERVE | MEM_COMMIT, fPageProt); 60 if ((uintptr_t)pv == uAddr) 61 { 62 *ppv = pv; 63 return VINF_SUCCESS; 64 } 65 AssertStmt(!pv, VirtualFree(pv, cbAlloc, MEM_RELEASE)); 66 } 67 68 /* skip ahead */ 69 uintptr_t uAddrNext = (uintptr_t)MemInfo.BaseAddress + MemInfo.RegionSize; 70 if (uAddrNext <= uAddr) 71 break; 72 uAddr += uAddrNext; 73 } 74 75 return VERR_NO_MEMORY; 76 } 59 77 60 78 79 DECLHIDDEN(int) rtMemAllocEx16BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 80 { 81 cbAlloc = RT_ALIGN_Z(cbAlloc, PAGE_SIZE); 82 AssertReturn(cbAlloc <= _64K - PAGE_SIZE, VERR_NO_MEMORY); 61 83 62 RTDECL(int) RTMemAllocExTag(size_t cb, size_t cbAlignment, uint32_t fFlags, const char *pszTag, void **ppv) RT_NO_THROW 84 /* Seems this doesn't work on W7/64... */ 85 return rtMemAllocExInRange(cbAlloc, fFlags, ppv, PAGE_SIZE, _64K - cbAlloc); 86 } 87 88 89 DECLHIDDEN(int) rtMemAllocEx32BitReach(size_t cbAlloc, uint32_t fFlags, void **ppv) 63 90 { 64 /* 65 * Validate and adjust input. 66 */ 67 AssertMsgReturn(!(fFlags & ~RTMEMALLOCEX_FLAGS_VALID_MASK), ("%#x\n", fFlags), VERR_INVALID_PARAMETER); 68 AssertReturn(cb > 0, VERR_INVALID_PARAMETER); 69 AssertReturn(RT_IS_POWER_OF_TWO(cbAlignment), VERR_INVALID_PARAMETER); 70 AssertMsgReturn(cbAlignment <= sizeof(void *), ("%zu (%#x)\n", cbAlignment, cbAlignment), VERR_UNSUPPORTED_ALIGNMENT); 71 72 if (fFlags & (RTMEMALLOCEX_FLAGS_16BIT_REACH | RTMEMALLOCEX_FLAGS_32BIT_REACH | RTMEMALLOCEX_FLAGS_ANY_CTX)) 73 return VERR_NOT_SUPPORTED; 91 cbAlloc = RT_ALIGN_Z(cbAlloc, PAGE_SIZE); 92 AssertReturn(cbAlloc <= _2G+_1G, VERR_NO_MEMORY); 74 93 75 94 /* 76 * Align the request.95 * Just try first. 77 96 */ 78 size_t cbAligned = cb; 79 if (cbAlignment) 80 cbAligned = RT_ALIGN_Z(cb, cbAlignment); 81 else 82 cbAligned = RT_ALIGN_Z(cb, sizeof(uint64_t)); 83 AssertMsgReturn(cbAligned >= cb && cbAligned <= ~(size_t)0, ("cbAligned=%#zx cb=%#zx", cbAligned, cb), 84 VERR_INVALID_PARAMETER); 97 DWORD fPageProt = (fFlags & RTMEMALLOCEX_FLAGS_EXEC ? PAGE_EXECUTE_READWRITE : PAGE_READWRITE); 98 void *pv = VirtualAlloc(NULL, cbAlloc, MEM_RESERVE | MEM_COMMIT, fPageProt); 99 if (!pv) 100 return VERR_NO_MEMORY; 101 if ((uintptr_t)pv + cbAlloc - 1 < _4G) 102 { 103 *ppv = pv; 104 return VINF_SUCCESS; 105 } 106 VirtualFree(pv, cbAlloc, MEM_RELEASE); 85 107 86 108 /* 87 * Allocate the requested memory.109 * No luck, do address scan based allocation. 88 110 */ 89 void *pv; 90 if (fFlags & RTMEMALLOCEX_FLAGS_EXEC) 91 { 92 pv = RTMemExecAlloc(cbAligned + sizeof(RTMEMHDRR3)); 93 if ((fFlags & RTMEMALLOCEX_FLAGS_ZEROED) && pv) 94 RT_BZERO(pv, cbAligned + sizeof(RTMEMHDRR3)); 95 } 96 else if (fFlags & RTMEMALLOCEX_FLAGS_ZEROED) 97 pv = RTMemAllocZ(cbAligned + sizeof(RTMEMHDRR3)); 98 else 99 pv = RTMemAlloc(cbAligned + sizeof(RTMEMHDRR3)); 100 if (!pv) 101 return VERR_NO_MEMORY; 102 103 /* 104 * Fill in the header and return. 105 */ 106 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv; 107 pHdr->u32Magic = RTMEMHDR_MAGIC; 108 pHdr->fFlags = fFlags; 109 pHdr->cb = (uint32_t)cbAligned; 110 pHdr->cbReq = (uint32_t)cb; 111 112 *ppv = pHdr + 1; 113 return VINF_SUCCESS; 111 return rtMemAllocExInRange(cbAlloc, fFlags, ppv, _64K, _4G - cbAlloc); 114 112 } 115 RT_EXPORT_SYMBOL(RTMemAllocExTag);116 113 117 114 118 RTDECL(void) RTMemFreeEx(void *pv, size_t cb) RT_NO_THROW 115 DECLHIDDEN(void) rtMemFreeExYyBitReach(void *pv, size_t cb, uint32_t fFlags) 119 116 { 120 if (!pv)121 return;122 AssertPtr(pv); 117 BOOL fRc = VirtualFree(pv, cb, MEM_RELEASE); 118 Assert(fRc); 119 } 123 120 124 PRTMEMHDRR3 pHdr = (PRTMEMHDRR3)pv - 1;125 AssertMsg(pHdr->u32Magic == RTMEMHDR_MAGIC, ("pHdr->u32Magic=%RX32 pv=%p cb=%#x\n", pHdr->u32Magic, pv, cb));126 pHdr->u32Magic = RTMEMHDR_MAGIC_DEAD;127 Assert(pHdr->cbReq == cb);128 129 if (pHdr->fFlags & RTMEMALLOCEX_FLAGS_EXEC)130 RTMemExecFree(pHdr, pHdr->cb + sizeof(*pHdr));131 else132 RTMemFree(pHdr);133 }134 RT_EXPORT_SYMBOL(RTMemFreeEx);135
Note:
See TracChangeset
for help on using the changeset viewer.