//
//===----------------------------------------------------------------------===//
-#ifndef LLVM_TRANSFORMS_UTILS_SCCP_SOLVER_H
-#define LLVM_TRANSFORMS_UTILS_SCCP_SOLVER_H
+#ifndef LLVM_TRANSFORMS_UTILS_SCCPSOLVER_H
+#define LLVM_TRANSFORMS_UTILS_SCCPSOLVER_H
#include "llvm/ADT/MapVector.h"
#include "llvm/Analysis/DomTreeUpdater.h"
void addAnalysis(Function &F, AnalysisResultsForFn A);
- /// MarkBlockExecutable - This method can be used by clients to mark all of
+ /// markBlockExecutable - This method can be used by clients to mark all of
/// the blocks that are known to be intrinsically live in the processed unit.
/// This returns true if the block was not considered live before.
- bool MarkBlockExecutable(BasicBlock *BB);
+ bool markBlockExecutable(BasicBlock *BB);
const PredicateBase *getPredicateInfoFor(Instruction *I);
DomTreeUpdater getDTU(Function &F);
- /// TrackValueOfGlobalVariable - Clients can use this method to
+ /// trackValueOfGlobalVariable - Clients can use this method to
/// inform the SCCPSolver that it should track loads and stores to the
/// specified global variable if it can. This is only legal to call if
/// performing Interprocedural SCCP.
- void TrackValueOfGlobalVariable(GlobalVariable *GV);
+ void trackValueOfGlobalVariable(GlobalVariable *GV);
- /// AddTrackedFunction - If the SCCP solver is supposed to track calls into
+ /// addTrackedFunction - If the SCCP solver is supposed to track calls into
/// and out of the specified function (which cannot have its address taken),
/// this method must be called.
- void AddTrackedFunction(Function *F);
+ void addTrackedFunction(Function *F);
/// Add function to the list of functions whose return cannot be modified.
void addToMustPreserveReturnsInFunctions(Function *F);
/// Returns true if the return of the given function cannot be modified.
bool mustPreserveReturn(Function *F);
- void AddArgumentTrackedFunction(Function *F);
+ void addArgumentTrackedFunction(Function *F);
/// Returns true if the given function is in the solver's set of
/// argument-tracked functions.
bool isArgumentTrackedFunction(Function *F);
/// Solve - Solve for constants and executable blocks.
- void Solve();
+ void solve();
- /// ResolvedUndefsIn - While solving the dataflow for a function, we assume
+ /// resolvedUndefsIn - While solving the dataflow for a function, we assume
/// that branches on undef values cannot reach any of their successors.
/// However, this is not a safe assumption. After we solve dataflow, this
/// method should be use to handle this. If this returns true, the solver
/// should be rerun.
- bool ResolvedUndefsIn(Function &F);
+ bool resolvedUndefsIn(Function &F);
bool isBlockExecutable(BasicBlock *BB) const;
} // namespace llvm
-#endif // LLVM_TRANSFORMS_UTILS_SCCP_SOLVER_H
+#endif // LLVM_TRANSFORMS_UTILS_SCCPSOLVER_H
//
//===----------------------------------------------------------------------===//
+#include "llvm/Transforms/Utils/SCCPSolver.h"
#include "llvm/Analysis/ConstantFolding.h"
#include "llvm/Analysis/InstructionSimplify.h"
#include "llvm/Analysis/ValueTracking.h"
#include "llvm/Support/ErrorHandling.h"
#include "llvm/Support/raw_ostream.h"
#include "llvm/Transforms/Utils/Local.h"
-#include "llvm/Transforms/Utils/SCCPSolver.h"
#include <cassert>
#include <utility>
#include <vector>
// OperandChangedState - This method is invoked on all of the users of an
// instruction that was just changed state somehow. Based on this
// information, we need to update the specified user of this instruction.
- void OperandChangedState(Instruction *I) {
+ void operandChangedState(Instruction *I) {
if (BBExecutable.count(I->getParent())) // Inst is executable?
visit(*I);
}
} else {
for (User *U : I->users())
if (auto *UI = dyn_cast<Instruction>(U))
- OperandChangedState(UI);
+ operandChangedState(UI);
}
auto Iter = AdditionalUsers.find(I);
if (auto *UI = dyn_cast<Instruction>(U))
ToNotify.push_back(UI);
for (Instruction *UI : ToNotify)
- OperandChangedState(UI);
+ operandChangedState(UI);
}
}
void handleCallOverdefined(CallBase &CB);
AnalysisResults.insert({&F, std::move(A)});
}
- bool MarkBlockExecutable(BasicBlock *BB);
+ bool markBlockExecutable(BasicBlock *BB);
const PredicateBase *getPredicateInfoFor(Instruction *I) {
auto A = AnalysisResults.find(I->getParent()->getParent());
LLVMContext &Ctx)
: DL(DL), GetTLI(GetTLI), Ctx(Ctx) {}
- void TrackValueOfGlobalVariable(GlobalVariable *GV) {
+ void trackValueOfGlobalVariable(GlobalVariable *GV) {
// We only track the contents of scalar globals.
if (GV->getValueType()->isSingleValueType()) {
ValueLatticeElement &IV = TrackedGlobals[GV];
}
}
- void AddTrackedFunction(Function *F) {
+ void addTrackedFunction(Function *F) {
// Add an entry, F -> undef.
if (auto *STy = dyn_cast<StructType>(F->getReturnType())) {
MRVFunctionsTracked.insert(F);
return MustPreserveReturnsInFunctions.count(F);
}
- void AddArgumentTrackedFunction(Function *F) {
+ void addArgumentTrackedFunction(Function *F) {
TrackingIncomingArguments.insert(F);
}
return TrackingIncomingArguments.count(F);
}
- void Solve();
+ void solve();
- bool ResolvedUndefsIn(Function &F);
+ bool resolvedUndefsIn(Function &F);
bool isBlockExecutable(BasicBlock *BB) const {
return BBExecutable.count(BB);
} // namespace llvm
-bool SCCPInstVisitor::MarkBlockExecutable(BasicBlock *BB) {
+bool SCCPInstVisitor::markBlockExecutable(BasicBlock *BB) {
if (!BBExecutable.insert(BB).second)
return false;
LLVM_DEBUG(dbgs() << "Marking Block Executable: " << BB->getName() << '\n');
return LV.getConstant();
if (LV.isConstantRange()) {
- auto &CR = LV.getConstantRange();
+ const auto &CR = LV.getConstantRange();
if (CR.getSingleElement())
return ConstantInt::get(Ctx, *CR.getSingleElement());
}
if (!KnownFeasibleEdges.insert(Edge(Source, Dest)).second)
return false; // This edge is already known to be executable!
- if (!MarkBlockExecutable(Dest)) {
+ if (!markBlockExecutable(Dest)) {
// If the destination is already executable, we just made an *edge*
// feasible that wasn't before. Revisit the PHI nodes in the block
// because they have potentially new operands.
if (EVI.getType()->isStructTy())
return (void)markOverdefined(&EVI);
- // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+ // resolvedUndefsIn might mark I as overdefined. Bail out, even if we would
// discover a concrete value later.
if (ValueState[&EVI].isOverdefined())
return (void)markOverdefined(&EVI);
if (!STy)
return (void)markOverdefined(&IVI);
- // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+ // resolvedUndefsIn might mark I as overdefined. Bail out, even if we would
// discover a concrete value later.
if (isOverdefined(ValueState[&IVI]))
return (void)markOverdefined(&IVI);
if (I.getType()->isStructTy())
return (void)markOverdefined(&I);
- // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+ // resolvedUndefsIn might mark I as overdefined. Bail out, even if we would
// discover a concrete value later.
if (ValueState[&I].isOverdefined())
return (void)markOverdefined(&I);
ValueLatticeElement V0State = getValueState(I.getOperand(0));
ValueLatticeElement &IV = ValueState[&I];
- // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+ // resolvedUndefsIn might mark I as overdefined. Bail out, even if we would
// discover a concrete value later.
if (isOverdefined(IV))
return (void)markOverdefined(&I);
if (I.getType()->isStructTy() || I.isVolatile())
return (void)markOverdefined(&I);
- // ResolvedUndefsIn might mark I as overdefined. Bail out, even if we would
+ // resolvedUndefsIn might mark I as overdefined. Bail out, even if we would
// discover a concrete value later.
if (ValueState[&I].isOverdefined())
return (void)markOverdefined(&I);
// the formal arguments of the function.
if (!TrackingIncomingArguments.empty() &&
TrackingIncomingArguments.count(F)) {
- MarkBlockExecutable(&F->front());
+ markBlockExecutable(&F->front());
// Propagate information from this call site into the callee.
auto CAI = CB.arg_begin();
Value *CopyOf = CB.getOperand(0);
ValueLatticeElement CopyOfVal = getValueState(CopyOf);
- auto *PI = getPredicateInfoFor(&CB);
+ const auto *PI = getPredicateInfoFor(&CB);
assert(PI && "Missing predicate info for ssa.copy");
const Optional<PredicateConstraint> &Constraint = PI->getConstraint();
}
}
-void SCCPInstVisitor::Solve() {
+void SCCPInstVisitor::solve() {
// Process the work lists until they are empty!
while (!BBWorkList.empty() || !InstWorkList.empty() ||
!OverdefinedInstWorkList.empty()) {
}
}
-/// ResolvedUndefsIn - While solving the dataflow for a function, we assume
+/// resolvedUndefsIn - While solving the dataflow for a function, we assume
/// that branches on undef values cannot reach any of their successors.
/// However, this is not a safe assumption. After we solve dataflow, this
/// method should be use to handle this. If this returns true, the solver
///
/// This scan also checks for values that use undefs. It conservatively marks
/// them as overdefined.
-bool SCCPInstVisitor::ResolvedUndefsIn(Function &F) {
+bool SCCPInstVisitor::resolvedUndefsIn(Function &F) {
bool MadeChange = false;
for (BasicBlock &BB : F) {
if (!BBExecutable.count(&BB))
if (auto *STy = dyn_cast<StructType>(I.getType())) {
// Only a few things that can be structs matter for undef.
- // Tracked calls must never be marked overdefined in ResolvedUndefsIn.
+ // Tracked calls must never be marked overdefined in resolvedUndefsIn.
if (auto *CB = dyn_cast<CallBase>(&I))
if (Function *F = CB->getCalledFunction())
if (MRVFunctionsTracked.count(F))
// 1. It could be tracked.
// 2. It could be constant-foldable.
// Because of the way we solve return values, tracked calls must
- // never be marked overdefined in ResolvedUndefsIn.
+ // never be marked overdefined in resolvedUndefsIn.
if (auto *CB = dyn_cast<CallBase>(&I))
if (Function *F = CB->getCalledFunction())
if (TrackedRetVals.count(F))
return Visitor->addAnalysis(F, std::move(A));
}
-bool SCCPSolver::MarkBlockExecutable(BasicBlock *BB) {
- return Visitor->MarkBlockExecutable(BB);
+bool SCCPSolver::markBlockExecutable(BasicBlock *BB) {
+ return Visitor->markBlockExecutable(BB);
}
const PredicateBase *SCCPSolver::getPredicateInfoFor(Instruction *I) {
DomTreeUpdater SCCPSolver::getDTU(Function &F) { return Visitor->getDTU(F); }
-void SCCPSolver::TrackValueOfGlobalVariable(GlobalVariable *GV) {
- Visitor->TrackValueOfGlobalVariable(GV);
+void SCCPSolver::trackValueOfGlobalVariable(GlobalVariable *GV) {
+ Visitor->trackValueOfGlobalVariable(GV);
}
-void SCCPSolver::AddTrackedFunction(Function *F) {
- Visitor->AddTrackedFunction(F);
+void SCCPSolver::addTrackedFunction(Function *F) {
+ Visitor->addTrackedFunction(F);
}
void SCCPSolver::addToMustPreserveReturnsInFunctions(Function *F) {
return Visitor->mustPreserveReturn(F);
}
-void SCCPSolver::AddArgumentTrackedFunction(Function *F) {
- Visitor->AddArgumentTrackedFunction(F);
+void SCCPSolver::addArgumentTrackedFunction(Function *F) {
+ Visitor->addArgumentTrackedFunction(F);
}
bool SCCPSolver::isArgumentTrackedFunction(Function *F) {
return Visitor->isArgumentTrackedFunction(F);
}
-void SCCPSolver::Solve() { Visitor->Solve(); }
+void SCCPSolver::solve() { Visitor->solve(); }
-bool SCCPSolver::ResolvedUndefsIn(Function &F) {
- return Visitor->ResolvedUndefsIn(F);
+bool SCCPSolver::resolvedUndefsIn(Function &F) {
+ return Visitor->resolvedUndefsIn(F);
}
bool SCCPSolver::isBlockExecutable(BasicBlock *BB) const {