[llvm] 9d43f6d - [LowerConstantIntrinsics] avoid crashing on alloca with unexpected operand type
Sanjay Patel via llvm-commits
llvm-commits at lists.llvm.org
Mon Apr 19 10:21:04 PDT 2021
Author: Sanjay Patel
Date: 2021-04-19T13:06:29-04:00
New Revision: 9d43f6d7cee8887cb2a7a2442dffa4ef21ef4446
URL: https://github.com/llvm/llvm-project/commit/9d43f6d7cee8887cb2a7a2442dffa4ef21ef4446
DIFF: https://github.com/llvm/llvm-project/commit/9d43f6d7cee8887cb2a7a2442dffa4ef21ef4446.diff
LOG: [LowerConstantIntrinsics] avoid crashing on alloca with unexpected operand type
The test here is reduced from the fuzzer-generated crasher in:
https://llvm.org/PR50023
https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=33395
I don't know if this is the best or complete solution, but the
zext of the i42 type appears to match the behavior if we run a
weird type example like this through the IR optimizer with -O1.
Differential Revision: https://reviews.llvm.org/D100766
Added:
Modified:
llvm/lib/Analysis/MemoryBuiltins.cpp
llvm/test/Transforms/LowerConstantIntrinsics/objectsize_basic.ll
Removed:
################################################################################
diff --git a/llvm/lib/Analysis/MemoryBuiltins.cpp b/llvm/lib/Analysis/MemoryBuiltins.cpp
index 5dda96a2ca947..51a59efb94f36 100644
--- a/llvm/lib/Analysis/MemoryBuiltins.cpp
+++ b/llvm/lib/Analysis/MemoryBuiltins.cpp
@@ -955,7 +955,14 @@ SizeOffsetEvalType ObjectSizeOffsetEvaluator::visitAllocaInst(AllocaInst &I) {
// must be a VLA
assert(I.isArrayAllocation());
- Value *ArraySize = I.getArraySize();
+
+ // If needed, adjust the alloca's operand size to match the pointer size.
+ // Subsequent math operations expect the types to match.
+ Value *ArraySize = Builder.CreateZExtOrTrunc(
+ I.getArraySize(), DL.getIntPtrType(I.getContext()));
+ assert(ArraySize->getType() == Zero->getType() &&
+ "Expected zero constant to have pointer type");
+
Value *Size = ConstantInt::get(ArraySize->getType(),
DL.getTypeAllocSize(I.getAllocatedType()));
Size = Builder.CreateMul(Size, ArraySize);
diff --git a/llvm/test/Transforms/LowerConstantIntrinsics/objectsize_basic.ll b/llvm/test/Transforms/LowerConstantIntrinsics/objectsize_basic.ll
index ab59b8950d700..6d5e5080f13c7 100644
--- a/llvm/test/Transforms/LowerConstantIntrinsics/objectsize_basic.ll
+++ b/llvm/test/Transforms/LowerConstantIntrinsics/objectsize_basic.ll
@@ -97,3 +97,25 @@ define i64 @test_objectsize_byref_arg([42 x i8]* byref([42 x i8]) %ptr) {
%size = tail call i64 @llvm.objectsize.i64(i8* %cast, i1 true, i1 false, i1 false)
ret i64 %size
}
+
+; https://llvm.org/PR50023
+; The alloca operand type may not match pointer type size.
+
+define i64 @vla_pointer_size_mismatch(i42 %x) {
+; CHECK-LABEL: @vla_pointer_size_mismatch(
+; CHECK-NEXT: [[TMP1:%.*]] = zext i42 [[X:%.*]] to i64
+; CHECK-NEXT: [[TMP2:%.*]] = mul i64 1, [[TMP1]]
+; CHECK-NEXT: [[A:%.*]] = alloca i8, i42 [[X]], align 1
+; CHECK-NEXT: [[G1:%.*]] = getelementptr i8, i8* [[A]], i8 17
+; CHECK-NEXT: [[TMP3:%.*]] = sub i64 [[TMP2]], 17
+; CHECK-NEXT: [[TMP4:%.*]] = icmp ult i64 [[TMP2]], 17
+; CHECK-NEXT: [[TMP5:%.*]] = select i1 [[TMP4]], i64 0, i64 [[TMP3]]
+; CHECK-NEXT: [[TMP6:%.*]] = icmp ne i64 [[TMP5]], -1
+; CHECK-NEXT: call void @llvm.assume(i1 [[TMP6]])
+; CHECK-NEXT: ret i64 [[TMP5]]
+;
+ %A = alloca i8, i42 %x, align 1
+ %G1 = getelementptr i8, i8* %A, i8 17
+ %objsize = call i64 @llvm.objectsize.i64(i8* %G1, i1 false, i1 true, i1 true)
+ ret i64 %objsize
+}
More information about the llvm-commits
mailing list