| 1 | /******************************************************************************/ |
| 2 | #ifdef JEMALLOC_H_TYPES |
| 3 | |
| 4 | #ifdef JEMALLOC_VALGRIND |
| 5 | #include <valgrind/valgrind.h> |
| 6 | |
| 7 | /* |
| 8 | * The size that is reported to Valgrind must be consistent through a chain of |
| 9 | * malloc..realloc..realloc calls. Request size isn't recorded anywhere in |
| 10 | * jemalloc, so it is critical that all callers of these macros provide usize |
| 11 | * rather than request size. As a result, buffer overflow detection is |
| 12 | * technically weakened for the standard API, though it is generally accepted |
| 13 | * practice to consider any extra bytes reported by malloc_usable_size() as |
| 14 | * usable space. |
| 15 | */ |
| 16 | #define JEMALLOC_VALGRIND_MAKE_MEM_NOACCESS(ptr, usize) do { \ |
| 17 | if (unlikely(in_valgrind)) \ |
| 18 | valgrind_make_mem_noaccess(ptr, usize); \ |
| 19 | } while (0) |
| 20 | #define JEMALLOC_VALGRIND_MAKE_MEM_UNDEFINED(ptr, usize) do { \ |
| 21 | if (unlikely(in_valgrind)) \ |
| 22 | valgrind_make_mem_undefined(ptr, usize); \ |
| 23 | } while (0) |
| 24 | #define JEMALLOC_VALGRIND_MAKE_MEM_DEFINED(ptr, usize) do { \ |
| 25 | if (unlikely(in_valgrind)) \ |
| 26 | valgrind_make_mem_defined(ptr, usize); \ |
| 27 | } while (0) |
| 28 | /* |
| 29 | * The VALGRIND_MALLOCLIKE_BLOCK() and VALGRIND_RESIZEINPLACE_BLOCK() macro |
| 30 | * calls must be embedded in macros rather than in functions so that when |
| 31 | * Valgrind reports errors, there are no extra stack frames in the backtraces. |
| 32 | */ |
| 33 | #define JEMALLOC_VALGRIND_MALLOC(cond, tsdn, ptr, usize, zero) do { \ |
| 34 | if (unlikely(in_valgrind && cond)) { \ |
| 35 | VALGRIND_MALLOCLIKE_BLOCK(ptr, usize, p2rz(tsdn, ptr), \ |
| 36 | zero); \ |
| 37 | } \ |
| 38 | } while (0) |
| 39 | #define JEMALLOC_VALGRIND_REALLOC(maybe_moved, tsdn, ptr, usize, \ |
| 40 | ptr_maybe_null, old_ptr, old_usize, old_rzsize, old_ptr_maybe_null, \ |
| 41 | zero) do { \ |
| 42 | if (unlikely(in_valgrind)) { \ |
| 43 | size_t rzsize = p2rz(tsdn, ptr); \ |
| 44 | \ |
| 45 | if (!maybe_moved || ptr == old_ptr) { \ |
| 46 | VALGRIND_RESIZEINPLACE_BLOCK(ptr, old_usize, \ |
| 47 | usize, rzsize); \ |
| 48 | if (zero && old_usize < usize) { \ |
| 49 | valgrind_make_mem_defined( \ |
| 50 | (void *)((uintptr_t)ptr + \ |
| 51 | old_usize), usize - old_usize); \ |
| 52 | } \ |
| 53 | } else { \ |
| 54 | if (!old_ptr_maybe_null || old_ptr != NULL) { \ |
| 55 | valgrind_freelike_block(old_ptr, \ |
| 56 | old_rzsize); \ |
| 57 | } \ |
| 58 | if (!ptr_maybe_null || ptr != NULL) { \ |
| 59 | size_t copy_size = (old_usize < usize) \ |
| 60 | ? old_usize : usize; \ |
| 61 | size_t tail_size = usize - copy_size; \ |
| 62 | VALGRIND_MALLOCLIKE_BLOCK(ptr, usize, \ |
| 63 | rzsize, false); \ |
| 64 | if (copy_size > 0) { \ |
| 65 | valgrind_make_mem_defined(ptr, \ |
| 66 | copy_size); \ |
| 67 | } \ |
| 68 | if (zero && tail_size > 0) { \ |
| 69 | valgrind_make_mem_defined( \ |
| 70 | (void *)((uintptr_t)ptr + \ |
| 71 | copy_size), tail_size); \ |
| 72 | } \ |
| 73 | } \ |
| 74 | } \ |
| 75 | } \ |
| 76 | } while (0) |
| 77 | #define JEMALLOC_VALGRIND_FREE(ptr, rzsize) do { \ |
| 78 | if (unlikely(in_valgrind)) \ |
| 79 | valgrind_freelike_block(ptr, rzsize); \ |
| 80 | } while (0) |
| 81 | #else |
| 82 | #define RUNNING_ON_VALGRIND ((unsigned)0) |
| 83 | #define JEMALLOC_VALGRIND_MAKE_MEM_NOACCESS(ptr, usize) do {} while (0) |
| 84 | #define JEMALLOC_VALGRIND_MAKE_MEM_UNDEFINED(ptr, usize) do {} while (0) |
| 85 | #define JEMALLOC_VALGRIND_MAKE_MEM_DEFINED(ptr, usize) do {} while (0) |
| 86 | #define JEMALLOC_VALGRIND_MALLOC(cond, tsdn, ptr, usize, zero) do {} while (0) |
| 87 | #define JEMALLOC_VALGRIND_REALLOC(maybe_moved, tsdn, ptr, usize, \ |
| 88 | ptr_maybe_null, old_ptr, old_usize, old_rzsize, old_ptr_maybe_null, \ |
| 89 | zero) do {} while (0) |
| 90 | #define JEMALLOC_VALGRIND_FREE(ptr, rzsize) do {} while (0) |
| 91 | #endif |
| 92 | |
| 93 | #endif /* JEMALLOC_H_TYPES */ |
| 94 | /******************************************************************************/ |
| 95 | #ifdef JEMALLOC_H_STRUCTS |
| 96 | |
| 97 | #endif /* JEMALLOC_H_STRUCTS */ |
| 98 | /******************************************************************************/ |
| 99 | #ifdef JEMALLOC_H_EXTERNS |
| 100 | |
| 101 | #ifdef JEMALLOC_VALGRIND |
| 102 | void valgrind_make_mem_noaccess(void *ptr, size_t usize); |
| 103 | void valgrind_make_mem_undefined(void *ptr, size_t usize); |
| 104 | void valgrind_make_mem_defined(void *ptr, size_t usize); |
| 105 | void valgrind_freelike_block(void *ptr, size_t usize); |
| 106 | #endif |
| 107 | |
| 108 | #endif /* JEMALLOC_H_EXTERNS */ |
| 109 | /******************************************************************************/ |
| 110 | #ifdef JEMALLOC_H_INLINES |
| 111 | |
| 112 | #endif /* JEMALLOC_H_INLINES */ |
| 113 | /******************************************************************************/ |
| 114 | |
| 115 | |