xref: /openbsd-src/gnu/llvm/compiler-rt/lib/sanitizer_common/sanitizer_allocator_dlsym.h (revision 810390e339a5425391477d5d41c78d7cab2424ac)
1*810390e3Srobert //===-- sanitizer_allocator_dlsym.h -----------------------------*- C++ -*-===//
2*810390e3Srobert //
3*810390e3Srobert // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4*810390e3Srobert // See https://llvm.org/LICENSE.txt for license information.
5*810390e3Srobert // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6*810390e3Srobert //
7*810390e3Srobert //===----------------------------------------------------------------------===//
8*810390e3Srobert //
9*810390e3Srobert // Hack: Sanitizer initializer calls dlsym which may need to allocate and call
10*810390e3Srobert // back into uninitialized sanitizer.
11*810390e3Srobert //
12*810390e3Srobert //===----------------------------------------------------------------------===//
13*810390e3Srobert 
14*810390e3Srobert #ifndef SANITIZER_ALLOCATOR_DLSYM_H
15*810390e3Srobert #define SANITIZER_ALLOCATOR_DLSYM_H
16*810390e3Srobert 
17*810390e3Srobert #include "sanitizer_allocator_internal.h"
18*810390e3Srobert 
19*810390e3Srobert namespace __sanitizer {
20*810390e3Srobert 
21*810390e3Srobert template <typename Details>
22*810390e3Srobert struct DlSymAllocator {
UseDlSymAllocator23*810390e3Srobert   static bool Use() {
24*810390e3Srobert     // Fuchsia doesn't use dlsym-based interceptors.
25*810390e3Srobert     return !SANITIZER_FUCHSIA && UNLIKELY(Details::UseImpl());
26*810390e3Srobert   }
27*810390e3Srobert 
PointerIsMineDlSymAllocator28*810390e3Srobert   static bool PointerIsMine(const void *ptr) {
29*810390e3Srobert     // Fuchsia doesn't use dlsym-based interceptors.
30*810390e3Srobert     return !SANITIZER_FUCHSIA &&
31*810390e3Srobert            UNLIKELY(internal_allocator()->FromPrimary(ptr));
32*810390e3Srobert   }
33*810390e3Srobert 
AllocateDlSymAllocator34*810390e3Srobert   static void *Allocate(uptr size_in_bytes) {
35*810390e3Srobert     void *ptr = InternalAlloc(size_in_bytes, nullptr, kWordSize);
36*810390e3Srobert     CHECK(internal_allocator()->FromPrimary(ptr));
37*810390e3Srobert     Details::OnAllocate(ptr,
38*810390e3Srobert                         internal_allocator()->GetActuallyAllocatedSize(ptr));
39*810390e3Srobert     return ptr;
40*810390e3Srobert   }
41*810390e3Srobert 
CallocateDlSymAllocator42*810390e3Srobert   static void *Callocate(SIZE_T nmemb, SIZE_T size) {
43*810390e3Srobert     void *ptr = InternalCalloc(nmemb, size);
44*810390e3Srobert     CHECK(internal_allocator()->FromPrimary(ptr));
45*810390e3Srobert     Details::OnAllocate(ptr,
46*810390e3Srobert                         internal_allocator()->GetActuallyAllocatedSize(ptr));
47*810390e3Srobert     return ptr;
48*810390e3Srobert   }
49*810390e3Srobert 
FreeDlSymAllocator50*810390e3Srobert   static void Free(void *ptr) {
51*810390e3Srobert     uptr size = internal_allocator()->GetActuallyAllocatedSize(ptr);
52*810390e3Srobert     Details::OnFree(ptr, size);
53*810390e3Srobert     InternalFree(ptr);
54*810390e3Srobert   }
55*810390e3Srobert 
ReallocDlSymAllocator56*810390e3Srobert   static void *Realloc(void *ptr, uptr new_size) {
57*810390e3Srobert     if (!ptr)
58*810390e3Srobert       return Allocate(new_size);
59*810390e3Srobert     CHECK(internal_allocator()->FromPrimary(ptr));
60*810390e3Srobert     if (!new_size) {
61*810390e3Srobert       Free(ptr);
62*810390e3Srobert       return nullptr;
63*810390e3Srobert     }
64*810390e3Srobert     uptr size = internal_allocator()->GetActuallyAllocatedSize(ptr);
65*810390e3Srobert     uptr memcpy_size = Min(new_size, size);
66*810390e3Srobert     void *new_ptr = Allocate(new_size);
67*810390e3Srobert     if (new_ptr)
68*810390e3Srobert       internal_memcpy(new_ptr, ptr, memcpy_size);
69*810390e3Srobert     Free(ptr);
70*810390e3Srobert     return new_ptr;
71*810390e3Srobert   }
72*810390e3Srobert 
OnAllocateDlSymAllocator73*810390e3Srobert   static void OnAllocate(const void *ptr, uptr size) {}
OnFreeDlSymAllocator74*810390e3Srobert   static void OnFree(const void *ptr, uptr size) {}
75*810390e3Srobert };
76*810390e3Srobert 
77*810390e3Srobert }  // namespace __sanitizer
78*810390e3Srobert 
79*810390e3Srobert #endif  // SANITIZER_ALLOCATOR_DLSYM_H
80