1 //===----------------------------------------------------------------------===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
10 #define ASAN_TESTING_H
12 #include "test_macros.h"
16 #include <type_traits>
18 #if TEST_HAS_FEATURE(address_sanitizer)
19 extern "C" int __sanitizer_verify_contiguous_container(const void* beg
, const void* mid
, const void* end
);
21 template <typename T
, typename Alloc
>
22 TEST_CONSTEXPR
bool is_contiguous_container_asan_correct(const std::vector
<T
, Alloc
>& c
) {
23 if (TEST_IS_CONSTANT_EVALUATED
)
25 if (std::is_same
<Alloc
, std::allocator
<T
> >::value
&& c
.data() != NULL
)
26 return __sanitizer_verify_contiguous_container(c
.data(), c
.data() + c
.size(), c
.data() + c
.capacity()) != 0;
30 template <typename T
, typename Alloc
>
31 TEST_CONSTEXPR
bool is_contiguous_container_asan_correct(const std::vector
<T
, Alloc
>&) {
34 #endif // TEST_HAS_FEATURE(address_sanitizer)
36 #if TEST_HAS_FEATURE(address_sanitizer)
37 extern "C" int __sanitizer_verify_double_ended_contiguous_container(
38 const void* beg
, const void* con_beg
, const void* con_end
, const void* end
);
39 extern "C" bool __sanitizer_is_annotable(const void* address
, const unsigned long size
);
42 template <class T
, class Alloc
>
43 TEST_CONSTEXPR
bool is_double_ended_contiguous_container_asan_correct(const std::deque
<T
, Alloc
>& c
) {
44 if (TEST_IS_CONSTANT_EVALUATED
)
46 if (std::is_same
<Alloc
, std::allocator
<T
> >::value
)
47 return c
.__verify_asan_annotations();
52 template <class T
, class Alloc
>
53 TEST_CONSTEXPR
bool is_double_ended_contiguous_container_asan_correct(const std::deque
<T
, Alloc
>&) {
58 #if TEST_HAS_FEATURE(address_sanitizer)
60 bool is_string_short(S
const& s
) {
61 // We do not have access to __is_long(), but we can check if strings
62 // buffer is inside strings memory. If strings memory contains its content,
63 // SSO is in use. To check it, we can just confirm that the beginning is in
64 // the string object memory block.
65 // &s - beginning of objects memory
66 // &s[0] - beginning of the buffer
67 // (&s+1) - end of objects memory
68 return (void*)std::addressof(s
) <= (void*)std::addressof(s
[0]) &&
69 (void*)std::addressof(s
[0]) < (void*)(std::addressof(s
) + 1);
72 template <typename ChrT
, typename TraitsT
, typename Alloc
>
73 TEST_CONSTEXPR
bool is_string_asan_correct(const std::basic_string
<ChrT
, TraitsT
, Alloc
>& c
) {
74 if (TEST_IS_CONSTANT_EVALUATED
)
77 if (!is_string_short(c
) || _LIBCPP_SHORT_STRING_ANNOTATIONS_ALLOWED
) {
78 if (std::__asan_annotate_container_with_allocator
<Alloc
>::value
)
79 return __sanitizer_verify_contiguous_container(c
.data(), c
.data() + c
.size() + 1, c
.data() + c
.capacity() + 1) !=
82 return __sanitizer_verify_contiguous_container(
83 c
.data(), c
.data() + c
.capacity() + 1, c
.data() + c
.capacity() + 1) != 0;
85 return __sanitizer_verify_contiguous_container(std::addressof(c
), std::addressof(c
) + 1, std::addressof(c
) + 1) !=
91 template <typename ChrT
, typename TraitsT
, typename Alloc
>
92 TEST_CONSTEXPR
bool is_string_asan_correct(const std::basic_string
<ChrT
, TraitsT
, Alloc
>&) {
95 #endif // TEST_HAS_FEATURE(address_sanitizer)
96 #endif // ASAN_TESTING_H