VirtualBox

source: vbox/trunk/include/iprt/mem.h@ 86649

Last change on this file since 86649 was 83546, checked in by vboxsync, 5 years ago

IPRT: Added RTMemFreeZ, RTMemTmpFreeZ, and RTMemEf* variants. bugref:9698

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 45.5 KB
Line 
1/** @file
2 * IPRT - Memory Management and Manipulation.
3 */
4
5/*
6 * Copyright (C) 2006-2020 Oracle Corporation
7 *
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.virtualbox.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License (GPL) as published by the Free Software
12 * Foundation, in version 2 as it comes in the "COPYING" file of the
13 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
14 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * The contents of this file may alternatively be used under the terms
17 * of the Common Development and Distribution License Version 1.0
18 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
19 * VirtualBox OSE distribution, in which case the provisions of the
20 * CDDL are applicable instead of those of the GPL.
21 *
22 * You may elect to license modified versions of this file under the
23 * terms and conditions of either the GPL or the CDDL or both.
24 */
25
26#ifndef IPRT_INCLUDED_mem_h
27#define IPRT_INCLUDED_mem_h
28#ifndef RT_WITHOUT_PRAGMA_ONCE
29# pragma once
30#endif
31
32
33#include <iprt/cdefs.h>
34#include <iprt/types.h>
35
36#ifdef IPRT_WITH_GCC_SANITIZER
37# include <sanitizer/lsan_interface.h>
38#endif
39
40#ifdef IN_RC
41# error "There are no RTMem APIs available Guest Context!"
42#endif
43
44
45/** @defgroup grp_rt_mem RTMem - Memory Management and Manipulation
46 * @ingroup grp_rt
47 * @{
48 */
49
50RT_C_DECLS_BEGIN
51
52/** @def RTMEM_ALIGNMENT
53 * The alignment of the memory blocks returned by RTMemAlloc(), RTMemAllocZ(),
54 * RTMemRealloc(), RTMemTmpAlloc() and RTMemTmpAllocZ() for allocations greater
55 * than RTMEM_ALIGNMENT.
56 *
57 * @note This alignment is not forced if the electric fence is active!
58 */
59#if defined(RT_OS_OS2)
60# define RTMEM_ALIGNMENT 4
61#else
62# define RTMEM_ALIGNMENT 8
63#endif
64
65/** @def RTMEM_TAG
66 * The default allocation tag used by the RTMem allocation APIs.
67 *
68 * When not defined before the inclusion of iprt/mem.h or iprt/memobj.h, this
69 * will default to the pointer to the current file name. The memory API will
70 * make of use of this as pointer to a volatile but read-only string.
71 * The alternative tag includes the line number for a more-detailed analysis.
72 */
73#ifndef RTMEM_TAG
74# if 0
75# define RTMEM_TAG (__FILE__ ":" RT_XSTR(__LINE__))
76# else
77# define RTMEM_TAG (__FILE__)
78# endif
79#endif
80
81
82/** @name Allocate temporary memory.
83 * @{ */
84/**
85 * Allocates temporary memory with default tag.
86 *
87 * Temporary memory blocks are used for not too large memory blocks which
88 * are believed not to stick around for too long. Using this API instead
89 * of RTMemAlloc() not only gives the heap manager room for optimization
90 * but makes the code easier to read.
91 *
92 * @returns Pointer to the allocated memory.
93 * @returns NULL on failure, assertion raised in strict builds.
94 * @param cb Size in bytes of the memory block to allocated.
95 */
96#define RTMemTmpAlloc(cb) RTMemTmpAllocTag((cb), RTMEM_TAG)
97
98/**
99 * Allocates temporary memory with custom tag.
100 *
101 * Temporary memory blocks are used for not too large memory blocks which
102 * are believed not to stick around for too long. Using this API instead
103 * of RTMemAlloc() not only gives the heap manager room for optimization
104 * but makes the code easier to read.
105 *
106 * @returns Pointer to the allocated memory.
107 * @returns NULL on failure, assertion raised in strict builds.
108 * @param cb Size in bytes of the memory block to allocated.
109 * @param pszTag Allocation tag used for statistics and such.
110 */
111RTDECL(void *) RTMemTmpAllocTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
112
113/**
114 * Allocates zero'd temporary memory with default tag.
115 *
116 * Same as RTMemTmpAlloc() but the memory will be zero'd.
117 *
118 * @returns Pointer to the allocated memory.
119 * @returns NULL on failure, assertion raised in strict builds.
120 * @param cb Size in bytes of the memory block to allocated.
121 */
122#define RTMemTmpAllocZ(cb) RTMemTmpAllocZTag((cb), RTMEM_TAG)
123
124/**
125 * Allocates zero'd temporary memory with custom tag.
126 *
127 * Same as RTMemTmpAlloc() but the memory will be zero'd.
128 *
129 * @returns Pointer to the allocated memory.
130 * @returns NULL on failure, assertion raised in strict builds.
131 * @param cb Size in bytes of the memory block to allocated.
132 * @param pszTag Allocation tag used for statistics and such.
133 */
134RTDECL(void *) RTMemTmpAllocZTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
135
136/**
137 * Free temporary memory.
138 *
139 * @param pv Pointer to memory block.
140 */
141RTDECL(void) RTMemTmpFree(void *pv) RT_NO_THROW_PROTO;
142
143/**
144 * Clear and free temporary memory.
145 *
146 * This is strongly recommended when the memory being freed holds untrusted data
147 * to help counter heap spraying.
148 *
149 * @param pv Pointer to memory block.
150 * @param cb Size of the memory block.
151 *
152 * @note The memory isn't always filled with zeros, it can be set to a
153 * different value in some configurations.
154 */
155RTDECL(void) RTMemTmpFreeZ(void *pv, size_t cb) RT_NO_THROW_PROTO;
156
157/** @} */
158
159
160/**
161 * Allocates memory with default tag.
162 *
163 * @returns Pointer to the allocated memory.
164 * @returns NULL on failure, assertion raised in strict builds.
165 * @param cb Size in bytes of the memory block to allocated.
166 */
167#define RTMemAlloc(cb) RTMemAllocTag((cb), RTMEM_TAG)
168
169/**
170 * Allocates memory with custom tag.
171 *
172 * @returns Pointer to the allocated memory.
173 * @returns NULL on failure, assertion raised in strict builds.
174 * @param cb Size in bytes of the memory block to allocated.
175 * @param pszTag Allocation tag used for statistics and such.
176 */
177RTDECL(void *) RTMemAllocTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
178
179/**
180 * Allocates zero'd memory with default tag.
181 *
182 * Instead of memset(pv, 0, sizeof()) use this when you want zero'd
183 * memory. This keeps the code smaller and the heap can skip the memset
184 * in about 0.42% of calls :-).
185 *
186 * @returns Pointer to the allocated memory.
187 * @returns NULL on failure.
188 * @param cb Size in bytes of the memory block to allocated.
189 */
190#define RTMemAllocZ(cb) RTMemAllocZTag((cb), RTMEM_TAG)
191
192/**
193 * Allocates zero'd memory with custom tag.
194 *
195 * Instead of memset(pv, 0, sizeof()) use this when you want zero'd
196 * memory. This keeps the code smaller and the heap can skip the memset
197 * in about 0.42% of calls :-).
198 *
199 * @returns Pointer to the allocated memory.
200 * @returns NULL on failure.
201 * @param cb Size in bytes of the memory block to allocated.
202 * @param pszTag Allocation tag used for statistics and such.
203 */
204RTDECL(void *) RTMemAllocZTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
205
206/**
207 * Wrapper around RTMemAlloc for automatically aligning variable sized
208 * allocations so that the various electric fence heaps works correctly.
209 *
210 * @returns See RTMemAlloc.
211 * @param cbUnaligned The unaligned size.
212 */
213#define RTMemAllocVar(cbUnaligned) RTMemAllocVarTag((cbUnaligned), RTMEM_TAG)
214
215/**
216 * Wrapper around RTMemAllocTag for automatically aligning variable sized
217 * allocations so that the various electric fence heaps works correctly.
218 *
219 * @returns See RTMemAlloc.
220 * @param cbUnaligned The unaligned size.
221 * @param pszTag Allocation tag used for statistics and such.
222 */
223RTDECL(void *) RTMemAllocVarTag(size_t cbUnaligned, const char *pszTag) RT_NO_THROW_PROTO;
224
225/**
226 * Wrapper around RTMemAllocZ for automatically aligning variable sized
227 * allocations so that the various electric fence heaps works correctly.
228 *
229 * @returns See RTMemAllocZ.
230 * @param cbUnaligned The unaligned size.
231 */
232#define RTMemAllocZVar(cbUnaligned) RTMemAllocZVarTag((cbUnaligned), RTMEM_TAG)
233
234/**
235 * Wrapper around RTMemAllocZTag for automatically aligning variable sized
236 * allocations so that the various electric fence heaps works correctly.
237 *
238 * @returns See RTMemAllocZ.
239 * @param cbUnaligned The unaligned size.
240 * @param pszTag Allocation tag used for statistics and such.
241 */
242RTDECL(void *) RTMemAllocZVarTag(size_t cbUnaligned, const char *pszTag) RT_NO_THROW_PROTO;
243
244/**
245 * Duplicates a chunk of memory into a new heap block (default tag).
246 *
247 * @returns New heap block with the duplicate data.
248 * @returns NULL if we're out of memory.
249 * @param pvSrc The memory to duplicate.
250 * @param cb The amount of memory to duplicate.
251 */
252#define RTMemDup(pvSrc, cb) RTMemDupTag((pvSrc), (cb), RTMEM_TAG)
253
254/**
255 * Duplicates a chunk of memory into a new heap block (custom tag).
256 *
257 * @returns New heap block with the duplicate data.
258 * @returns NULL if we're out of memory.
259 * @param pvSrc The memory to duplicate.
260 * @param cb The amount of memory to duplicate.
261 * @param pszTag Allocation tag used for statistics and such.
262 */
263RTDECL(void *) RTMemDupTag(const void *pvSrc, size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
264
265/**
266 * Duplicates a chunk of memory into a new heap block with some additional
267 * zeroed memory (default tag).
268 *
269 * @returns New heap block with the duplicate data.
270 * @returns NULL if we're out of memory.
271 * @param pvSrc The memory to duplicate.
272 * @param cbSrc The amount of memory to duplicate.
273 * @param cbExtra The amount of extra memory to allocate and zero.
274 */
275#define RTMemDupEx(pvSrc, cbSrc, cbExtra) RTMemDupExTag((pvSrc), (cbSrc), (cbExtra), RTMEM_TAG)
276
277/**
278 * Duplicates a chunk of memory into a new heap block with some additional
279 * zeroed memory (default tag).
280 *
281 * @returns New heap block with the duplicate data.
282 * @returns NULL if we're out of memory.
283 * @param pvSrc The memory to duplicate.
284 * @param cbSrc The amount of memory to duplicate.
285 * @param cbExtra The amount of extra memory to allocate and zero.
286 * @param pszTag Allocation tag used for statistics and such.
287 */
288RTDECL(void *) RTMemDupExTag(const void *pvSrc, size_t cbSrc, size_t cbExtra, const char *pszTag) RT_NO_THROW_PROTO;
289
290/**
291 * Reallocates memory with default tag.
292 *
293 * @returns Pointer to the allocated memory.
294 * @returns NULL on failure.
295 * @param pvOld The memory block to reallocate.
296 * @param cbNew The new block size (in bytes).
297 */
298#define RTMemRealloc(pvOld, cbNew) RTMemReallocTag((pvOld), (cbNew), RTMEM_TAG)
299
300/**
301 * Reallocates memory with custom tag.
302 *
303 * @returns Pointer to the allocated memory.
304 * @returns NULL on failure.
305 * @param pvOld The memory block to reallocate.
306 * @param cbNew The new block size (in bytes).
307 * @param pszTag Allocation tag used for statistics and such.
308 */
309RTDECL(void *) RTMemReallocTag(void *pvOld, size_t cbNew, const char *pszTag) RT_NO_THROW_PROTO;
310
311/**
312 * Reallocates memory with default tag, initializing any new space to zero.
313 *
314 * @returns Pointer to the allocated memory.
315 * @returns NULL on failure.
316 * @param pvOld The memory block to reallocate.
317 * @param cbOld The old block size (in bytes).
318 * @param cbNew The new block size (in bytes).
319 */
320#define RTMemReallocZ(pvOld, cbOld, cbNew) RTMemReallocZTag((pvOld), (cbOld), (cbNew), RTMEM_TAG)
321
322/**
323 * Reallocates memory with custom tag, initializing any new space to zero.
324 *
325 * @returns Pointer to the allocated memory.
326 * @returns NULL on failure.
327 * @param pvOld The memory block to reallocate.
328 * @param cbOld The old block size (in bytes).
329 * @param cbNew The new block size (in bytes).
330 * @param pszTag Allocation tag used for statistics and such.
331 */
332RTDECL(void *) RTMemReallocZTag(void *pvOld, size_t cbOld, size_t cbNew, const char *pszTag) RT_NO_THROW_PROTO;
333
334/**
335 * Frees memory.
336 *
337 * @param pv Pointer to memory block.
338 */
339RTDECL(void) RTMemFree(void *pv) RT_NO_THROW_PROTO;
340
341/**
342 * Clears and frees memory.
343 *
344 * This is strongly recommended when the memory being freed holds untrusted data
345 * to help counter heap spraying.
346 *
347 * @param pv Pointer to memory block.
348 * @param cb The size of the allocation.
349 *
350 * @note The memory isn't always filled with zeros, it can be set to a
351 * different value in some configurations.
352 */
353RTDECL(void) RTMemFreeZ(void *pv, size_t cb) RT_NO_THROW_PROTO;
354
355
356
357/** @name RTR0MemAllocEx and RTR0MemAllocExTag flags.
358 * @{ */
359/** The returned memory should be zeroed. */
360#define RTMEMALLOCEX_FLAGS_ZEROED RT_BIT(0)
361/** It must be load code into the returned memory block and execute it. */
362#define RTMEMALLOCEX_FLAGS_EXEC RT_BIT(1)
363/** Allocation from any context.
364 * Will return VERR_NOT_SUPPORTED if not supported. */
365#define RTMEMALLOCEX_FLAGS_ANY_CTX_ALLOC RT_BIT(2)
366/** Allocate the memory such that it can be freed from any context.
367 * Will return VERR_NOT_SUPPORTED if not supported. */
368#define RTMEMALLOCEX_FLAGS_ANY_CTX_FREE RT_BIT(3)
369/** Allocate and free from any context.
370 * Will return VERR_NOT_SUPPORTED if not supported. */
371#define RTMEMALLOCEX_FLAGS_ANY_CTX (RTMEMALLOCEX_FLAGS_ANY_CTX_ALLOC | RTMEMALLOCEX_FLAGS_ANY_CTX_FREE)
372/** Reachable by 16-bit address.
373 * Will return VERR_NOT_SUPPORTED if not supported. */
374#define RTMEMALLOCEX_FLAGS_16BIT_REACH RT_BIT(4)
375/** Reachable by 32-bit address.
376 * Will return VERR_NOT_SUPPORTED if not supported. */
377#define RTMEMALLOCEX_FLAGS_32BIT_REACH RT_BIT(5)
378/** Mask of valid flags. */
379#define RTMEMALLOCEX_FLAGS_VALID_MASK UINT32_C(0x0000003f)
380/** Mask of valid flags for ring-0. */
381#define RTMEMALLOCEX_FLAGS_VALID_MASK_R0 UINT32_C(0x0000000f)
382/** @} */
383
384/**
385 * Extended heap allocation API, default tag.
386 *
387 * @returns IPRT status code.
388 * @retval VERR_NO_MEMORY if we're out of memory.
389 * @retval VERR_NO_EXEC_MEMORY if we're out of executable memory.
390 * @retval VERR_NOT_SUPPORTED if any of the specified flags are unsupported.
391 *
392 * @param cb The amount of memory to allocate.
393 * @param cbAlignment The alignment requirements. Use 0 to indicate
394 * default alignment.
395 * @param fFlags A combination of the RTMEMALLOCEX_FLAGS_XXX
396 * defines.
397 * @param ppv Where to return the memory.
398 */
399#define RTMemAllocEx(cb, cbAlignment, fFlags, ppv) RTMemAllocExTag((cb), (cbAlignment), (fFlags), RTMEM_TAG, (ppv))
400
401/**
402 * Extended heap allocation API, custom tag.
403 *
404 * Depending on the implementation, using this function may add extra overhead,
405 * so use the simpler APIs where ever possible.
406 *
407 * @returns IPRT status code.
408 * @retval VERR_NO_MEMORY if we're out of memory.
409 * @retval VERR_NO_EXEC_MEMORY if we're out of executable memory.
410 * @retval VERR_NOT_SUPPORTED if any of the specified flags are unsupported.
411 *
412 * @param cb The amount of memory to allocate.
413 * @param cbAlignment The alignment requirements. Use 0 to indicate
414 * default alignment.
415 * @param fFlags A combination of the RTMEMALLOCEX_FLAGS_XXX
416 * defines.
417 * @param pszTag The tag.
418 * @param ppv Where to return the memory.
419 */
420RTDECL(int) RTMemAllocExTag(size_t cb, size_t cbAlignment, uint32_t fFlags, const char *pszTag, void **ppv) RT_NO_THROW_PROTO;
421
422/**
423 * For freeing memory allocated by RTMemAllocEx or RTMemAllocExTag.
424 *
425 * @param pv What to free, NULL is fine.
426 * @param cb The amount of allocated memory.
427 */
428RTDECL(void) RTMemFreeEx(void *pv, size_t cb) RT_NO_THROW_PROTO;
429
430
431
432/**
433 * Allocates memory which may contain code (default tag).
434 *
435 * @returns Pointer to the allocated memory.
436 * @returns NULL on failure.
437 * @param cb Size in bytes of the memory block to allocate.
438 */
439#define RTMemExecAlloc(cb) RTMemExecAllocTag((cb), RTMEM_TAG)
440
441/**
442 * Allocates memory which may contain code (custom tag).
443 *
444 * @returns Pointer to the allocated memory.
445 * @returns NULL on failure.
446 * @param cb Size in bytes of the memory block to allocate.
447 * @param pszTag Allocation tag used for statistics and such.
448 */
449RTDECL(void *) RTMemExecAllocTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
450
451/**
452 * Free executable/read/write memory allocated by RTMemExecAlloc().
453 *
454 * @param pv Pointer to memory block.
455 * @param cb The allocation size.
456 */
457RTDECL(void) RTMemExecFree(void *pv, size_t cb) RT_NO_THROW_PROTO;
458
459#if defined(IN_RING0) && defined(RT_ARCH_AMD64) && defined(RT_OS_LINUX)
460/**
461 * Donate read+write+execute memory to the exec heap.
462 *
463 * This API is specific to AMD64 and Linux/GNU. A kernel module that desires to
464 * use RTMemExecAlloc on AMD64 Linux/GNU will have to donate some statically
465 * allocated memory in the module if it wishes for GCC generated code to work.
466 * GCC can only generate modules that work in the address range ~2GB to ~0
467 * currently.
468 *
469 * The API only accept one single donation.
470 *
471 * @returns IPRT status code.
472 * @param pvMemory Pointer to the memory block.
473 * @param cb The size of the memory block.
474 */
475RTR0DECL(int) RTR0MemExecDonate(void *pvMemory, size_t cb) RT_NO_THROW_PROTO;
476#endif /* R0+AMD64+LINUX */
477
478/**
479 * Allocate page aligned memory with default tag.
480 *
481 * @returns Pointer to the allocated memory.
482 * @returns NULL if we're out of memory.
483 * @param cb Size of the memory block. Will be rounded up to page size.
484 */
485#define RTMemPageAlloc(cb) RTMemPageAllocTag((cb), RTMEM_TAG)
486
487/**
488 * Allocate page aligned memory with custom tag.
489 *
490 * @returns Pointer to the allocated memory.
491 * @returns NULL if we're out of memory.
492 * @param cb Size of the memory block. Will be rounded up to page size.
493 * @param pszTag Allocation tag used for statistics and such.
494 */
495RTDECL(void *) RTMemPageAllocTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
496
497/**
498 * Allocate zero'd page aligned memory with default tag.
499 *
500 * @returns Pointer to the allocated memory.
501 * @returns NULL if we're out of memory.
502 * @param cb Size of the memory block. Will be rounded up to page size.
503 */
504#define RTMemPageAllocZ(cb) RTMemPageAllocZTag((cb), RTMEM_TAG)
505
506/**
507 * Allocate zero'd page aligned memory with custom tag.
508 *
509 * @returns Pointer to the allocated memory.
510 * @returns NULL if we're out of memory.
511 * @param cb Size of the memory block. Will be rounded up to page size.
512 * @param pszTag Allocation tag used for statistics and such.
513 */
514RTDECL(void *) RTMemPageAllocZTag(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
515
516/**
517 * Allocate page aligned memory with default tag, extended version.
518 *
519 * @returns Pointer to the allocated memory.
520 * @returns NULL if we're out of memory.
521 * @param cb Size of the memory block. Will be rounded up to page size.
522 * @param fFlags RTMEMPAGEALLOC_F_XXX.
523 */
524#define RTMemPageAllocEx(cb, fFlags) RTMemPageAllocExTag((cb), (fFlags), RTMEM_TAG)
525
526/**
527 * Allocate page aligned memory with custom tag, extended version.
528 *
529 * @returns Pointer to the allocated memory.
530 * @returns NULL if we're out of memory.
531 * @param cb Size of the memory block. Will be rounded up to page size.
532 * @param fFlags RTMEMPAGEALLOC_F_XXX.
533 * @param pszTag Allocation tag used for statistics and such.
534 */
535RTDECL(void *) RTMemPageAllocExTag(size_t cb, uint32_t fFlags, const char *pszTag) RT_NO_THROW_PROTO;
536
537/** @name RTMEMPAGEALLOC_F_XXX - flags for RTMemPageAllocEx() and RTMemPageAllocExTag()
538 * @{ */
539/** Zero the allocation. */
540#define RTMEMPAGEALLOC_F_ZERO RT_BIT_32(0)
541/** Try lock the allocation (failure ignored). */
542#define RTMEMPAGEALLOC_F_ADVISE_LOCKED RT_BIT_32(1)
543/** Try prevent the memory from ending up in a dump/core. */
544#define RTMEMPAGEALLOC_F_ADVISE_NO_DUMP RT_BIT_32(2)
545/** Valid bit mask. */
546#define RTMEMPAGEALLOC_F_VALID_MASK UINT32_C(0x00000007)
547/** @} */
548
549/**
550 * Free a memory block allocated with RTMemPageAlloc() or RTMemPageAllocZ().
551 *
552 * @param pv Pointer to the block as it was returned by the allocation function.
553 * NULL will be ignored.
554 * @param cb The allocation size. Will be rounded up to page size.
555 * Ignored if @a pv is NULL.
556 */
557RTDECL(void) RTMemPageFree(void *pv, size_t cb) RT_NO_THROW_PROTO;
558
559/** Page level protection flags for RTMemProtect().
560 * @{
561 */
562/** No access at all. */
563#define RTMEM_PROT_NONE 0
564/** Read access. */
565#define RTMEM_PROT_READ 1
566/** Write access. */
567#define RTMEM_PROT_WRITE 2
568/** Execute access. */
569#define RTMEM_PROT_EXEC 4
570/** @} */
571
572/**
573 * Change the page level protection of a memory region.
574 *
575 * @returns iprt status code.
576 * @param pv Start of the region. Will be rounded down to nearest page boundary.
577 * @param cb Size of the region. Will be rounded up to the nearest page boundary.
578 * @param fProtect The new protection, a combination of the RTMEM_PROT_* defines.
579 */
580RTDECL(int) RTMemProtect(void *pv, size_t cb, unsigned fProtect) RT_NO_THROW_PROTO;
581
582/**
583 * Goes thru some pains to make sure the specified memory block is thoroughly
584 * scrambled.
585 *
586 * @param pv The start of the memory block.
587 * @param cb The size of the memory block.
588 * @param cMinPasses The minimum number of passes to make.
589 */
590RTDECL(void) RTMemWipeThoroughly(void *pv, size_t cb, size_t cMinPasses) RT_NO_THROW_PROTO;
591
592
593/** @def RTMEM_WILL_LEAK
594 * Macro for hinting that a memory allocation @a a_pv will leak.
595 *
596 * @note This shall only be used in code that doesn't allocate the object.
597 * Code allocating memory knowing it will leak shall start the allocation
598 * tag string with 'will-leak:'.
599 */
600/** @def RTMEM_MAY_LEAK
601 * Macro for hinting that a memory allocation @a a_pv may leak.
602 *
603 * @note This shall only be used in code that doesn't allocate the object.
604 * Code allocating memory knowing it may leak shall start the allocation
605 * tag string with 'may-leak:'.
606 */
607#ifdef IPRT_WITH_GCC_SANITIZER
608# define RTMEM_WILL_LEAK(a_pv) __lsan_ignore_object(a_pv)
609# define RTMEM_MAY_LEAK(a_pv) __lsan_ignore_object(a_pv)
610#else
611# define RTMEM_WILL_LEAK(a_pv) do { } while (0)
612# define RTMEM_MAY_LEAK(a_pv) do { } while (0)
613#endif
614
615
616/** @def RTMEM_IMPLEMENT_NEW_AND_DELETE
617 * Provides a new and delete implementation to a class using IPRT's RTMem
618 * allocator.
619 */
620#if !defined(RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF) || defined(RTMEM_NO_WRAP_SOME_NEW_AND_DELETE_TO_EF)
621# ifdef RT_EXCEPTIONS_ENABLED
622# define RTMEM_IMPLEMENT_NEW_AND_DELETE() \
623 void *operator new(size_t cb) RT_THROW(std::bad_alloc) \
624 { \
625 void *pv = RTMemAlloc(cb); \
626 if (RT_LIKELY(pv)) \
627 return pv; \
628 throw std::bad_alloc(); \
629 } \
630 void *operator new(size_t cb, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
631 { \
632 NOREF(nothrow_constant); \
633 return RTMemAlloc(cb); \
634 } \
635 void *operator new(size_t cb, void *pvBuf) RT_NO_THROW_DEF \
636 { \
637 NOREF(cb); \
638 return pvBuf; \
639 } \
640 void *operator new[](size_t cb) RT_THROW(std::bad_alloc) \
641 { \
642 void *pv = RTMemAlloc(cb); \
643 if (RT_LIKELY(pv)) \
644 return pv; \
645 throw std::bad_alloc(); \
646 } \
647 void *operator new[](size_t cb, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
648 { \
649 NOREF(nothrow_constant); \
650 return RTMemAlloc(cb); \
651 } \
652 \
653 void operator delete(void *pv) RT_NO_THROW_DEF \
654 { \
655 RTMemFree(pv); \
656 } \
657 void operator delete(void *pv, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
658 { \
659 NOREF(nothrow_constant); \
660 RTMemFree(pv); \
661 } \
662 void operator delete[](void *pv) RT_NO_THROW_DEF \
663 { \
664 RTMemFree(pv); \
665 } \
666 void operator delete[](void *pv, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
667 { \
668 NOREF(nothrow_constant); \
669 RTMemFree(pv); \
670 } \
671 \
672 typedef int UsingIprtNewAndDeleteOperators
673# else /* !RT_EXCEPTIONS_ENABLED */
674# define RTMEM_IMPLEMENT_NEW_AND_DELETE() \
675 void *operator new(size_t cb) \
676 { \
677 return RTMemAlloc(cb); \
678 } \
679 void *operator new(size_t cb, const std::nothrow_t &nothrow_constant) \
680 { \
681 NOREF(nothrow_constant); \
682 return RTMemAlloc(cb); \
683 } \
684 void *operator new(size_t cb, void *pvBuf) RT_NO_THROW_DEF \
685 { \
686 NOREF(cb); \
687 return pvBuf; \
688 } \
689 void *operator new[](size_t cb) \
690 { \
691 return RTMemAlloc(cb); \
692 } \
693 void *operator new[](size_t cb, const std::nothrow_t &nothrow_constant) \
694 { \
695 NOREF(nothrow_constant); \
696 return RTMemAlloc(cb); \
697 } \
698 \
699 void operator delete(void *pv) \
700 { \
701 RTMemFree(pv); \
702 } \
703 void operator delete(void *pv, const std::nothrow_t &nothrow_constant) \
704 { \
705 NOREF(nothrow_constant); \
706 RTMemFree(pv); \
707 } \
708 void operator delete[](void *pv) \
709 { \
710 RTMemFree(pv); \
711 } \
712 void operator delete[](void *pv, const std::nothrow_t &nothrow_constant) \
713 { \
714 NOREF(nothrow_constant); \
715 RTMemFree(pv); \
716 } \
717 \
718 typedef int UsingIprtNewAndDeleteOperators
719# endif /* !RT_EXCEPTIONS_ENABLED */
720#else /* defined(RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF) && !defined(RTMEM_NO_WRAP_SOME_NEW_AND_DELETE_TO_EF) */
721# define RTMEM_IMPLEMENT_NEW_AND_DELETE() RTMEMEF_NEW_AND_DELETE_OPERATORS()
722#endif /* defined(RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF) && !defined(RTMEM_NO_WRAP_SOME_NEW_AND_DELETE_TO_EF) */
723
724
725#ifdef IN_RING0
726
727/**
728 * Allocates physical contiguous memory (below 4GB).
729 * The allocation is page aligned and the content is undefined.
730 *
731 * @returns Pointer to the memory block. This is page aligned.
732 * @param pPhys Where to store the physical address.
733 * @param cb The allocation size in bytes. This is always
734 * rounded up to PAGE_SIZE.
735 */
736RTR0DECL(void *) RTMemContAlloc(PRTCCPHYS pPhys, size_t cb) RT_NO_THROW_PROTO;
737
738/**
739 * Frees memory allocated ysing RTMemContAlloc().
740 *
741 * @param pv Pointer to return from RTMemContAlloc().
742 * @param cb The cb parameter passed to RTMemContAlloc().
743 */
744RTR0DECL(void) RTMemContFree(void *pv, size_t cb) RT_NO_THROW_PROTO;
745
746/**
747 * Copy memory from an user mode buffer into a kernel buffer.
748 *
749 * @retval VINF_SUCCESS on success.
750 * @retval VERR_ACCESS_DENIED on error.
751 *
752 * @param pvDst The kernel mode destination address.
753 * @param R3PtrSrc The user mode source address.
754 * @param cb The number of bytes to copy.
755 */
756RTR0DECL(int) RTR0MemUserCopyFrom(void *pvDst, RTR3PTR R3PtrSrc, size_t cb);
757
758/**
759 * Copy memory from a kernel buffer into a user mode one.
760 *
761 * @retval VINF_SUCCESS on success.
762 * @retval VERR_ACCESS_DENIED on error.
763 *
764 * @param R3PtrDst The user mode destination address.
765 * @param pvSrc The kernel mode source address.
766 * @param cb The number of bytes to copy.
767 */
768RTR0DECL(int) RTR0MemUserCopyTo(RTR3PTR R3PtrDst, void const *pvSrc, size_t cb);
769
770/**
771 * Tests if the specified address is in the user addressable range.
772 *
773 * This function does not check whether the memory at that address is accessible
774 * or anything of that sort, only if the address it self is in the user mode
775 * range.
776 *
777 * @returns true if it's in the user addressable range. false if not.
778 * @param R3Ptr The user mode pointer to test.
779 *
780 * @remarks Some systems may have overlapping kernel and user address ranges.
781 * One prominent example of this is the x86 version of Mac OS X. Use
782 * RTR0MemAreKrnlAndUsrDifferent() to check.
783 */
784RTR0DECL(bool) RTR0MemUserIsValidAddr(RTR3PTR R3Ptr);
785
786/**
787 * Tests if the specified address is in the kernel mode range.
788 *
789 * This function does not check whether the memory at that address is accessible
790 * or anything of that sort, only if the address it self is in the kernel mode
791 * range.
792 *
793 * @returns true if it's in the kernel range. false if not.
794 * @param pv The alleged kernel mode pointer.
795 *
796 * @remarks Some systems may have overlapping kernel and user address ranges.
797 * One prominent example of this is the x86 version of Mac OS X. Use
798 * RTR0MemAreKrnlAndUsrDifferent() to check.
799 */
800RTR0DECL(bool) RTR0MemKernelIsValidAddr(void *pv);
801
802/**
803 * Are user mode and kernel mode address ranges distinctly different.
804 *
805 * This determines whether RTR0MemKernelIsValidAddr and RTR0MemUserIsValidAddr
806 * can be used for deciding whether some arbitrary address is a user mode or a
807 * kernel mode one.
808 *
809 * @returns true if they are, false if not.
810 */
811RTR0DECL(bool) RTR0MemAreKrnlAndUsrDifferent(void);
812
813/**
814 * Copy memory from an potentially unsafe kernel mode location and into a safe
815 * (kernel) buffer.
816 *
817 * @retval VINF_SUCCESS on success.
818 * @retval VERR_ACCESS_DENIED on error.
819 * @retval VERR_NOT_SUPPORTED if not (yet) supported.
820 *
821 * @param pvDst The destination address (safe).
822 * @param pvSrc The source address (potentially unsafe).
823 * @param cb The number of bytes to copy.
824 */
825RTR0DECL(int) RTR0MemKernelCopyFrom(void *pvDst, void const *pvSrc, size_t cb);
826
827/**
828 * Copy from a safe (kernel) buffer and to a potentially unsafe kenrel mode
829 * location.
830 *
831 * @retval VINF_SUCCESS on success.
832 * @retval VERR_ACCESS_DENIED on error.
833 * @retval VERR_NOT_SUPPORTED if not (yet) supported.
834 *
835 * @param pvDst The destination address (potentially unsafe).
836 * @param pvSrc The source address (safe).
837 * @param cb The number of bytes to copy.
838 */
839RTR0DECL(int) RTR0MemKernelCopyTo(void *pvDst, void const *pvSrc, size_t cb);
840
841#endif /* IN_RING0 */
842
843
844/** @name Electrical Fence Version of some APIs.
845 * @{
846 */
847
848/**
849 * Same as RTMemTmpAllocTag() except that it's fenced.
850 *
851 * @returns Pointer to the allocated memory.
852 * @returns NULL on failure.
853 * @param cb Size in bytes of the memory block to allocate.
854 * @param pszTag Allocation tag used for statistics and such.
855 * @param SRC_POS The source position where call is being made from.
856 * Use RT_SRC_POS when possible. Optional.
857 */
858RTDECL(void *) RTMemEfTmpAlloc(size_t cb, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
859
860/**
861 * Same as RTMemTmpAllocZTag() except that it's fenced.
862 *
863 * @returns Pointer to the allocated memory.
864 * @returns NULL on failure.
865 * @param cb Size in bytes of the memory block to allocate.
866 * @param pszTag Allocation tag used for statistics and such.
867 * @param SRC_POS The source position where call is being made from. Use
868 * RT_SRC_POS when possible. Optional.
869 */
870RTDECL(void *) RTMemEfTmpAllocZ(size_t cb, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
871
872/**
873 * Same as RTMemTmpFree() except that it's for fenced memory.
874 *
875 * @param pv Pointer to memory block.
876 * @param SRC_POS The source position where call is being made from. Use
877 * RT_SRC_POS when possible. Optional.
878 */
879RTDECL(void) RTMemEfTmpFree(void *pv, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
880
881/**
882 * Same as RTMemTmpFreeZ() except that it's for fenced memory.
883 *
884 * @param pv Pointer to memory block.
885 * @param cb Size of the memory block.
886 * @param SRC_POS The source position where call is being made from. Use
887 * RT_SRC_POS when possible. Optional.
888 */
889RTDECL(void) RTMemEfTmpFreeZ(void *pv, size_t cb, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
890
891/**
892 * Same as RTMemAllocTag() except that it's fenced.
893 *
894 * @returns Pointer to the allocated memory. Free with RTMemEfFree().
895 * @returns NULL on failure.
896 * @param cb Size in bytes of the memory block to allocate.
897 * @param pszTag Allocation tag used for statistics and such.
898 * @param SRC_POS The source position where call is being made from. Use
899 * RT_SRC_POS when possible. Optional.
900 */
901RTDECL(void *) RTMemEfAlloc(size_t cb, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
902
903/**
904 * Same as RTMemAllocZTag() except that it's fenced.
905 *
906 * @returns Pointer to the allocated memory.
907 * @returns NULL on failure.
908 * @param cb Size in bytes of the memory block to allocate.
909 * @param pszTag Allocation tag used for statistics and such.
910 * @param SRC_POS The source position where call is being made from. Use
911 * RT_SRC_POS when possible. Optional.
912 */
913RTDECL(void *) RTMemEfAllocZ(size_t cb, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
914
915/**
916 * Same as RTMemAllocVarTag() except that it's fenced.
917 *
918 * @returns Pointer to the allocated memory. Free with RTMemEfFree().
919 * @returns NULL on failure.
920 * @param cbUnaligned Size in bytes of the memory block to allocate.
921 * @param pszTag Allocation tag used for statistics and such.
922 * @param SRC_POS The source position where call is being made from. Use
923 * RT_SRC_POS when possible. Optional.
924 */
925RTDECL(void *) RTMemEfAllocVar(size_t cbUnaligned, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
926
927/**
928 * Same as RTMemAllocZVarTag() except that it's fenced.
929 *
930 * @returns Pointer to the allocated memory.
931 * @returns NULL on failure.
932 * @param cbUnaligned Size in bytes of the memory block to allocate.
933 * @param pszTag Allocation tag used for statistics and such.
934 * @param SRC_POS The source position where call is being made from. Use
935 * RT_SRC_POS when possible. Optional.
936 */
937RTDECL(void *) RTMemEfAllocZVar(size_t cbUnaligned, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
938
939/**
940 * Same as RTMemReallocTag() except that it's fenced.
941 *
942 * @returns Pointer to the allocated memory.
943 * @returns NULL on failure.
944 * @param pvOld The memory block to reallocate.
945 * @param cbNew The new block size (in bytes).
946 * @param pszTag Allocation tag used for statistics and such.
947 * @param SRC_POS The source position where call is being made from. Use
948 * RT_SRC_POS when possible. Optional.
949 */
950RTDECL(void *) RTMemEfRealloc(void *pvOld, size_t cbNew, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
951
952/**
953 * Same as RTMemReallocZTag() except that it's fenced.
954 *
955 * @returns Pointer to the allocated memory.
956 * @returns NULL on failure.
957 * @param pvOld The memory block to reallocate.
958 * @param cbOld The old block size (in bytes).
959 * @param cbNew The new block size (in bytes).
960 * @param pszTag Allocation tag used for statistics and such.
961 * @param SRC_POS The source position where call is being made from. Use
962 * RT_SRC_POS when possible. Optional.
963 */
964RTDECL(void *) RTMemEfReallocZ(void *pvOld, size_t cbOld, size_t cbNew, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
965
966/**
967 * Free memory allocated by any of the RTMemEf* allocators.
968 *
969 * @param pv Pointer to memory block.
970 * @param SRC_POS The source position where call is being made from. Use
971 * RT_SRC_POS when possible. Optional.
972 */
973RTDECL(void) RTMemEfFree(void *pv, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
974
975/**
976 * Clear and free memory allocated by any of the RTMemEf* allocators.
977 *
978 * @param pv Pointer to memory block.
979 * @param cb Size of the allocation.
980 * @param SRC_POS The source position where call is being made from. Use
981 * RT_SRC_POS when possible. Optional.
982 */
983RTDECL(void) RTMemEfFreeZ(void *pv, size_t cb, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
984
985/**
986 * Same as RTMemDupTag() except that it's fenced.
987 *
988 * @returns New heap block with the duplicate data.
989 * @returns NULL if we're out of memory.
990 * @param pvSrc The memory to duplicate.
991 * @param cb The amount of memory to duplicate.
992 * @param pszTag Allocation tag used for statistics and such.
993 * @param SRC_POS The source position where call is being made from. Use
994 * RT_SRC_POS when possible. Optional.
995 */
996RTDECL(void *) RTMemEfDup(const void *pvSrc, size_t cb, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
997
998/**
999 * Same as RTMemEfDupExTag except that it's fenced.
1000 *
1001 * @returns New heap block with the duplicate data.
1002 * @returns NULL if we're out of memory.
1003 * @param pvSrc The memory to duplicate.
1004 * @param cbSrc The amount of memory to duplicate.
1005 * @param cbExtra The amount of extra memory to allocate and zero.
1006 * @param pszTag Allocation tag used for statistics and such.
1007 * @param SRC_POS The source position where call is being made from. Use
1008 * RT_SRC_POS when possible. Optional.
1009 */
1010RTDECL(void *) RTMemEfDupEx(const void *pvSrc, size_t cbSrc, size_t cbExtra, const char *pszTag, RT_SRC_POS_DECL) RT_NO_THROW_PROTO;
1011
1012/** @def RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF
1013 * Define RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF to enable electric fence new and
1014 * delete operators for classes which uses the RTMEMEF_NEW_AND_DELETE_OPERATORS
1015 * macro.
1016 */
1017/** @def RTMEMEF_NEW_AND_DELETE_OPERATORS
1018 * Defines the electric fence new and delete operators for a class when
1019 * RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF is define.
1020 */
1021/** @def RTR0MEMEF_NEW_AND_DELETE_OPERATORS_IOKIT
1022 * Defines the electric fence new and delete operators for an IOKit class when
1023 * RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF is define.
1024 *
1025 * This differs from RTMEMEF_NEW_AND_DELETE_OPERATORS in that the memory we
1026 * allocate is initialized to zero. It is also assuming we don't have nothrow
1027 * variants and exceptions, so fewer variations.
1028 */
1029#if defined(RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF) && !defined(RTMEM_NO_WRAP_SOME_NEW_AND_DELETE_TO_EF)
1030# if defined(RT_EXCEPTIONS_ENABLED)
1031# define RTMEMEF_NEW_AND_DELETE_OPERATORS() \
1032 void *operator new(size_t cb) RT_THROW(std::bad_alloc) \
1033 { \
1034 void *pv = RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1035 if (RT_LIKELY(pv)) \
1036 return pv; \
1037 throw std::bad_alloc(); \
1038 } \
1039 void *operator new(size_t cb, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
1040 { \
1041 NOREF(nothrow_constant); \
1042 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1043 } \
1044 void *operator new(size_t cb, void *pvBuf) RT_NO_THROW_DEF \
1045 { \
1046 NOREF(cb); \
1047 return pvBuf; \
1048 } \
1049 void *operator new[](size_t cb) RT_THROW(std::bad_alloc) \
1050 { \
1051 void *pv = RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1052 if (RT_LIKELY(pv)) \
1053 return pv; \
1054 throw std::bad_alloc(); \
1055 } \
1056 void *operator new[](size_t cb, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
1057 { \
1058 NOREF(nothrow_constant); \
1059 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1060 } \
1061 \
1062 void operator delete(void *pv) RT_NO_THROW_DEF \
1063 { \
1064 RTMemEfFree(pv, RT_SRC_POS); \
1065 } \
1066 void operator delete(void *pv, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
1067 { \
1068 NOREF(nothrow_constant); \
1069 RTMemEfFree(pv, RT_SRC_POS); \
1070 } \
1071 void operator delete[](void *pv) RT_NO_THROW_DEF \
1072 { \
1073 RTMemEfFree(pv, RT_SRC_POS); \
1074 } \
1075 void operator delete[](void *pv, const std::nothrow_t &nothrow_constant) RT_NO_THROW_DEF \
1076 { \
1077 NOREF(nothrow_constant); \
1078 RTMemEfFree(pv, RT_SRC_POS); \
1079 } \
1080 \
1081 typedef int UsingElectricNewAndDeleteOperators
1082# else
1083# define RTMEMEF_NEW_AND_DELETE_OPERATORS() \
1084 void *operator new(size_t cb) \
1085 { \
1086 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1087 } \
1088 void *operator new(size_t cb, const std::nothrow_t &nothrow_constant) \
1089 { \
1090 NOREF(nothrow_constant); \
1091 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1092 } \
1093 void *operator new(size_t cb, void *pvBuf) RT_NO_THROW_DEF \
1094 { \
1095 NOREF(cb); \
1096 return pvBuf; \
1097 } \
1098 void *operator new[](size_t cb) \
1099 { \
1100 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1101 } \
1102 void *operator new[](size_t cb, const std::nothrow_t &nothrow_constant) \
1103 { \
1104 NOREF(nothrow_constant); \
1105 return RTMemEfAlloc(cb, RTMEM_TAG, RT_SRC_POS); \
1106 } \
1107 \
1108 void operator delete(void *pv) \
1109 { \
1110 RTMemEfFree(pv, RT_SRC_POS); \
1111 } \
1112 void operator delete(void *pv, const std::nothrow_t &nothrow_constant) \
1113 { \
1114 NOREF(nothrow_constant); \
1115 RTMemEfFree(pv, RT_SRC_POS); \
1116 } \
1117 void operator delete[](void *pv) \
1118 { \
1119 RTMemEfFree(pv, RT_SRC_POS); \
1120 } \
1121 void operator delete[](void *pv, const std::nothrow_t &nothrow_constant) \
1122 { \
1123 NOREF(nothrow_constant); \
1124 RTMemEfFree(pv, RT_SRC_POS); \
1125 } \
1126 \
1127 typedef int UsingElectricNewAndDeleteOperators
1128# endif
1129# define RTR0MEMEF_NEW_AND_DELETE_OPERATORS_IOKIT() \
1130 void *operator new(size_t cb) \
1131 { \
1132 return RTMemEfAllocZ(cb, RTMEM_TAG, RT_SRC_POS); \
1133 } \
1134 void *operator new[](size_t cb) \
1135 { \
1136 return RTMemEfAllocZ(cb, RTMEM_TAG, RT_SRC_POS); \
1137 } \
1138 \
1139 void operator delete(void *pv) \
1140 { \
1141 RTMemEfFree(pv, RT_SRC_POS); \
1142 } \
1143 void operator delete[](void *pv) \
1144 { \
1145 RTMemEfFree(pv, RT_SRC_POS); \
1146 } \
1147 \
1148 typedef int UsingElectricNewAndDeleteOperators
1149#else
1150# define RTMEMEF_NEW_AND_DELETE_OPERATORS() \
1151 typedef int UsingDefaultNewAndDeleteOperators
1152# define RTR0MEMEF_NEW_AND_DELETE_OPERATORS_IOKIT() \
1153 typedef int UsingDefaultNewAndDeleteOperators
1154#endif
1155#ifdef DOXYGEN_RUNNING
1156# define RTMEM_WRAP_SOME_NEW_AND_DELETE_TO_EF
1157#endif
1158
1159/** @def RTMEM_WRAP_TO_EF_APIS
1160 * Define RTMEM_WRAP_TO_EF_APIS to wrap RTMem APIs to RTMemEf APIs.
1161 */
1162#if defined(RTMEM_WRAP_TO_EF_APIS) && !defined(RTMEM_NO_WRAP_TO_EF_APIS) \
1163 && ( defined(IN_RING3) || ( defined(IN_RING0) && !defined(IN_RING0_AGNOSTIC) && (defined(RT_OS_DARWIN) || 0) ) )
1164# define RTMemTmpAllocTag(cb, pszTag) RTMemEfTmpAlloc((cb), (pszTag), RT_SRC_POS)
1165# define RTMemTmpAllocZTag(cb, pszTag) RTMemEfTmpAllocZ((cb), (pszTag), RT_SRC_POS)
1166# define RTMemTmpFree(pv) RTMemEfTmpFree((pv), RT_SRC_POS)
1167# define RTMemTmpFreeZ(pv, cb) RTMemEfTmpFreeZ((pv), (cb), RT_SRC_POS)
1168# define RTMemAllocTag(cb, pszTag) RTMemEfAlloc((cb), (pszTag), RT_SRC_POS)
1169# define RTMemAllocZTag(cb, pszTag) RTMemEfAllocZ((cb), (pszTag), RT_SRC_POS)
1170# define RTMemAllocVarTag(cbUnaligned, pszTag) RTMemEfAllocVar((cbUnaligned), (pszTag), RT_SRC_POS)
1171# define RTMemAllocZVarTag(cbUnaligned, pszTag) RTMemEfAllocZVar((cbUnaligned), (pszTag), RT_SRC_POS)
1172# define RTMemReallocTag(pvOld, cbNew, pszTag) RTMemEfRealloc((pvOld), (cbNew), (pszTag), RT_SRC_POS)
1173# define RTMemReallocZTag(pvOld, cbOld, cbNew, pszTag) RTMemEfReallocZ((pvOld), (cbOld), (cbNew), (pszTag), RT_SRC_POS)
1174# define RTMemFree(pv) RTMemEfFree((pv), RT_SRC_POS)
1175# define RTMemFreeZ(pv, cb) RTMemEfFreeZ((pv), (cb), RT_SRC_POS)
1176# define RTMemDupTag(pvSrc, cb, pszTag) RTMemEfDup((pvSrc), (cb), (pszTag), RT_SRC_POS)
1177# define RTMemDupExTag(pvSrc, cbSrc, cbExtra, pszTag) RTMemEfDupEx((pvSrc), (cbSrc), (cbExtra), (pszTag), RT_SRC_POS)
1178#endif
1179#ifdef DOXYGEN_RUNNING
1180# define RTMEM_WRAP_TO_EF_APIS
1181#endif
1182
1183/**
1184 * Fenced drop-in replacement for RTMemTmpAllocTag.
1185 * @copydoc RTMemTmpAllocTag
1186 */
1187RTDECL(void *) RTMemEfTmpAllocNP(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
1188
1189/**
1190 * Fenced drop-in replacement for RTMemTmpAllocZTag.
1191 * @copydoc RTMemTmpAllocZTag
1192 */
1193RTDECL(void *) RTMemEfTmpAllocZNP(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
1194
1195/**
1196 * Fenced drop-in replacement for RTMemTmpFree.
1197 * @copydoc RTMemTmpFree
1198 */
1199RTDECL(void) RTMemEfTmpFreeNP(void *pv) RT_NO_THROW_PROTO;
1200
1201/**
1202 * Fenced drop-in replacement for RTMemTmpFreeZ.
1203 * @copydoc RTMemTmpFreeZ
1204 */
1205RTDECL(void) RTMemEfTmpFreeZNP(void *pv, size_t cb) RT_NO_THROW_PROTO;
1206
1207/**
1208 * Fenced drop-in replacement for RTMemAllocTag.
1209 * @copydoc RTMemAllocTag
1210 */
1211RTDECL(void *) RTMemEfAllocNP(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
1212
1213/**
1214 * Fenced drop-in replacement for RTMemAllocZTag.
1215 * @copydoc RTMemAllocZTag
1216 */
1217RTDECL(void *) RTMemEfAllocZNP(size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
1218
1219/**
1220 * Fenced drop-in replacement for RTMemAllocVarTag
1221 * @copydoc RTMemAllocVarTag
1222 */
1223RTDECL(void *) RTMemEfAllocVarNP(size_t cbUnaligned, const char *pszTag) RT_NO_THROW_PROTO;
1224
1225/**
1226 * Fenced drop-in replacement for RTMemAllocZVarTag.
1227 * @copydoc RTMemAllocZVarTag
1228 */
1229RTDECL(void *) RTMemEfAllocZVarNP(size_t cbUnaligned, const char *pszTag) RT_NO_THROW_PROTO;
1230
1231/**
1232 * Fenced drop-in replacement for RTMemReallocTag.
1233 * @copydoc RTMemReallocTag
1234 */
1235RTDECL(void *) RTMemEfReallocNP(void *pvOld, size_t cbNew, const char *pszTag) RT_NO_THROW_PROTO;
1236
1237/**
1238 * Fenced drop-in replacement for RTMemReallocZTag.
1239 * @copydoc RTMemReallocZTag
1240 */
1241RTDECL(void *) RTMemEfReallocZNP(void *pvOld, size_t cbOld, size_t cbNew, const char *pszTag) RT_NO_THROW_PROTO;
1242
1243/**
1244 * Fenced drop-in replacement for RTMemFree.
1245 * @copydoc RTMemFree
1246 */
1247RTDECL(void) RTMemEfFreeNP(void *pv) RT_NO_THROW_PROTO;
1248
1249/**
1250 * Fenced drop-in replacement for RTMemFreeZ.
1251 * @copydoc RTMemFreeZ
1252 */
1253RTDECL(void) RTMemEfFreeZNP(void *pv, size_t cb) RT_NO_THROW_PROTO;
1254
1255/**
1256 * Fenced drop-in replacement for RTMemDupExTag.
1257 * @copydoc RTMemDupTag
1258 */
1259RTDECL(void *) RTMemEfDupNP(const void *pvSrc, size_t cb, const char *pszTag) RT_NO_THROW_PROTO;
1260
1261/**
1262 * Fenced drop-in replacement for RTMemDupExTag.
1263 * @copydoc RTMemDupExTag
1264 */
1265RTDECL(void *) RTMemEfDupExNP(const void *pvSrc, size_t cbSrc, size_t cbExtra, const char *pszTag) RT_NO_THROW_PROTO;
1266
1267/** @} */
1268
1269RT_C_DECLS_END
1270
1271/** @} */
1272
1273
1274#endif /* !IPRT_INCLUDED_mem_h */
1275
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette