aboutsummaryrefslogtreecommitdiff
path: root/lib/ubsan
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2018-08-02 17:33:19 +0000
committerDimitry Andric <dim@FreeBSD.org>2018-08-02 17:33:19 +0000
commit005b7ed8f76756d94ef6266ded755ab7863cb936 (patch)
treede2aa8f0c2f604d3b4f81a94dd20ea0c50bf1e68 /lib/ubsan
parent93c1b73a09a52d4a265f683bf1954b08bb430049 (diff)
downloadsrc-005b7ed8f76756d94ef6266ded755ab7863cb936.tar.gz
src-005b7ed8f76756d94ef6266ded755ab7863cb936.zip
Vendor import of compiler-rt trunk r338536:vendor/compiler-rt/compiler-rt-trunk-r338536
Notes
Notes: svn path=/vendor/compiler-rt/dist/; revision=337141 svn path=/vendor/compiler-rt/compiler-rt-trunk-r338536/; revision=337142; tag=vendor/compiler-rt/compiler-rt-trunk-r338536
Diffstat (limited to 'lib/ubsan')
-rw-r--r--lib/ubsan/ubsan_checks.inc2
-rw-r--r--lib/ubsan/ubsan_diag.h2
-rw-r--r--lib/ubsan/ubsan_handlers.cc43
-rw-r--r--lib/ubsan/ubsan_handlers.h17
-rw-r--r--lib/ubsan/ubsan_interface.inc2
5 files changed, 65 insertions, 1 deletions
diff --git a/lib/ubsan/ubsan_checks.inc b/lib/ubsan/ubsan_checks.inc
index 73c69363215a..5a7bdec2df12 100644
--- a/lib/ubsan/ubsan_checks.inc
+++ b/lib/ubsan/ubsan_checks.inc
@@ -30,6 +30,8 @@ UBSAN_CHECK(IntegerDivideByZero, "integer-divide-by-zero",
"integer-divide-by-zero")
UBSAN_CHECK(FloatDivideByZero, "float-divide-by-zero", "float-divide-by-zero")
UBSAN_CHECK(InvalidBuiltin, "invalid-builtin-use", "invalid-builtin-use")
+UBSAN_CHECK(ImplicitIntegerTruncation, "implicit-integer-truncation",
+ "implicit-integer-truncation")
UBSAN_CHECK(InvalidShiftBase, "invalid-shift-base", "shift-base")
UBSAN_CHECK(InvalidShiftExponent, "invalid-shift-exponent", "shift-exponent")
UBSAN_CHECK(OutOfBoundsIndex, "out-of-bounds-index", "bounds")
diff --git a/lib/ubsan/ubsan_diag.h b/lib/ubsan/ubsan_diag.h
index d9ea410c358c..bde749684c65 100644
--- a/lib/ubsan/ubsan_diag.h
+++ b/lib/ubsan/ubsan_diag.h
@@ -178,7 +178,7 @@ public:
};
private:
- static const unsigned MaxArgs = 5;
+ static const unsigned MaxArgs = 8;
static const unsigned MaxRanges = 1;
/// The arguments which have been added to this diagnostic so far.
diff --git a/lib/ubsan/ubsan_handlers.cc b/lib/ubsan/ubsan_handlers.cc
index 49c6bcacbe27..e72a32cf32c2 100644
--- a/lib/ubsan/ubsan_handlers.cc
+++ b/lib/ubsan/ubsan_handlers.cc
@@ -451,6 +451,49 @@ void __ubsan::__ubsan_handle_load_invalid_value_abort(InvalidValueData *Data,
Die();
}
+static void handleImplicitConversion(ImplicitConversionData *Data,
+ ReportOptions Opts, ValueHandle Src,
+ ValueHandle Dst) {
+ SourceLocation Loc = Data->Loc.acquire();
+ ErrorType ET = ErrorType::GenericUB;
+
+ switch (Data->Kind) {
+ case ICCK_IntegerTruncation:
+ ET = ErrorType::ImplicitIntegerTruncation;
+ break;
+ }
+
+ if (ignoreReport(Loc, Opts, ET))
+ return;
+
+ const TypeDescriptor &SrcTy = Data->FromType;
+ const TypeDescriptor &DstTy = Data->ToType;
+
+ ScopedReport R(Opts, Loc, ET);
+
+ // FIXME: is it possible to dump the values as hex with fixed width?
+
+ Diag(Loc, DL_Error, ET,
+ "implicit conversion from type %0 of value %1 (%2-bit, %3signed) to "
+ "type %4 changed the value to %5 (%6-bit, %7signed)")
+ << SrcTy << Value(SrcTy, Src) << SrcTy.getIntegerBitWidth()
+ << (SrcTy.isSignedIntegerTy() ? "" : "un") << DstTy << Value(DstTy, Dst)
+ << DstTy.getIntegerBitWidth() << (DstTy.isSignedIntegerTy() ? "" : "un");
+}
+
+void __ubsan::__ubsan_handle_implicit_conversion(ImplicitConversionData *Data,
+ ValueHandle Src,
+ ValueHandle Dst) {
+ GET_REPORT_OPTIONS(false);
+ handleImplicitConversion(Data, Opts, Src, Dst);
+}
+void __ubsan::__ubsan_handle_implicit_conversion_abort(
+ ImplicitConversionData *Data, ValueHandle Src, ValueHandle Dst) {
+ GET_REPORT_OPTIONS(true);
+ handleImplicitConversion(Data, Opts, Src, Dst);
+ Die();
+}
+
static void handleInvalidBuiltin(InvalidBuiltinData *Data, ReportOptions Opts) {
SourceLocation Loc = Data->Loc.acquire();
ErrorType ET = ErrorType::InvalidBuiltin;
diff --git a/lib/ubsan/ubsan_handlers.h b/lib/ubsan/ubsan_handlers.h
index ed3c8f0b1b0e..07644b7ea15d 100644
--- a/lib/ubsan/ubsan_handlers.h
+++ b/lib/ubsan/ubsan_handlers.h
@@ -122,6 +122,23 @@ struct InvalidValueData {
/// \brief Handle a load of an invalid value for the type.
RECOVERABLE(load_invalid_value, InvalidValueData *Data, ValueHandle Val)
+/// Known implicit conversion check kinds.
+/// Keep in sync with the enum of the same name in CGExprScalar.cpp
+enum ImplicitConversionCheckKind : unsigned char {
+ ICCK_IntegerTruncation = 0,
+};
+
+struct ImplicitConversionData {
+ SourceLocation Loc;
+ const TypeDescriptor &FromType;
+ const TypeDescriptor &ToType;
+ /* ImplicitConversionCheckKind */ unsigned char Kind;
+};
+
+/// \brief Implict conversion that changed the value.
+RECOVERABLE(implicit_conversion, ImplicitConversionData *Data, ValueHandle Src,
+ ValueHandle Dst)
+
/// Known builtin check kinds.
/// Keep in sync with the enum of the same name in CodeGenFunction.h
enum BuiltinCheckKind : unsigned char {
diff --git a/lib/ubsan/ubsan_interface.inc b/lib/ubsan/ubsan_interface.inc
index 782c621a2b47..0be6010ad27b 100644
--- a/lib/ubsan/ubsan_interface.inc
+++ b/lib/ubsan/ubsan_interface.inc
@@ -22,6 +22,8 @@ INTERFACE_FUNCTION(__ubsan_handle_float_cast_overflow)
INTERFACE_FUNCTION(__ubsan_handle_float_cast_overflow_abort)
INTERFACE_FUNCTION(__ubsan_handle_function_type_mismatch)
INTERFACE_FUNCTION(__ubsan_handle_function_type_mismatch_abort)
+INTERFACE_FUNCTION(__ubsan_handle_implicit_conversion)
+INTERFACE_FUNCTION(__ubsan_handle_implicit_conversion_abort)
INTERFACE_FUNCTION(__ubsan_handle_invalid_builtin)
INTERFACE_FUNCTION(__ubsan_handle_invalid_builtin_abort)
INTERFACE_FUNCTION(__ubsan_handle_load_invalid_value)