Skip to content

Commit 298e292

Browse files
authored
[IR] Add overflow check in AllocaInst::getAllocationSize (#97170)
Fixes #91380.
1 parent a6d289d commit 298e292

File tree

2 files changed

+16
-4
lines changed

2 files changed

+16
-4
lines changed

llvm/lib/IR/Instructions.cpp

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737
#include "llvm/IR/Value.h"
3838
#include "llvm/Support/AtomicOrdering.h"
3939
#include "llvm/Support/Casting.h"
40+
#include "llvm/Support/CheckedArithmetic.h"
4041
#include "llvm/Support/ErrorHandling.h"
4142
#include "llvm/Support/MathExtras.h"
4243
#include "llvm/Support/ModRef.h"
@@ -65,17 +66,25 @@ AllocaInst::getAllocationSize(const DataLayout &DL) const {
6566
if (!C)
6667
return std::nullopt;
6768
assert(!Size.isScalable() && "Array elements cannot have a scalable size");
68-
Size *= C->getZExtValue();
69+
auto CheckedProd =
70+
checkedMulUnsigned(Size.getKnownMinValue(), C->getZExtValue());
71+
if (!CheckedProd)
72+
return std::nullopt;
73+
return TypeSize::getFixed(*CheckedProd);
6974
}
7075
return Size;
7176
}
7277

7378
std::optional<TypeSize>
7479
AllocaInst::getAllocationSizeInBits(const DataLayout &DL) const {
7580
std::optional<TypeSize> Size = getAllocationSize(DL);
76-
if (Size)
77-
return *Size * 8;
78-
return std::nullopt;
81+
if (!Size)
82+
return std::nullopt;
83+
auto CheckedProd = checkedMulUnsigned(Size->getKnownMinValue(),
84+
static_cast<TypeSize::ScalarTy>(8));
85+
if (!CheckedProd)
86+
return std::nullopt;
87+
return TypeSize::get(*CheckedProd, Size->isScalable());
7988
}
8089

8190
//===----------------------------------------------------------------------===//

llvm/unittests/IR/InstructionsTest.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1750,6 +1750,7 @@ TEST(InstructionsTest, AllocaInst) {
17501750
%F = alloca [2 x half]
17511751
%G = alloca [2 x [3 x i128]]
17521752
%H = alloca %T
1753+
%I = alloca i32, i64 9223372036854775807
17531754
ret void
17541755
}
17551756
)");
@@ -1766,6 +1767,7 @@ TEST(InstructionsTest, AllocaInst) {
17661767
AllocaInst &F = cast<AllocaInst>(*It++);
17671768
AllocaInst &G = cast<AllocaInst>(*It++);
17681769
AllocaInst &H = cast<AllocaInst>(*It++);
1770+
AllocaInst &I = cast<AllocaInst>(*It++);
17691771
EXPECT_EQ(A.getAllocationSizeInBits(DL), TypeSize::getFixed(32));
17701772
EXPECT_EQ(B.getAllocationSizeInBits(DL), TypeSize::getFixed(128));
17711773
EXPECT_FALSE(C.getAllocationSizeInBits(DL));
@@ -1774,6 +1776,7 @@ TEST(InstructionsTest, AllocaInst) {
17741776
EXPECT_EQ(F.getAllocationSizeInBits(DL), TypeSize::getFixed(32));
17751777
EXPECT_EQ(G.getAllocationSizeInBits(DL), TypeSize::getFixed(768));
17761778
EXPECT_EQ(H.getAllocationSizeInBits(DL), TypeSize::getFixed(160));
1779+
EXPECT_FALSE(I.getAllocationSizeInBits(DL));
17771780
}
17781781

17791782
TEST(InstructionsTest, InsertAtBegin) {

0 commit comments

Comments
 (0)