xref: /freebsd-src/contrib/llvm-project/compiler-rt/lib/memprof/memprof_allocator.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
1e8d8bef9SDimitry Andric //===-- memprof_allocator.h ------------------------------------*- C++ -*-===//
2e8d8bef9SDimitry Andric //
3e8d8bef9SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4e8d8bef9SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
5e8d8bef9SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6e8d8bef9SDimitry Andric //
7e8d8bef9SDimitry Andric //===----------------------------------------------------------------------===//
8e8d8bef9SDimitry Andric //
9e8d8bef9SDimitry Andric // This file is a part of MemProfiler, a memory profiler.
10e8d8bef9SDimitry Andric //
11e8d8bef9SDimitry Andric // MemProf-private header for memprof_allocator.cpp.
12e8d8bef9SDimitry Andric //===----------------------------------------------------------------------===//
13e8d8bef9SDimitry Andric 
14e8d8bef9SDimitry Andric #ifndef MEMPROF_ALLOCATOR_H
15e8d8bef9SDimitry Andric #define MEMPROF_ALLOCATOR_H
16e8d8bef9SDimitry Andric 
17e8d8bef9SDimitry Andric #include "memprof_flags.h"
18e8d8bef9SDimitry Andric #include "memprof_interceptors.h"
19e8d8bef9SDimitry Andric #include "memprof_internal.h"
20e8d8bef9SDimitry Andric #include "sanitizer_common/sanitizer_allocator.h"
21e8d8bef9SDimitry Andric #include "sanitizer_common/sanitizer_list.h"
22e8d8bef9SDimitry Andric 
23e8d8bef9SDimitry Andric #if !defined(__x86_64__)
24e8d8bef9SDimitry Andric #error Unsupported platform
25e8d8bef9SDimitry Andric #endif
26e8d8bef9SDimitry Andric #if !SANITIZER_CAN_USE_ALLOCATOR64
27e8d8bef9SDimitry Andric #error Only 64-bit allocator supported
28e8d8bef9SDimitry Andric #endif
29e8d8bef9SDimitry Andric 
30e8d8bef9SDimitry Andric namespace __memprof {
31e8d8bef9SDimitry Andric 
32e8d8bef9SDimitry Andric enum AllocType {
33e8d8bef9SDimitry Andric   FROM_MALLOC = 1, // Memory block came from malloc, calloc, realloc, etc.
34e8d8bef9SDimitry Andric   FROM_NEW = 2,    // Memory block came from operator new.
35e8d8bef9SDimitry Andric   FROM_NEW_BR = 3  // Memory block came from operator new [ ]
36e8d8bef9SDimitry Andric };
37e8d8bef9SDimitry Andric 
38e8d8bef9SDimitry Andric void InitializeAllocator();
39e8d8bef9SDimitry Andric 
40e8d8bef9SDimitry Andric struct MemprofMapUnmapCallback {
41e8d8bef9SDimitry Andric   void OnMap(uptr p, uptr size) const;
4206c3fb27SDimitry Andric   void OnMapSecondary(uptr p, uptr size, uptr user_begin,
4306c3fb27SDimitry Andric                       uptr user_size) const {
4406c3fb27SDimitry Andric     OnMap(p, size);
4506c3fb27SDimitry Andric   }
46e8d8bef9SDimitry Andric   void OnUnmap(uptr p, uptr size) const;
47e8d8bef9SDimitry Andric };
48e8d8bef9SDimitry Andric 
49*0fca6ea1SDimitry Andric constexpr uptr kAllocatorSpace = ~(uptr)0;
50e8d8bef9SDimitry Andric constexpr uptr kAllocatorSize = 0x40000000000ULL; // 4T.
51e8d8bef9SDimitry Andric typedef DefaultSizeClassMap SizeClassMap;
52e8d8bef9SDimitry Andric template <typename AddressSpaceViewTy>
53e8d8bef9SDimitry Andric struct AP64 { // Allocator64 parameters. Deliberately using a short name.
54e8d8bef9SDimitry Andric   static const uptr kSpaceBeg = kAllocatorSpace;
55e8d8bef9SDimitry Andric   static const uptr kSpaceSize = kAllocatorSize;
56e8d8bef9SDimitry Andric   static const uptr kMetadataSize = 0;
57e8d8bef9SDimitry Andric   typedef __memprof::SizeClassMap SizeClassMap;
58e8d8bef9SDimitry Andric   typedef MemprofMapUnmapCallback MapUnmapCallback;
59e8d8bef9SDimitry Andric   static const uptr kFlags = 0;
60e8d8bef9SDimitry Andric   using AddressSpaceView = AddressSpaceViewTy;
61e8d8bef9SDimitry Andric };
62e8d8bef9SDimitry Andric 
63e8d8bef9SDimitry Andric template <typename AddressSpaceView>
64e8d8bef9SDimitry Andric using PrimaryAllocatorASVT = SizeClassAllocator64<AP64<AddressSpaceView>>;
65e8d8bef9SDimitry Andric using PrimaryAllocator = PrimaryAllocatorASVT<LocalAddressSpaceView>;
66e8d8bef9SDimitry Andric 
67e8d8bef9SDimitry Andric static const uptr kNumberOfSizeClasses = SizeClassMap::kNumClasses;
68e8d8bef9SDimitry Andric 
69e8d8bef9SDimitry Andric template <typename AddressSpaceView>
70e8d8bef9SDimitry Andric using MemprofAllocatorASVT =
71e8d8bef9SDimitry Andric     CombinedAllocator<PrimaryAllocatorASVT<AddressSpaceView>>;
72e8d8bef9SDimitry Andric using MemprofAllocator = MemprofAllocatorASVT<LocalAddressSpaceView>;
73e8d8bef9SDimitry Andric using AllocatorCache = MemprofAllocator::AllocatorCache;
74e8d8bef9SDimitry Andric 
75e8d8bef9SDimitry Andric struct MemprofThreadLocalMallocStorage {
76e8d8bef9SDimitry Andric   AllocatorCache allocator_cache;
77e8d8bef9SDimitry Andric   void CommitBack();
78e8d8bef9SDimitry Andric 
79e8d8bef9SDimitry Andric private:
80e8d8bef9SDimitry Andric   // These objects are allocated via mmap() and are zero-initialized.
81e8d8bef9SDimitry Andric   MemprofThreadLocalMallocStorage() {}
82e8d8bef9SDimitry Andric };
83e8d8bef9SDimitry Andric 
84e8d8bef9SDimitry Andric void *memprof_memalign(uptr alignment, uptr size, BufferedStackTrace *stack,
85e8d8bef9SDimitry Andric                        AllocType alloc_type);
86e8d8bef9SDimitry Andric void memprof_free(void *ptr, BufferedStackTrace *stack, AllocType alloc_type);
87e8d8bef9SDimitry Andric void memprof_delete(void *ptr, uptr size, uptr alignment,
88e8d8bef9SDimitry Andric                     BufferedStackTrace *stack, AllocType alloc_type);
89e8d8bef9SDimitry Andric 
90e8d8bef9SDimitry Andric void *memprof_malloc(uptr size, BufferedStackTrace *stack);
91e8d8bef9SDimitry Andric void *memprof_calloc(uptr nmemb, uptr size, BufferedStackTrace *stack);
92e8d8bef9SDimitry Andric void *memprof_realloc(void *p, uptr size, BufferedStackTrace *stack);
93e8d8bef9SDimitry Andric void *memprof_reallocarray(void *p, uptr nmemb, uptr size,
94e8d8bef9SDimitry Andric                            BufferedStackTrace *stack);
95e8d8bef9SDimitry Andric void *memprof_valloc(uptr size, BufferedStackTrace *stack);
96e8d8bef9SDimitry Andric void *memprof_pvalloc(uptr size, BufferedStackTrace *stack);
97e8d8bef9SDimitry Andric 
98e8d8bef9SDimitry Andric void *memprof_aligned_alloc(uptr alignment, uptr size,
99e8d8bef9SDimitry Andric                             BufferedStackTrace *stack);
100e8d8bef9SDimitry Andric int memprof_posix_memalign(void **memptr, uptr alignment, uptr size,
101e8d8bef9SDimitry Andric                            BufferedStackTrace *stack);
102*0fca6ea1SDimitry Andric uptr memprof_malloc_usable_size(const void *ptr);
103e8d8bef9SDimitry Andric 
104e8d8bef9SDimitry Andric void PrintInternalAllocatorStats();
105e8d8bef9SDimitry Andric 
106e8d8bef9SDimitry Andric } // namespace __memprof
107e8d8bef9SDimitry Andric #endif // MEMPROF_ALLOCATOR_H
108