1 //===-- sanitizer_allocator_testlib.cc ------------------------------------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
9 // Malloc replacement library based on CombinedAllocator.
10 // The primary purpose of this file is an end-to-end integration test
11 // for CombinedAllocator.
12 //===----------------------------------------------------------------------===//
14 clang++ -fno-exceptions -g -fPIC -I. -I../include -Isanitizer \
15 sanitizer_common/tests/sanitizer_allocator_testlib.cc \
16 sanitizer_common/sanitizer_*.cc -shared -lpthread -o testmalloc.so
17 LD_PRELOAD=`pwd`/testmalloc.so /your/app
19 #include "sanitizer_common/sanitizer_allocator.h"
20 #include "sanitizer_common/sanitizer_common.h"
27 #ifndef SANITIZER_MALLOC_HOOK
28 # define SANITIZER_MALLOC_HOOK(p, s)
31 #ifndef SANITIZER_FREE_HOOK
32 # define SANITIZER_FREE_HOOK(p)
36 static const uptr kAllocatorSpace
= 0x600000000000ULL
;
37 static const uptr kAllocatorSize
= 0x10000000000ULL
; // 1T.
39 typedef SizeClassAllocator64
<kAllocatorSpace
, kAllocatorSize
, 0,
40 CompactSizeClassMap
> PrimaryAllocator
;
41 typedef SizeClassAllocatorLocalCache
<PrimaryAllocator
> AllocatorCache
;
42 typedef LargeMmapAllocator
<> SecondaryAllocator
;
43 typedef CombinedAllocator
<PrimaryAllocator
, AllocatorCache
,
44 SecondaryAllocator
> Allocator
;
46 static Allocator allocator
;
47 static bool global_inited
;
48 static THREADLOCAL AllocatorCache cache
;
49 static THREADLOCAL
bool thread_inited
;
50 static pthread_key_t pkey
;
52 static void thread_dtor(void *v
) {
54 pthread_setspecific(pkey
, (void*)((uptr
)v
+ 1));
57 allocator
.SwallowCache(&cache
);
60 static void NOINLINE
thread_init() {
64 pthread_key_create(&pkey
, thread_dtor
);
67 pthread_setspecific(pkey
, (void*)1);
73 void *malloc(size_t size
) {
74 if (UNLIKELY(!thread_inited
))
76 void *p
= allocator
.Allocate(&cache
, size
, 8);
77 SANITIZER_MALLOC_HOOK(p
, size
);
82 if (UNLIKELY(!thread_inited
))
84 SANITIZER_FREE_HOOK(p
);
85 allocator
.Deallocate(&cache
, p
);
88 void *calloc(size_t nmemb
, size_t size
) {
89 if (UNLIKELY(!thread_inited
))
92 void *p
= allocator
.Allocate(&cache
, size
, 8, false);
94 SANITIZER_MALLOC_HOOK(p
, size
);
98 void *realloc(void *p
, size_t size
) {
99 if (UNLIKELY(!thread_inited
))
102 SANITIZER_FREE_HOOK(p
);
104 p
= allocator
.Reallocate(&cache
, p
, size
, 8);
106 SANITIZER_MALLOC_HOOK(p
, size
);
111 void *memalign(size_t alignment
, size_t size
) {
112 if (UNLIKELY(!thread_inited
))
114 void *p
= allocator
.Allocate(&cache
, size
, alignment
);
115 SANITIZER_MALLOC_HOOK(p
, size
);
119 int posix_memalign(void **memptr
, size_t alignment
, size_t size
) {
120 if (UNLIKELY(!thread_inited
))
122 *memptr
= allocator
.Allocate(&cache
, size
, alignment
);
123 SANITIZER_MALLOC_HOOK(*memptr
, size
);
127 void *valloc(size_t size
) {
128 if (UNLIKELY(!thread_inited
))
131 size
= GetPageSizeCached();
132 void *p
= allocator
.Allocate(&cache
, size
, GetPageSizeCached());
133 SANITIZER_MALLOC_HOOK(p
, size
);
137 void cfree(void *p
) ALIAS("free");
138 void *pvalloc(size_t size
) ALIAS("valloc");
139 void *__libc_memalign(size_t alignment
, size_t size
) ALIAS("memalign");
141 void malloc_usable_size() {
155 void *operator new(size_t size
) ALIAS("malloc");
156 void *operator new[](size_t size
) ALIAS("malloc");
157 void *operator new(size_t size
, std::nothrow_t
const&) ALIAS("malloc");
158 void *operator new[](size_t size
, std::nothrow_t
const&) ALIAS("malloc");
159 void operator delete(void *ptr
) throw() ALIAS("free");
160 void operator delete[](void *ptr
) throw() ALIAS("free");
161 void operator delete(void *ptr
, std::nothrow_t
const&) ALIAS("free");
162 void operator delete[](void *ptr
, std::nothrow_t
const&) ALIAS("free");