summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Transforms
diff options
context:
space:
mode:
authorMichael Gottesman <mgottesman@apple.com>2013-06-07 06:16:49 +0000
committerMichael Gottesman <mgottesman@apple.com>2013-06-07 06:16:49 +0000
commit9e7261c87469548754ac83f98a53e985e820a381 (patch)
treed67a34b02a6d35d31c799d2be1469384bf79e54b /llvm/lib/Transforms
parentf95178e67956c1d71f71b7893fb01c9aac3fd691 (diff)
downloadbcm5719-llvm-9e7261c87469548754ac83f98a53e985e820a381.tar.gz
bcm5719-llvm-9e7261c87469548754ac83f98a53e985e820a381.zip
[objc-arc] Ensure that the cfg path count does not overflow when we multiply TopDownPathCount/BottomUpPathCount.
rdar://12480535 llvm-svn: 183489
Diffstat (limited to 'llvm/lib/Transforms')
-rw-r--r--llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp48
1 files changed, 38 insertions, 10 deletions
diff --git a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp
index e6e1ff95aab..fc5cf4e8646 100644
--- a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp
+++ b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp
@@ -670,13 +670,20 @@ namespace {
void MergePred(const BBState &Other);
void MergeSucc(const BBState &Other);
- /// Return the number of possible unique paths from an entry to an exit
+ /// Compute the number of possible unique paths from an entry to an exit
/// which pass through this block. This is only valid after both the
/// top-down and bottom-up traversals are complete.
- unsigned GetAllPathCount() const {
+ ///
+ /// Returns true if overflow occured. Returns false if overflow did not
+ /// occur.
+ bool GetAllPathCountWithOverflow(unsigned &PathCount) const {
assert(TopDownPathCount != 0);
assert(BottomUpPathCount != 0);
- return TopDownPathCount * BottomUpPathCount;
+ unsigned long long Product =
+ (unsigned long long)TopDownPathCount*BottomUpPathCount;
+ PathCount = Product;
+ // Overflow occured if any of the upper bits of Product are set.
+ return Product >> 32;
}
// Specialized CFG utilities.
@@ -2543,8 +2550,14 @@ ObjCARCOpt::ConnectTDBUTraversals(DenseMap<const BasicBlock *, BBState>
const RRInfo &NewRetainReleaseRRI = Jt->second;
assert(NewRetainReleaseRRI.Calls.count(NewRetain));
if (ReleasesToMove.Calls.insert(NewRetainRelease)) {
- OldDelta -=
- BBStates[NewRetainRelease->getParent()].GetAllPathCount();
+
+ // If we overflow when we compute the path count, don't remove/move
+ // anything.
+ const BBState &NRRBBState = BBStates[NewRetainRelease->getParent()];
+ unsigned PathCount;
+ if (NRRBBState.GetAllPathCountWithOverflow(PathCount))
+ return false;
+ OldDelta -= PathCount;
// Merge the ReleaseMetadata and IsTailCallRelease values.
if (FirstRelease) {
@@ -2569,8 +2582,14 @@ ObjCARCOpt::ConnectTDBUTraversals(DenseMap<const BasicBlock *, BBState>
RE = NewRetainReleaseRRI.ReverseInsertPts.end();
RI != RE; ++RI) {
Instruction *RIP = *RI;
- if (ReleasesToMove.ReverseInsertPts.insert(RIP))
- NewDelta -= BBStates[RIP->getParent()].GetAllPathCount();
+ if (ReleasesToMove.ReverseInsertPts.insert(RIP)) {
+ // If we overflow when we compute the path count, don't
+ // remove/move anything.
+ const BBState &RIPBBState = BBStates[RIP->getParent()];
+ if (RIPBBState.GetAllPathCountWithOverflow(PathCount))
+ return false;
+ NewDelta -= PathCount;
+ }
}
NewReleases.push_back(NewRetainRelease);
}
@@ -2600,8 +2619,13 @@ ObjCARCOpt::ConnectTDBUTraversals(DenseMap<const BasicBlock *, BBState>
const RRInfo &NewReleaseRetainRRI = Jt->second;
assert(NewReleaseRetainRRI.Calls.count(NewRelease));
if (RetainsToMove.Calls.insert(NewReleaseRetain)) {
- unsigned PathCount =
- BBStates[NewReleaseRetain->getParent()].GetAllPathCount();
+
+ // If we overflow when we compute the path count, don't remove/move
+ // anything.
+ const BBState &NRRBBState = BBStates[NewReleaseRetain->getParent()];
+ unsigned PathCount;
+ if (NRRBBState.GetAllPathCountWithOverflow(PathCount))
+ return false;
OldDelta += PathCount;
OldCount += PathCount;
@@ -2613,7 +2637,11 @@ ObjCARCOpt::ConnectTDBUTraversals(DenseMap<const BasicBlock *, BBState>
RI != RE; ++RI) {
Instruction *RIP = *RI;
if (RetainsToMove.ReverseInsertPts.insert(RIP)) {
- PathCount = BBStates[RIP->getParent()].GetAllPathCount();
+ // If we overflow when we compute the path count, don't
+ // remove/move anything.
+ const BBState &RIPBBState = BBStates[RIP->getParent()];
+ if (RIPBBState.GetAllPathCountWithOverflow(PathCount))
+ return false;
NewDelta += PathCount;
NewCount += PathCount;
}
OpenPOWER on IntegriCloud