1 //===-- asan_errors.h -------------------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // This file is a part of AddressSanitizer, an address sanity checker.
12 // ASan-private header for error structures.
13 //===----------------------------------------------------------------------===//
17 #include "asan_descriptions.h"
18 #include "asan_scariness_score.h"
19 #include "sanitizer_common/sanitizer_common.h"
24 ErrorBase() = default;
25 explicit ErrorBase(u32 tid_) : tid(tid_) {}
26 ScarinessScoreBase scariness;
30 struct ErrorStackOverflow : ErrorBase {
31 uptr addr, pc, bp, sp;
32 // ErrorStackOverflow never owns the context.
34 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
36 ErrorStackOverflow() = default;
37 ErrorStackOverflow(u32 tid, const SignalContext &sig)
43 context(sig.context) {
45 scariness.Scare(10, "stack-overflow");
50 struct ErrorDeadlySignal : ErrorBase {
51 uptr addr, pc, bp, sp;
52 // ErrorDeadlySignal never owns the context.
55 SignalContext::WriteFlag write_flag;
56 bool is_memory_access;
57 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
59 ErrorDeadlySignal() = default;
60 ErrorDeadlySignal(u32 tid, const SignalContext &sig, int signo_)
68 write_flag(sig.write_flag),
69 is_memory_access(sig.is_memory_access) {
71 if (is_memory_access) {
72 if (addr < GetPageSizeCached()) {
73 scariness.Scare(10, "null-deref");
74 } else if (addr == pc) {
75 scariness.Scare(60, "wild-jump");
76 } else if (write_flag == SignalContext::WRITE) {
77 scariness.Scare(30, "wild-addr-write");
78 } else if (write_flag == SignalContext::READ) {
79 scariness.Scare(20, "wild-addr-read");
81 scariness.Scare(25, "wild-addr");
84 scariness.Scare(10, "signal");
90 struct ErrorDoubleFree : ErrorBase {
91 // ErrorDoubleFree doesn't own the stack trace.
92 const BufferedStackTrace *second_free_stack;
93 HeapAddressDescription addr_description;
94 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
96 ErrorDoubleFree() = default;
97 ErrorDoubleFree(u32 tid, BufferedStackTrace *stack, uptr addr)
98 : ErrorBase(tid), second_free_stack(stack) {
99 CHECK_GT(second_free_stack->size, 0);
100 GetHeapAddressInformation(addr, 1, &addr_description);
102 scariness.Scare(42, "double-free");
107 struct ErrorNewDeleteSizeMismatch : ErrorBase {
108 // ErrorNewDeleteSizeMismatch doesn't own the stack trace.
109 const BufferedStackTrace *free_stack;
110 HeapAddressDescription addr_description;
112 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
114 ErrorNewDeleteSizeMismatch() = default;
115 ErrorNewDeleteSizeMismatch(u32 tid, BufferedStackTrace *stack, uptr addr,
117 : ErrorBase(tid), free_stack(stack), delete_size(delete_size_) {
118 GetHeapAddressInformation(addr, 1, &addr_description);
120 scariness.Scare(10, "new-delete-type-mismatch");
125 struct ErrorFreeNotMalloced : ErrorBase {
126 // ErrorFreeNotMalloced doesn't own the stack trace.
127 const BufferedStackTrace *free_stack;
128 AddressDescription addr_description;
129 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
131 ErrorFreeNotMalloced() = default;
132 ErrorFreeNotMalloced(u32 tid, BufferedStackTrace *stack, uptr addr)
135 addr_description(addr, /*shouldLockThreadRegistry=*/false) {
137 scariness.Scare(40, "bad-free");
142 struct ErrorAllocTypeMismatch : ErrorBase {
143 // ErrorAllocTypeMismatch doesn't own the stack trace.
144 const BufferedStackTrace *dealloc_stack;
145 HeapAddressDescription addr_description;
146 AllocType alloc_type, dealloc_type;
147 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
149 ErrorAllocTypeMismatch() = default;
150 ErrorAllocTypeMismatch(u32 tid, BufferedStackTrace *stack, uptr addr,
151 AllocType alloc_type_, AllocType dealloc_type_)
153 dealloc_stack(stack),
154 alloc_type(alloc_type_),
155 dealloc_type(dealloc_type_) {
156 GetHeapAddressInformation(addr, 1, &addr_description);
158 scariness.Scare(10, "alloc-dealloc-mismatch");
163 struct ErrorMallocUsableSizeNotOwned : ErrorBase {
164 // ErrorMallocUsableSizeNotOwned doesn't own the stack trace.
165 const BufferedStackTrace *stack;
166 AddressDescription addr_description;
167 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
169 ErrorMallocUsableSizeNotOwned() = default;
170 ErrorMallocUsableSizeNotOwned(u32 tid, BufferedStackTrace *stack_, uptr addr)
173 addr_description(addr, /*shouldLockThreadRegistry=*/false) {
175 scariness.Scare(10, "bad-malloc_usable_size");
180 struct ErrorSanitizerGetAllocatedSizeNotOwned : ErrorBase {
181 // ErrorSanitizerGetAllocatedSizeNotOwned doesn't own the stack trace.
182 const BufferedStackTrace *stack;
183 AddressDescription addr_description;
184 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
186 ErrorSanitizerGetAllocatedSizeNotOwned() = default;
187 ErrorSanitizerGetAllocatedSizeNotOwned(u32 tid, BufferedStackTrace *stack_,
191 addr_description(addr, /*shouldLockThreadRegistry=*/false) {
193 scariness.Scare(10, "bad-__sanitizer_get_allocated_size");
198 struct ErrorStringFunctionMemoryRangesOverlap : ErrorBase {
199 // ErrorStringFunctionMemoryRangesOverlap doesn't own the stack trace.
200 const BufferedStackTrace *stack;
201 uptr length1, length2;
202 AddressDescription addr1_description;
203 AddressDescription addr2_description;
204 const char *function;
205 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
207 ErrorStringFunctionMemoryRangesOverlap() = default;
208 ErrorStringFunctionMemoryRangesOverlap(u32 tid, BufferedStackTrace *stack_,
209 uptr addr1, uptr length1_, uptr addr2,
210 uptr length2_, const char *function_)
215 addr1_description(addr1, length1, /*shouldLockThreadRegistry=*/false),
216 addr2_description(addr2, length2, /*shouldLockThreadRegistry=*/false),
217 function(function_) {
219 internal_snprintf(bug_type, sizeof(bug_type), "%s-param-overlap", function);
221 scariness.Scare(10, bug_type);
226 struct ErrorStringFunctionSizeOverflow : ErrorBase {
227 // ErrorStringFunctionSizeOverflow doesn't own the stack trace.
228 const BufferedStackTrace *stack;
229 AddressDescription addr_description;
231 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
233 ErrorStringFunctionSizeOverflow() = default;
234 ErrorStringFunctionSizeOverflow(u32 tid, BufferedStackTrace *stack_,
235 uptr addr, uptr size_)
238 addr_description(addr, /*shouldLockThreadRegistry=*/false),
241 scariness.Scare(10, "negative-size-param");
246 struct ErrorBadParamsToAnnotateContiguousContainer : ErrorBase {
247 // ErrorBadParamsToAnnotateContiguousContainer doesn't own the stack trace.
248 const BufferedStackTrace *stack;
249 uptr beg, end, old_mid, new_mid;
250 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
252 ErrorBadParamsToAnnotateContiguousContainer() = default;
253 // PS4: Do we want an AddressDescription for beg?
254 ErrorBadParamsToAnnotateContiguousContainer(u32 tid,
255 BufferedStackTrace *stack_,
256 uptr beg_, uptr end_,
257 uptr old_mid_, uptr new_mid_)
265 scariness.Scare(10, "bad-__sanitizer_annotate_contiguous_container");
270 struct ErrorODRViolation : ErrorBase {
271 __asan_global global1, global2;
272 u32 stack_id1, stack_id2;
273 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
275 ErrorODRViolation() = default;
276 ErrorODRViolation(u32 tid, const __asan_global *g1, u32 stack_id1_,
277 const __asan_global *g2, u32 stack_id2_)
281 stack_id1(stack_id1_),
282 stack_id2(stack_id2_) {
284 scariness.Scare(10, "odr-violation");
289 struct ErrorInvalidPointerPair : ErrorBase {
291 AddressDescription addr1_description;
292 AddressDescription addr2_description;
293 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
295 ErrorInvalidPointerPair() = default;
296 ErrorInvalidPointerPair(u32 tid, uptr pc_, uptr bp_, uptr sp_, uptr p1,
302 addr1_description(p1, 1, /*shouldLockThreadRegistry=*/false),
303 addr2_description(p2, 1, /*shouldLockThreadRegistry=*/false) {
305 scariness.Scare(10, "invalid-pointer-pair");
310 struct ErrorGeneric : ErrorBase {
311 AddressDescription addr_description;
314 const char *bug_descr;
317 // VS2013 doesn't implement unrestricted unions, so we need a trivial default
319 ErrorGeneric() = default;
320 ErrorGeneric(u32 tid, uptr addr, uptr pc_, uptr bp_, uptr sp_, bool is_write_,
326 #define ASAN_FOR_EACH_ERROR_KIND(macro) \
327 macro(StackOverflow) \
328 macro(DeadlySignal) \
330 macro(NewDeleteSizeMismatch) \
331 macro(FreeNotMalloced) \
332 macro(AllocTypeMismatch) \
333 macro(MallocUsableSizeNotOwned) \
334 macro(SanitizerGetAllocatedSizeNotOwned) \
335 macro(StringFunctionMemoryRangesOverlap) \
336 macro(StringFunctionSizeOverflow) \
337 macro(BadParamsToAnnotateContiguousContainer) \
338 macro(ODRViolation) \
339 macro(InvalidPointerPair) \
343 #define ASAN_DEFINE_ERROR_KIND(name) kErrorKind##name,
344 #define ASAN_ERROR_DESCRIPTION_MEMBER(name) Error##name name;
345 #define ASAN_ERROR_DESCRIPTION_CONSTRUCTOR(name) \
346 ErrorDescription(Error##name const &e) : kind(kErrorKind##name), name(e) {}
347 #define ASAN_ERROR_DESCRIPTION_PRINT(name) \
348 case kErrorKind##name: \
352 kErrorKindInvalid = 0,
353 ASAN_FOR_EACH_ERROR_KIND(ASAN_DEFINE_ERROR_KIND)
356 struct ErrorDescription {
358 // We're using a tagged union because it allows us to have a trivially
359 // copiable type and use the same structures as the public interface.
361 // We can add a wrapper around it to make it "more c++-like", but that would
362 // add a lot of code and the benefit wouldn't be that big.
365 ASAN_FOR_EACH_ERROR_KIND(ASAN_ERROR_DESCRIPTION_MEMBER)
368 ErrorDescription() { internal_memset(this, 0, sizeof(*this)); }
369 ASAN_FOR_EACH_ERROR_KIND(ASAN_ERROR_DESCRIPTION_CONSTRUCTOR)
371 bool IsValid() { return kind != kErrorKindInvalid; }
374 ASAN_FOR_EACH_ERROR_KIND(ASAN_ERROR_DESCRIPTION_PRINT)
375 case kErrorKindInvalid:
382 #undef ASAN_FOR_EACH_ERROR_KIND
383 #undef ASAN_DEFINE_ERROR_KIND
384 #undef ASAN_ERROR_DESCRIPTION_MEMBER
385 #undef ASAN_ERROR_DESCRIPTION_CONSTRUCTOR
386 #undef ASAN_ERROR_DESCRIPTION_PRINT
388 } // namespace __asan
390 #endif // ASAN_ERRORS_H