diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2020-07-26 19:36:28 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2020-07-26 19:36:28 +0000 |
commit | cfca06d7963fa0909f90483b42a6d7d194d01e08 (patch) | |
tree | 209fb2a2d68f8f277793fc8df46c753d31bc853b /compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp | |
parent | 706b4fc47bbc608932d3b491ae19a3b9cde9497b (diff) |
Notes
Diffstat (limited to 'compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp')
-rw-r--r-- | compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp | 90 |
1 files changed, 90 insertions, 0 deletions
diff --git a/compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp b/compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp new file mode 100644 index 000000000000..0e6059896702 --- /dev/null +++ b/compiler-rt/lib/gwp_asan/platform_specific/utilities_posix.cpp @@ -0,0 +1,90 @@ +//===-- utilities_posix.cpp -------------------------------------*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "gwp_asan/definitions.h" +#include "gwp_asan/utilities.h" + +#include <assert.h> + +#ifdef __BIONIC__ +#include <stdlib.h> +extern "C" GWP_ASAN_WEAK void android_set_abort_message(const char *); +#else // __BIONIC__ +#include <stdio.h> +#endif + +namespace gwp_asan { + +#ifdef __BIONIC__ +void Check(bool Condition, const char *Message) { + if (Condition) + return; + if (&android_set_abort_message != nullptr) + android_set_abort_message(Message); + abort(); +} +#else // __BIONIC__ +void Check(bool Condition, const char *Message) { + if (Condition) + return; + fprintf(stderr, "%s", Message); + __builtin_trap(); +} +#endif // __BIONIC__ + +// See `bionic/tests/malloc_test.cpp` in the Android source for documentation +// regarding their alignment guarantees. We always round up to the closest +// 8-byte window. As GWP-ASan's malloc(X) can always get exactly an X-sized +// allocation, an allocation that rounds up to 16-bytes will always be given a +// 16-byte aligned allocation. +static size_t alignBionic(size_t RealAllocationSize) { + if (RealAllocationSize % 8 == 0) + return RealAllocationSize; + return RealAllocationSize + 8 - (RealAllocationSize % 8); +} + +static size_t alignPowerOfTwo(size_t RealAllocationSize) { + if (RealAllocationSize <= 2) + return RealAllocationSize; + if (RealAllocationSize <= 4) + return 4; + if (RealAllocationSize <= 8) + return 8; + if (RealAllocationSize % 16 == 0) + return RealAllocationSize; + return RealAllocationSize + 16 - (RealAllocationSize % 16); +} + +#ifdef __BIONIC__ +static constexpr AlignmentStrategy PlatformDefaultAlignment = + AlignmentStrategy::BIONIC; +#else // __BIONIC__ +static constexpr AlignmentStrategy PlatformDefaultAlignment = + AlignmentStrategy::POWER_OF_TWO; +#endif // __BIONIC__ + +size_t rightAlignedAllocationSize(size_t RealAllocationSize, + AlignmentStrategy Align) { + assert(RealAllocationSize > 0); + if (Align == AlignmentStrategy::DEFAULT) + Align = PlatformDefaultAlignment; + + switch (Align) { + case AlignmentStrategy::BIONIC: + return alignBionic(RealAllocationSize); + case AlignmentStrategy::POWER_OF_TWO: + return alignPowerOfTwo(RealAllocationSize); + case AlignmentStrategy::PERFECT: + return RealAllocationSize; + case AlignmentStrategy::DEFAULT: + __builtin_unreachable(); + } + __builtin_unreachable(); +} + +} // namespace gwp_asan |