1238106Sdes//===-- ubsan_handlers.h ----------------------------------------*- C++ -*-===//
2238106Sdes//
3238106Sdes//                     The LLVM Compiler Infrastructure
4238106Sdes//
5238106Sdes// This file is distributed under the University of Illinois Open Source
6238106Sdes// License. See LICENSE.TXT for details.
7238106Sdes//
8238106Sdes//===----------------------------------------------------------------------===//
9238106Sdes//
10238106Sdes// Entry points to the runtime library for Clang's undefined behavior sanitizer.
11238106Sdes//
12238106Sdes//===----------------------------------------------------------------------===//
13238106Sdes#ifndef UBSAN_HANDLERS_H
14238106Sdes#define UBSAN_HANDLERS_H
15238106Sdes
16238106Sdes#include "ubsan_value.h"
17238106Sdes
18238106Sdesnamespace __ubsan {
19238106Sdes
20238106Sdesstruct TypeMismatchData {
21238106Sdes  SourceLocation Loc;
22238106Sdes  const TypeDescriptor &Type;
23238106Sdes  unsigned char LogAlignment;
24269257Sdes  unsigned char TypeCheckKind;
25269257Sdes};
26269257Sdes
27269257Sdes#define UNRECOVERABLE(checkname, ...) \
28269257Sdes  extern "C" SANITIZER_INTERFACE_ATTRIBUTE NORETURN \
29269257Sdes    void __ubsan_handle_ ## checkname( __VA_ARGS__ );
30269257Sdes
31269257Sdes#define RECOVERABLE(checkname, ...) \
32269257Sdes  extern "C" SANITIZER_INTERFACE_ATTRIBUTE \
33269257Sdes    void __ubsan_handle_ ## checkname( __VA_ARGS__ ); \
34238106Sdes  extern "C" SANITIZER_INTERFACE_ATTRIBUTE NORETURN \
35238106Sdes    void __ubsan_handle_ ## checkname ## _abort( __VA_ARGS__ );
36238106Sdes
37238106Sdes/// \brief Handle a runtime type check failure, caused by either a misaligned
38238106Sdes/// pointer, a null pointer, or a pointer to insufficient storage for the
39238106Sdes/// type.
40238106SdesRECOVERABLE(type_mismatch_v1, TypeMismatchData *Data, ValueHandle Pointer)
41238106Sdes
42238106Sdesstruct OverflowData {
43238106Sdes  SourceLocation Loc;
44238106Sdes  const TypeDescriptor &Type;
45238106Sdes};
46238106Sdes
47238106Sdes/// \brief Handle an integer addition overflow.
48238106SdesRECOVERABLE(add_overflow, OverflowData *Data, ValueHandle LHS, ValueHandle RHS)
49238106Sdes
50238106Sdes/// \brief Handle an integer subtraction overflow.
51238106SdesRECOVERABLE(sub_overflow, OverflowData *Data, ValueHandle LHS, ValueHandle RHS)
52238106Sdes
53238106Sdes/// \brief Handle an integer multiplication overflow.
54238106SdesRECOVERABLE(mul_overflow, OverflowData *Data, ValueHandle LHS, ValueHandle RHS)
55238106Sdes
56238106Sdes/// \brief Handle a signed integer overflow for a unary negate operator.
57238106SdesRECOVERABLE(negate_overflow, OverflowData *Data, ValueHandle OldVal)
58238106Sdes
59238106Sdes/// \brief Handle an INT_MIN/-1 overflow or division by zero.
60238106SdesRECOVERABLE(divrem_overflow, OverflowData *Data,
61238106Sdes            ValueHandle LHS, ValueHandle RHS)
62238106Sdes
63269257Sdesstruct ShiftOutOfBoundsData {
64269257Sdes  SourceLocation Loc;
65249141Sdes  const TypeDescriptor &LHSType;
66249141Sdes  const TypeDescriptor &RHSType;
67249141Sdes};
68249141Sdes
69238106Sdes/// \brief Handle a shift where the RHS is out of bounds or a left shift where
70238106Sdes/// the LHS is negative or overflows.
71238106SdesRECOVERABLE(shift_out_of_bounds, ShiftOutOfBoundsData *Data,
72238106Sdes            ValueHandle LHS, ValueHandle RHS)
73238106Sdes
74238106Sdesstruct OutOfBoundsData {
75238106Sdes  SourceLocation Loc;
76238106Sdes  const TypeDescriptor &ArrayType;
77238106Sdes  const TypeDescriptor &IndexType;
78238106Sdes};
79238106Sdes
80238106Sdes/// \brief Handle an array index out of bounds error.
81238106SdesRECOVERABLE(out_of_bounds, OutOfBoundsData *Data, ValueHandle Index)
82238106Sdes
83238106Sdesstruct UnreachableData {
84238106Sdes  SourceLocation Loc;
85238106Sdes};
86238106Sdes
87238106Sdes/// \brief Handle a __builtin_unreachable which is reached.
88285206SdesUNRECOVERABLE(builtin_unreachable, UnreachableData *Data)
89285206Sdes/// \brief Handle reaching the end of a value-returning function.
90238106SdesUNRECOVERABLE(missing_return, UnreachableData *Data)
91238106Sdes
92238106Sdesstruct VLABoundData {
93238106Sdes  SourceLocation Loc;
94238106Sdes  const TypeDescriptor &Type;
95238106Sdes};
96238106Sdes
97238106Sdes/// \brief Handle a VLA with a non-positive bound.
98238106SdesRECOVERABLE(vla_bound_not_positive, VLABoundData *Data, ValueHandle Bound)
99238106Sdes
100238106Sdes// Keeping this around for binary compatibility with (sanitized) programs
101238106Sdes// compiled with older compilers.
102238106Sdesstruct FloatCastOverflowData {
103238106Sdes  const TypeDescriptor &FromType;
104238106Sdes  const TypeDescriptor &ToType;
105238106Sdes};
106238106Sdes
107238106Sdesstruct FloatCastOverflowDataV2 {
108238106Sdes  SourceLocation Loc;
109238106Sdes  const TypeDescriptor &FromType;
110238106Sdes  const TypeDescriptor &ToType;
111238106Sdes};
112238106Sdes
113238106Sdes/// Handle overflow in a conversion to or from a floating-point type.
114238106Sdes/// void *Data is one of FloatCastOverflowData* or FloatCastOverflowDataV2*
115238106SdesRECOVERABLE(float_cast_overflow, void *Data, ValueHandle From)
116238106Sdes
117238106Sdesstruct InvalidValueData {
118238106Sdes  SourceLocation Loc;
119238106Sdes  const TypeDescriptor &Type;
120238106Sdes};
121238106Sdes
122238106Sdes/// \brief Handle a load of an invalid value for the type.
123238106SdesRECOVERABLE(load_invalid_value, InvalidValueData *Data, ValueHandle Val)
124238106Sdes
125238106Sdes/// Known implicit conversion check kinds.
126238106Sdes/// Keep in sync with the enum of the same name in CGExprScalar.cpp
127238106Sdesenum ImplicitConversionCheckKind : unsigned char {
128238106Sdes  ICCK_IntegerTruncation = 0, // Legacy, was only used by clang 7.
129238106Sdes  ICCK_UnsignedIntegerTruncation = 1,
130238106Sdes  ICCK_SignedIntegerTruncation = 2,
131238106Sdes  ICCK_IntegerSignChange = 3,
132238106Sdes  ICCK_SignedIntegerTruncationOrSignChange = 4,
133238106Sdes};
134238106Sdes
135238106Sdesstruct ImplicitConversionData {
136238106Sdes  SourceLocation Loc;
137238106Sdes  const TypeDescriptor &FromType;
138238106Sdes  const TypeDescriptor &ToType;
139238106Sdes  /* ImplicitConversionCheckKind */ unsigned char Kind;
140238106Sdes};
141238106Sdes
142238106Sdes/// \brief Implict conversion that changed the value.
143238106SdesRECOVERABLE(implicit_conversion, ImplicitConversionData *Data, ValueHandle Src,
144238106Sdes            ValueHandle Dst)
145238106Sdes
146238106Sdes/// Known builtin check kinds.
147238106Sdes/// Keep in sync with the enum of the same name in CodeGenFunction.h
148238106Sdesenum BuiltinCheckKind : unsigned char {
149238106Sdes  BCK_CTZPassedZero,
150238106Sdes  BCK_CLZPassedZero,
151238106Sdes};
152238106Sdes
153238106Sdesstruct InvalidBuiltinData {
154238106Sdes  SourceLocation Loc;
155238106Sdes  unsigned char Kind;
156238106Sdes};
157238106Sdes
158238106Sdes/// Handle a builtin called in an invalid way.
159238106SdesRECOVERABLE(invalid_builtin, InvalidBuiltinData *Data)
160238106Sdes
161238106Sdesstruct FunctionTypeMismatchData {
162238106Sdes  SourceLocation Loc;
163238106Sdes  const TypeDescriptor &Type;
164238106Sdes};
165238106Sdes
166238106SdesRECOVERABLE(function_type_mismatch,
167238106Sdes            FunctionTypeMismatchData *Data,
168238106Sdes            ValueHandle Val)
169238106Sdes
170238106Sdesstruct NonNullReturnData {
171238106Sdes  SourceLocation AttrLoc;
172238106Sdes};
173238106Sdes
174238106Sdes/// \brief Handle returning null from function with the returns_nonnull
175238106Sdes/// attribute, or a return type annotated with _Nonnull.
176238106SdesRECOVERABLE(nonnull_return_v1, NonNullReturnData *Data, SourceLocation *Loc)
177238106SdesRECOVERABLE(nullability_return_v1, NonNullReturnData *Data, SourceLocation *Loc)
178269257Sdes
179238106Sdesstruct NonNullArgData {
180238106Sdes  SourceLocation Loc;
181238106Sdes  SourceLocation AttrLoc;
182238106Sdes  int ArgIndex;
183238106Sdes};
184238106Sdes
185238106Sdes/// \brief Handle passing null pointer to a function parameter with the nonnull
186238106Sdes/// attribute, or a _Nonnull type annotation.
187238106SdesRECOVERABLE(nonnull_arg, NonNullArgData *Data)
188238106SdesRECOVERABLE(nullability_arg, NonNullArgData *Data)
189238106Sdes
190238106Sdesstruct PointerOverflowData {
191238106Sdes  SourceLocation Loc;
192238106Sdes};
193238106Sdes
194238106SdesRECOVERABLE(pointer_overflow, PointerOverflowData *Data, ValueHandle Base,
195238106Sdes            ValueHandle Result)
196238106Sdes
197269257Sdes/// \brief Known CFI check kinds.
198238106Sdes/// Keep in sync with the enum of the same name in CodeGenFunction.h
199238106Sdesenum CFITypeCheckKind : unsigned char {
200238106Sdes  CFITCK_VCall,
201238106Sdes  CFITCK_NVCall,
202238106Sdes  CFITCK_DerivedCast,
203238106Sdes  CFITCK_UnrelatedCast,
204238106Sdes  CFITCK_ICall,
205238106Sdes  CFITCK_NVMFCall,
206238106Sdes  CFITCK_VMFCall,
207238106Sdes};
208238106Sdes
209238106Sdesstruct CFICheckFailData {
210238106Sdes  CFITypeCheckKind CheckKind;
211238106Sdes  SourceLocation Loc;
212238106Sdes  const TypeDescriptor &Type;
213238106Sdes};
214238106Sdes
215238106Sdes/// \brief Handle control flow integrity failures.
216238106SdesRECOVERABLE(cfi_check_fail, CFICheckFailData *Data, ValueHandle Function,
217238106Sdes            uptr VtableIsValid)
218238106Sdes
219238106Sdesstruct ReportOptions;
220238106Sdes
221269257Sdesextern "C" SANITIZER_INTERFACE_ATTRIBUTE void __ubsan_handle_cfi_bad_type(
222269257Sdes    CFICheckFailData *Data, ValueHandle Vtable, bool ValidVtable,
223238106Sdes    ReportOptions Opts);
224238106Sdes
225238106Sdes}
226238106Sdes
227238106Sdes#endif // UBSAN_HANDLERS_H
228238106Sdes