sanitizer_allocator.cc revision 238901
112795Swpaul//===-- sanitizer_allocator.cc --------------------------------------------===//
212795Swpaul//
312795Swpaul//                     The LLVM Compiler Infrastructure
412795Swpaul//
512795Swpaul// This file is distributed under the University of Illinois Open Source
612795Swpaul// License. See LICENSE.TXT for details.
712795Swpaul//
812795Swpaul//===----------------------------------------------------------------------===//
912795Swpaul//
1012795Swpaul// This file is shared between AddressSanitizer and ThreadSanitizer
1112795Swpaul// run-time libraries.
1212795Swpaul// This allocator that is used inside run-times.
1312795Swpaul//===----------------------------------------------------------------------===//
1412795Swpaul#include "sanitizer_common.h"
1512795Swpaul
1612795Swpaul// FIXME: We should probably use more low-level allocator that would
1712795Swpaul// mmap some pages and split them into chunks to fulfill requests.
1812795Swpaul#ifdef __linux__
1912795Swpaulextern "C" void *__libc_malloc(__sanitizer::uptr size);
2012795Swpaulextern "C" void __libc_free(void *ptr);
2112795Swpaul# define LIBC_MALLOC __libc_malloc
2212795Swpaul# define LIBC_FREE __libc_free
2312795Swpaul#else  // __linux__
2412795Swpaul# include <stdlib.h>
2512795Swpaul# define LIBC_MALLOC malloc
2612795Swpaul# define LIBC_FREE free
2712795Swpaul#endif  // __linux__
2812795Swpaul
2912795Swpaulnamespace __sanitizer {
3012795Swpaul
3112795Swpaulconst u64 kBlockMagic = 0x6A6CB03ABCEBC041ull;
3212795Swpaul
3312795Swpaulvoid *InternalAlloc(uptr size) {
3412795Swpaul  if (size + sizeof(u64) < size)
3512795Swpaul    return 0;
3612795Swpaul  void *p = LIBC_MALLOC(size + sizeof(u64));
3712795Swpaul  if (p == 0)
3812795Swpaul    return 0;
3912795Swpaul  ((u64*)p)[0] = kBlockMagic;
4012795Swpaul  return (char*)p + sizeof(u64);
4112795Swpaul}
4212795Swpaul
4312795Swpaulvoid InternalFree(void *addr) {
4412795Swpaul  if (addr == 0)
4512795Swpaul    return;
4612795Swpaul  addr = (char*)addr - sizeof(u64);
4712795Swpaul  CHECK_EQ(((u64*)addr)[0], kBlockMagic);
4812795Swpaul  ((u64*)addr)[0] = 0;
4912795Swpaul  LIBC_FREE(addr);
5012795Swpaul}
5112795Swpaul
5212795Swpaulvoid *InternalAllocBlock(void *p) {
5312795Swpaul  CHECK_NE(p, (void*)0);
5412795Swpaul  u64 *pp = (u64*)((uptr)p & ~0x7);
5512795Swpaul  for (; pp[0] != kBlockMagic; pp--) {}
5612795Swpaul  return pp + 1;
5712795Swpaul}
5812795Swpaul
5912795Swpaul}  // namespace __sanitizer
6012795Swpaul