diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2023-02-11 12:38:04 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2023-02-11 12:38:11 +0000 |
commit | e3b557809604d036af6e00c60f012c2025b59a5e (patch) | |
tree | 8a11ba2269a3b669601e2fd41145b174008f4da8 /llvm/lib/Analysis/StackLifetime.cpp | |
parent | 08e8dd7b9db7bb4a9de26d44c1cbfd24e869c014 (diff) |
Diffstat (limited to 'llvm/lib/Analysis/StackLifetime.cpp')
-rw-r--r-- | llvm/lib/Analysis/StackLifetime.cpp | 68 |
1 files changed, 42 insertions, 26 deletions
diff --git a/llvm/lib/Analysis/StackLifetime.cpp b/llvm/lib/Analysis/StackLifetime.cpp index 162fd75c73e0..ee77e81fc978 100644 --- a/llvm/lib/Analysis/StackLifetime.cpp +++ b/llvm/lib/Analysis/StackLifetime.cpp @@ -67,17 +67,16 @@ static const AllocaInst *findMatchingAlloca(const IntrinsicInst &II, if (!AI) return nullptr; - auto AllocaSizeInBits = AI->getAllocationSizeInBits(DL); - if (!AllocaSizeInBits) + auto AllocaSize = AI->getAllocationSize(DL); + if (!AllocaSize) return nullptr; - int64_t AllocaSize = *AllocaSizeInBits / 8; auto *Size = dyn_cast<ConstantInt>(II.getArgOperand(0)); if (!Size) return nullptr; int64_t LifetimeSize = Size->getSExtValue(); - if (LifetimeSize != -1 && LifetimeSize != AllocaSize) + if (LifetimeSize != -1 && uint64_t(LifetimeSize) != *AllocaSize) return nullptr; return AI; @@ -174,30 +173,35 @@ void StackLifetime::collectMarkers() { void StackLifetime::calculateLocalLiveness() { bool Changed = true; + + // LiveIn, LiveOut and BitsIn have a different meaning deppends on type. + // ::Maybe true bits represent "may be alive" allocas, ::Must true bits + // represent "may be dead". After the loop we will convert ::Must bits from + // "may be dead" to "must be alive". while (Changed) { + // TODO: Consider switching to worklist instead of traversing entire graph. Changed = false; for (const BasicBlock *BB : depth_first(&F)) { BlockLifetimeInfo &BlockInfo = BlockLiveness.find(BB)->getSecond(); - // Compute LiveIn by unioning together the LiveOut sets of all preds. - BitVector LocalLiveIn; + // Compute BitsIn by unioning together the LiveOut sets of all preds. + BitVector BitsIn; for (const auto *PredBB : predecessors(BB)) { LivenessMap::const_iterator I = BlockLiveness.find(PredBB); // If a predecessor is unreachable, ignore it. if (I == BlockLiveness.end()) continue; - switch (Type) { - case LivenessType::May: - LocalLiveIn |= I->second.LiveOut; - break; - case LivenessType::Must: - if (LocalLiveIn.empty()) - LocalLiveIn = I->second.LiveOut; - else - LocalLiveIn &= I->second.LiveOut; - break; - } + BitsIn |= I->second.LiveOut; + } + + // Everything is "may be dead" for entry without predecessors. + if (Type == LivenessType::Must && BitsIn.empty()) + BitsIn.resize(NumAllocas, true); + + // Update block LiveIn set, noting whether it has changed. + if (BitsIn.test(BlockInfo.LiveIn)) { + BlockInfo.LiveIn |= BitsIn; } // Compute LiveOut by subtracting out lifetimes that end in this @@ -207,22 +211,34 @@ void StackLifetime::calculateLocalLiveness() { // because we already handle the case where the BEGIN comes // before the END when collecting the markers (and building the // BEGIN/END vectors). - BitVector LocalLiveOut = LocalLiveIn; - LocalLiveOut.reset(BlockInfo.End); - LocalLiveOut |= BlockInfo.Begin; - - // Update block LiveIn set, noting whether it has changed. - if (LocalLiveIn.test(BlockInfo.LiveIn)) { - BlockInfo.LiveIn |= LocalLiveIn; + switch (Type) { + case LivenessType::May: + BitsIn.reset(BlockInfo.End); + // "may be alive" is set by lifetime start. + BitsIn |= BlockInfo.Begin; + break; + case LivenessType::Must: + BitsIn.reset(BlockInfo.Begin); + // "may be dead" is set by lifetime end. + BitsIn |= BlockInfo.End; + break; } // Update block LiveOut set, noting whether it has changed. - if (LocalLiveOut.test(BlockInfo.LiveOut)) { + if (BitsIn.test(BlockInfo.LiveOut)) { Changed = true; - BlockInfo.LiveOut |= LocalLiveOut; + BlockInfo.LiveOut |= BitsIn; } } } // while changed. + + if (Type == LivenessType::Must) { + // Convert from "may be dead" to "must be alive". + for (auto &[BB, BlockInfo] : BlockLiveness) { + BlockInfo.LiveIn.flip(); + BlockInfo.LiveOut.flip(); + } + } } void StackLifetime::calculateLiveIntervals() { |