Index: lib/Analysis/ConstantFolding.cpp =================================================================== --- lib/Analysis/ConstantFolding.cpp +++ lib/Analysis/ConstantFolding.cpp @@ -544,11 +544,11 @@ int64_t InitializerSize = DL.getTypeAllocSize(GV->getInitializer()->getType()); // If we're not accessing anything in this constant, the result is undefined. - if (Offset + BytesLoaded <= 0) + if (Offset >= InitializerSize) return UndefValue::get(IntType); // If we're not accessing anything in this constant, the result is undefined. - if (Offset >= InitializerSize) + if (Offset + BytesLoaded <= 0) return UndefValue::get(IntType); unsigned char RawBytes[32] = {0}; Index: test/Transforms/SCCP/ubsan_overflow.ll =================================================================== --- /dev/null +++ test/Transforms/SCCP/ubsan_overflow.ll @@ -0,0 +1,13 @@ +; RUN: opt -sccp -S %s | FileCheck %s + +@0 = private unnamed_addr constant [16 x i8] c"\01\00\00\00\01\01\00\00\01\01\01\00\01\01\01\01" + +; CHECK_LABEL: @foo +define void @foo() local_unnamed_addr { +entry: + %0 = add nuw nsw i64 0, -1 + %1 = lshr i64 %0, 1 + %2 = getelementptr inbounds [4 x [4 x i8]], [4 x [4 x i8]]* bitcast ([16 x i8]* @0 to [4 x [4 x i8]]*), i64 0, i64 0, i64 %1 + %3 = load i8, i8* %2, align 1 + unreachable +}