本文整理汇总了C++中function::iterator::begin方法的典型用法代码示例。如果您正苦于以下问题:C++ iterator::begin方法的具体用法?C++ iterator::begin怎么用?C++ iterator::begin使用的例子?那么恭喜您, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类function::iterator
的用法示例。
在下文中一共展示了iterator::begin方法的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: runOnModule
/*
* Main args are always input
* Functions currently considered as input functions:
* scanf
* fscanf
* gets
* fgets
* fread
* fgetc
* getc
* getchar
* recv
* recvmsg
* read
* recvfrom
* fread
*/
bool InputDep::runOnModule(Module &M) {
// DEBUG (errs() << "Function " << F.getName() << "\n";);
NumInputValues = 0;
bool inserted;
Function* main = M.getFunction("main");
if (main) {
MDNode *mdn = main->begin()->begin()->getMetadata("dbg");
for (Function::arg_iterator Arg = main->arg_begin(), aEnd =
main->arg_end(); Arg != aEnd; Arg++) {
inputDepValues.insert(Arg);
NumInputValues++;
if (mdn) {
DILocation Loc(mdn);
unsigned Line = Loc.getLineNumber();
lineNo[Arg] = Line-1; //educated guess (can only get line numbers from insts, suppose main is declared one line before 1st inst
}
}
}
for (Module::iterator F = M.begin(), eM = M.end(); F != eM; ++F) {
for (Function::iterator BB = F->begin(), e = F->end(); BB != e; ++BB) {
for (BasicBlock::iterator I = BB->begin(), ee = BB->end(); I != ee; ++I) {
if (CallInst *CI = dyn_cast<CallInst>(I)) {
Function *Callee = CI->getCalledFunction();
if (Callee) {
Value* V;
inserted = false;
StringRef Name = Callee->getName();
if (Name.equals("main")) {
errs() << "main\n";
V = CI->getArgOperand(1); //char* argv[]
inputDepValues.insert(V);
inserted = true;
//errs() << "Input " << *V << "\n";
}
if (Name.equals("__isoc99_scanf") || Name.equals(
"scanf")) {
for (unsigned i = 1, eee = CI->getNumArgOperands(); i
!= eee; ++i) { // skip format string (i=1)
V = CI->getArgOperand(i);
if (V->getType()->isPointerTy()) {
inputDepValues.insert(V);
inserted = true;
//errs() << "Input " << *V << "\n";
}
}
} else if (Name.equals("__isoc99_fscanf")
|| Name.equals("fscanf")) {
for (unsigned i = 2, eee = CI->getNumArgOperands(); i
!= eee; ++i) { // skip file pointer and format string (i=1)
V = CI->getArgOperand(i);
if (V->getType()->isPointerTy()) {
inputDepValues.insert(V);
inserted = true;
//errs() << "Input " << *V << "\n";
}
}
} else if ((Name.equals("gets") || Name.equals("fgets")
|| Name.equals("fread"))
|| Name.equals("getwd")
|| Name.equals("getcwd")) {
V = CI->getArgOperand(0); //the first argument receives the input for these functions
if (V->getType()->isPointerTy()) {
inputDepValues.insert(V);
inserted = true;
//errs() << "Input " << *V << "\n";
}
} else if ((Name.equals("fgetc") || Name.equals("getc")
|| Name.equals("getchar"))) {
inputDepValues.insert(CI);
inserted = true;
//errs() << "Input " << *CI << "\n";
} else if (Name.equals("recv")
|| Name.equals("recvmsg")
|| Name.equals("read")) {
Value* V = CI->getArgOperand(1);
if (V->getType()->isPointerTy()) {
inputDepValues.insert(V);
inserted = true;
//errs() << "Input " << *V << "\n";
}
} else if (Name.equals("recvfrom")) {
//.........这里部分代码省略.........
示例2: computeReachableUncovered
void StatsTracker::computeReachableUncovered() {
KModule *km = executor.kmodule;
Module *m = km->module;
static bool init = true;
const InstructionInfoTable &infos = *km->infos;
StatisticManager &sm = *theStatisticManager;
if (init) {
init = false;
// Compute call targets. It would be nice to use alias information
// instead of assuming all indirect calls hit all escaping
// functions, eh?
for (Module::iterator fnIt = m->begin(), fn_ie = m->end();
fnIt != fn_ie; ++fnIt) {
for (Function::iterator bbIt = fnIt->begin(), bb_ie = fnIt->end();
bbIt != bb_ie; ++bbIt) {
for (BasicBlock::iterator it = bbIt->begin(), ie = bbIt->end();
it != ie; ++it) {
if (isa<CallInst>(it) || isa<InvokeInst>(it)) {
if (isa<InlineAsm>(it->getOperand(0))) {
// We can never call through here so assume no targets
// (which should be correct anyhow).
callTargets.insert(std::make_pair(it,
std::vector<Function*>()));
} else if (Function *target = getDirectCallTarget(it)) {
callTargets[it].push_back(target);
} else {
callTargets[it] =
std::vector<Function*>(km->escapingFunctions.begin(),
km->escapingFunctions.end());
}
}
}
}
}
// Compute function callers as reflexion of callTargets.
for (calltargets_ty::iterator it = callTargets.begin(),
ie = callTargets.end(); it != ie; ++it)
for (std::vector<Function*>::iterator fit = it->second.begin(),
fie = it->second.end(); fit != fie; ++fit)
functionCallers[*fit].push_back(it->first);
// Initialize minDistToReturn to shortest paths through
// functions. 0 is unreachable.
std::vector<Instruction *> instructions;
for (Module::iterator fnIt = m->begin(), fn_ie = m->end();
fnIt != fn_ie; ++fnIt) {
if (fnIt->isDeclaration()) {
if (fnIt->doesNotReturn()) {
functionShortestPath[fnIt] = 0;
} else {
functionShortestPath[fnIt] = 1; // whatever
}
continue;
} else {
functionShortestPath[fnIt] = 0;
}
KFunction *kf = km->functionMap[fnIt];
for (unsigned i = 0; i < kf->numInstructions; ++i) {
Instruction *inst = kf->instrPostOrder[i]->inst;
instructions.push_back(inst);
sm.setIndexedValue(stats::minDistToReturn,
kf->instrPostOrder[i]->info->id,
isa<ReturnInst>(inst));
}
}
// I'm so lazy it's not even worklisted.
bool changed;
do {
changed = false;
for (std::vector<Instruction*>::iterator it = instructions.begin(),
ie = instructions.end(); it != ie; ++it) {
Instruction *inst = *it;
unsigned bestThrough = 0;
if (isa<CallInst>(inst) || isa<InvokeInst>(inst)) {
std::vector<Function*> &targets = callTargets[inst];
for (std::vector<Function*>::iterator fnIt = targets.begin(),
ie = targets.end(); fnIt != ie; ++fnIt) {
uint64_t dist = functionShortestPath[*fnIt];
if (dist) {
dist = 1+dist; // count instruction itself
if (bestThrough==0 || dist<bestThrough)
bestThrough = dist;
}
}
} else {
bestThrough = 1;
}
if (bestThrough) {
unsigned id = infos.getInfo(*it).id;
uint64_t best, cur = best = sm.getIndexedValue(stats::minDistToReturn, id);
std::vector<Instruction*> succs = getSuccs(*it);
for (std::vector<Instruction*>::iterator it2 = succs.begin(),
//.........这里部分代码省略.........
示例3: lowerAcrossUnwindEdges
/// lowerAcrossUnwindEdges - Find all variables which are alive across an unwind
/// edge and spill them.
void SjLjEHPass::lowerAcrossUnwindEdges(Function &F,
ArrayRef<InvokeInst*> Invokes) {
// Finally, scan the code looking for instructions with bad live ranges.
for (Function::iterator
BB = F.begin(), BBE = F.end(); BB != BBE; ++BB) {
for (BasicBlock::iterator
II = BB->begin(), IIE = BB->end(); II != IIE; ++II) {
// Ignore obvious cases we don't have to handle. In particular, most
// instructions either have no uses or only have a single use inside the
// current block. Ignore them quickly.
Instruction *Inst = II;
if (Inst->use_empty()) continue;
if (Inst->hasOneUse() &&
cast<Instruction>(Inst->use_back())->getParent() == BB &&
!isa<PHINode>(Inst->use_back())) continue;
// If this is an alloca in the entry block, it's not a real register
// value.
if (AllocaInst *AI = dyn_cast<AllocaInst>(Inst))
if (isa<ConstantInt>(AI->getArraySize()) && BB == F.begin())
continue;
// Avoid iterator invalidation by copying users to a temporary vector.
SmallVector<Instruction*, 16> Users;
for (Value::use_iterator
UI = Inst->use_begin(), E = Inst->use_end(); UI != E; ++UI) {
Instruction *User = cast<Instruction>(*UI);
if (User->getParent() != BB || isa<PHINode>(User))
Users.push_back(User);
}
// Find all of the blocks that this value is live in.
SmallPtrSet<BasicBlock*, 64> LiveBBs;
LiveBBs.insert(Inst->getParent());
while (!Users.empty()) {
Instruction *U = Users.back();
Users.pop_back();
if (!isa<PHINode>(U)) {
MarkBlocksLiveIn(U->getParent(), LiveBBs);
} else {
// Uses for a PHI node occur in their predecessor block.
PHINode *PN = cast<PHINode>(U);
for (unsigned i = 0, e = PN->getNumIncomingValues(); i != e; ++i)
if (PN->getIncomingValue(i) == Inst)
MarkBlocksLiveIn(PN->getIncomingBlock(i), LiveBBs);
}
}
// Now that we know all of the blocks that this thing is live in, see if
// it includes any of the unwind locations.
bool NeedsSpill = false;
for (unsigned i = 0, e = Invokes.size(); i != e; ++i) {
BasicBlock *UnwindBlock = Invokes[i]->getUnwindDest();
if (UnwindBlock != BB && LiveBBs.count(UnwindBlock)) {
DEBUG(dbgs() << "SJLJ Spill: " << *Inst << " around "
<< UnwindBlock->getName() << "\n");
NeedsSpill = true;
break;
}
}
// If we decided we need a spill, do it.
// FIXME: Spilling this way is overkill, as it forces all uses of
// the value to be reloaded from the stack slot, even those that aren't
// in the unwind blocks. We should be more selective.
if (NeedsSpill) {
DemoteRegToStack(*Inst, true);
++NumSpilled;
}
}
}
// Go through the landing pads and remove any PHIs there.
for (unsigned i = 0, e = Invokes.size(); i != e; ++i) {
BasicBlock *UnwindBlock = Invokes[i]->getUnwindDest();
LandingPadInst *LPI = UnwindBlock->getLandingPadInst();
// Place PHIs into a set to avoid invalidating the iterator.
SmallPtrSet<PHINode*, 8> PHIsToDemote;
for (BasicBlock::iterator
PN = UnwindBlock->begin(); isa<PHINode>(PN); ++PN)
PHIsToDemote.insert(cast<PHINode>(PN));
if (PHIsToDemote.empty()) continue;
// Demote the PHIs to the stack.
for (SmallPtrSet<PHINode*, 8>::iterator
I = PHIsToDemote.begin(), E = PHIsToDemote.end(); I != E; ++I)
DemotePHIToStack(*I);
// Move the landingpad instruction back to the top of the landing pad block.
LPI->moveBefore(UnwindBlock->begin());
}
}
示例4: cs
void CallTargetFinder<dsa>::findIndTargets(Module &M)
{
dsa* T = &getAnalysis<dsa>();
const DSCallGraph & callgraph = T->getCallGraph();
DSGraph* G = T->getGlobalsGraph();
DSGraph::ScalarMapTy& SM = G->getScalarMap();
for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I)
if (!I->isDeclaration())
for (Function::iterator F = I->begin(), FE = I->end(); F != FE; ++F)
for (BasicBlock::iterator B = F->begin(), BE = F->end(); B != BE; ++B)
if (isa<CallInst>(B) || isa<InvokeInst>(B)) {
CallSite cs(B);
AllSites.push_back(cs);
Function* CF = cs.getCalledFunction();
//
// If the called function is casted from one function type to
// another, peer into the cast instruction and pull out the actual
// function being called.
//
if (!CF)
CF = dyn_cast<Function>(cs.getCalledValue()->stripPointerCasts());
if (!CF) {
Value * calledValue = cs.getCalledValue()->stripPointerCasts();
if (isa<ConstantPointerNull>(calledValue)) {
++DirCall;
CompleteSites.insert(cs);
} else {
IndCall++;
DSCallGraph::callee_iterator csi = callgraph.callee_begin(cs),
cse = callgraph.callee_end(cs);
while(csi != cse) {
const Function *F = *csi;
DSCallGraph::scc_iterator sccii = callgraph.scc_begin(F),
sccee = callgraph.scc_end(F);
for(;sccii != sccee; ++sccii) {
DSGraph::ScalarMapTy::const_iterator I = SM.find(SM.getLeaderForGlobal(*sccii));
if (I != SM.end()) {
IndMap[cs].push_back (*sccii);
}
}
++csi;
}
const Function *F1 = (cs).getInstruction()->getParent()->getParent();
F1 = callgraph.sccLeader(&*F1);
DSCallGraph::scc_iterator sccii = callgraph.scc_begin(F1),
sccee = callgraph.scc_end(F1);
for(;sccii != sccee; ++sccii) {
DSGraph::ScalarMapTy::const_iterator I = SM.find(SM.getLeaderForGlobal(*sccii));
if (I != SM.end()) {
IndMap[cs].push_back (*sccii);
}
}
DSNode* N = T->getDSGraph(*cs.getCaller())
->getNodeForValue(cs.getCalledValue()).getNode();
assert (N && "CallTarget: findIndTargets: No DSNode!\n");
if (!N->isIncompleteNode() && !N->isExternalNode() && IndMap[cs].size()) {
CompleteSites.insert(cs);
++CompleteInd;
}
if (!N->isIncompleteNode() && !N->isExternalNode() && !IndMap[cs].size()) {
++CompleteEmpty;
DEBUG(errs() << "Call site empty: '"
<< cs.getInstruction()->getName()
<< "' In '"
<< cs.getInstruction()->getParent()->getParent()->getName()
<< "'\n");
}
}
} else {
++DirCall;
IndMap[cs].push_back(CF);
CompleteSites.insert(cs);
}
}
}
示例5: getCallgraphProfile
// TODO(sbucur): Break this into multiple methods
void StatsTracker::getCallgraphProfile(data::GlobalProfile &globalProfile) {
Module *m = executor.kmodule->module;
uint64_t istatsMask = 0;
StatisticManager &sm = *theStatisticManager;
unsigned nStats = sm.getNumStatistics();
istatsMask |= 1<<sm.getStatisticID("Queries");
istatsMask |= 1<<sm.getStatisticID("QueriesValid");
istatsMask |= 1<<sm.getStatisticID("QueriesInvalid");
istatsMask |= 1<<sm.getStatisticID("QueryTime");
istatsMask |= 1<<sm.getStatisticID("ResolveTime");
istatsMask |= 1<<sm.getStatisticID("Instructions");
istatsMask |= 1<<sm.getStatisticID("InstructionTimes");
istatsMask |= 1<<sm.getStatisticID("InstructionRealTimes");
istatsMask |= 1<<sm.getStatisticID("Forks");
istatsMask |= 1<<sm.getStatisticID("GloballyCoveredInstructions");
istatsMask |= 1<<sm.getStatisticID("GloballyUncoveredInstructions");
istatsMask |= 1<<sm.getStatisticID("States");
istatsMask |= 1<<sm.getStatisticID("MinDistToUncovered");
for (unsigned i=0; i<nStats; i++) {
if (istatsMask & (1<<i)) {
Statistic &s = sm.getStatistic(i);
globalProfile.add_cost_label(s.getName());
}
}
globalProfile.set_time_stamp(::time(NULL));
// set state counts, decremented after we process so that we don't
// have to zero all records each time.
if (istatsMask & (1<<stats::states.getID()))
updateStateStatistics(1);
CallSiteSummaryTable callSiteStats;
if (UseCallPaths)
callPathManager.getSummaryStatistics(callSiteStats);
for (Module::iterator fnIt = m->begin(), fn_ie = m->end();
fnIt != fn_ie; ++fnIt) {
if (fnIt->isDeclaration())
continue;
data::FunctionProfile *functionProfile = globalProfile.add_function_profile();
functionProfile->set_function_id(executor.kmodule->functionMap[&(*fnIt)]->nameID);
for (Function::iterator bbIt = fnIt->begin(), bb_ie = fnIt->end();
bbIt != bb_ie; ++bbIt) {
for (BasicBlock::iterator it = bbIt->begin(), ie = bbIt->end();
it != ie; ++it) {
Instruction *instr = &*it;
const InstructionInfo &ii = executor.kmodule->infos->getInfo(instr);
unsigned index = ii.id;
data::LineProfile *lineProfile = functionProfile->add_line_profile();
executor.kmodule->fillInstructionDebugInfo(
instr, *lineProfile->mutable_debug_info());
for (unsigned i=0; i<nStats; i++) {
if (istatsMask&(1<<i)) {
lineProfile->add_cost_value(
sm.getIndexedValue(sm.getStatistic(i), index));
}
}
if (UseCallPaths &&
(isa<CallInst>(instr) || isa<InvokeInst>(instr))) {
CallSiteSummaryTable::iterator it = callSiteStats.find(instr);
if (it!=callSiteStats.end()) {
for (std::map<llvm::Function*, CallSiteInfo>::iterator
fit = it->second.begin(), fie = it->second.end();
fit != fie; ++fit) {
Function *f = fit->first;
CallSiteInfo &csi = fit->second;
data::CallSiteProfile *callsiteProfile = lineProfile->add_call_site_profile();
executor.kmodule->fillFunctionDebugInfo(
f, *callsiteProfile->mutable_debug_info());
callsiteProfile->set_call_count(csi.count);
for (unsigned i=0; i<nStats; i++) {
if (istatsMask&(1<<i)) {
Statistic &s = sm.getStatistic(i);
uint64_t value;
// Hack, ignore things that don't make sense on
// call paths.
if (&s == &stats::globallyUncoveredInstructions) {
value = 0;
} else {
value = csi.statistics.getValue(s);
}
callsiteProfile->add_cost_value(value);
}
}
}
//.........这里部分代码省略.........
示例6: InlineFunction
/// InlineFunction - This function inlines the called function into the basic
/// block of the caller. This returns false if it is not possible to inline
/// this call. The program is still in a well defined state if this occurs
/// though.
///
/// Note that this only does one level of inlining. For example, if the
/// instruction 'call B' is inlined, and 'B' calls 'C', then the call to 'C' now
/// exists in the instruction stream. Similarly this will inline a recursive
/// function by one level.
bool llvm::InlineFunction(CallSite CS, InlineFunctionInfo &IFI,
bool InsertLifetime) {
Instruction *TheCall = CS.getInstruction();
assert(TheCall->getParent() && TheCall->getParent()->getParent() &&
"Instruction not in function!");
// If IFI has any state in it, zap it before we fill it in.
IFI.reset();
const Function *CalledFunc = CS.getCalledFunction();
if (CalledFunc == 0 || // Can't inline external function or indirect
CalledFunc->isDeclaration() || // call, or call to a vararg function!
CalledFunc->getFunctionType()->isVarArg()) return false;
// If the call to the callee is not a tail call, we must clear the 'tail'
// flags on any calls that we inline.
bool MustClearTailCallFlags =
!(isa<CallInst>(TheCall) && cast<CallInst>(TheCall)->isTailCall());
// If the call to the callee cannot throw, set the 'nounwind' flag on any
// calls that we inline.
bool MarkNoUnwind = CS.doesNotThrow();
BasicBlock *OrigBB = TheCall->getParent();
Function *Caller = OrigBB->getParent();
// GC poses two hazards to inlining, which only occur when the callee has GC:
// 1. If the caller has no GC, then the callee's GC must be propagated to the
// caller.
// 2. If the caller has a differing GC, it is invalid to inline.
if (CalledFunc->hasGC()) {
if (!Caller->hasGC())
Caller->setGC(CalledFunc->getGC());
else if (CalledFunc->getGC() != Caller->getGC())
return false;
}
// Get the personality function from the callee if it contains a landing pad.
Value *CalleePersonality = 0;
for (Function::const_iterator I = CalledFunc->begin(), E = CalledFunc->end();
I != E; ++I)
if (const InvokeInst *II = dyn_cast<InvokeInst>(I->getTerminator())) {
const BasicBlock *BB = II->getUnwindDest();
const LandingPadInst *LP = BB->getLandingPadInst();
CalleePersonality = LP->getPersonalityFn();
break;
}
// Find the personality function used by the landing pads of the caller. If it
// exists, then check to see that it matches the personality function used in
// the callee.
if (CalleePersonality) {
for (Function::const_iterator I = Caller->begin(), E = Caller->end();
I != E; ++I)
if (const InvokeInst *II = dyn_cast<InvokeInst>(I->getTerminator())) {
const BasicBlock *BB = II->getUnwindDest();
const LandingPadInst *LP = BB->getLandingPadInst();
// If the personality functions match, then we can perform the
// inlining. Otherwise, we can't inline.
// TODO: This isn't 100% true. Some personality functions are proper
// supersets of others and can be used in place of the other.
if (LP->getPersonalityFn() != CalleePersonality)
return false;
break;
}
}
// Get an iterator to the last basic block in the function, which will have
// the new function inlined after it.
Function::iterator LastBlock = &Caller->back();
// Make sure to capture all of the return instructions from the cloned
// function.
SmallVector<ReturnInst*, 8> Returns;
ClonedCodeInfo InlinedFunctionInfo;
Function::iterator FirstNewBlock;
{ // Scope to destroy VMap after cloning.
ValueToValueMapTy VMap;
assert(CalledFunc->arg_size() == CS.arg_size() &&
"No varargs calls can be inlined!");
// Calculate the vector of arguments to pass into the function cloner, which
// matches up the formal to the actual argument values.
CallSite::arg_iterator AI = CS.arg_begin();
unsigned ArgNo = 0;
for (Function::const_arg_iterator I = CalledFunc->arg_begin(),
E = CalledFunc->arg_end(); I != E; ++I, ++AI, ++ArgNo) {
//.........这里部分代码省略.........
示例7: runOnModule
bool GenericToNVVM::runOnModule(Module &M) {
// Create a clone of each global variable that has the default address space.
// The clone is created with the global address space specifier, and the pair
// of original global variable and its clone is placed in the GVMap for later
// use.
for (Module::global_iterator I = M.global_begin(), E = M.global_end();
I != E;) {
GlobalVariable *GV = I++;
if (GV->getType()->getAddressSpace() == llvm::ADDRESS_SPACE_GENERIC &&
!llvm::isTexture(*GV) && !llvm::isSurface(*GV) &&
!llvm::isSampler(*GV) && !GV->getName().startswith("llvm.")) {
GlobalVariable *NewGV = new GlobalVariable(
M, GV->getType()->getElementType(), GV->isConstant(),
GV->getLinkage(),
GV->hasInitializer() ? GV->getInitializer() : nullptr,
"", GV, GV->getThreadLocalMode(), llvm::ADDRESS_SPACE_GLOBAL);
NewGV->copyAttributesFrom(GV);
GVMap[GV] = NewGV;
}
}
// Return immediately, if every global variable has a specific address space
// specifier.
if (GVMap.empty()) {
return false;
}
// Walk through the instructions in function defitinions, and replace any use
// of original global variables in GVMap with a use of the corresponding
// copies in GVMap. If necessary, promote constants to instructions.
for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I) {
if (I->isDeclaration()) {
continue;
}
IRBuilder<> Builder(I->getEntryBlock().getFirstNonPHIOrDbg());
for (Function::iterator BBI = I->begin(), BBE = I->end(); BBI != BBE;
++BBI) {
for (BasicBlock::iterator II = BBI->begin(), IE = BBI->end(); II != IE;
++II) {
for (unsigned i = 0, e = II->getNumOperands(); i < e; ++i) {
Value *Operand = II->getOperand(i);
if (isa<Constant>(Operand)) {
II->setOperand(
i, remapConstant(&M, I, cast<Constant>(Operand), Builder));
}
}
}
}
ConstantToValueMap.clear();
}
// Walk through the metadata section and update the debug information
// associated with the global variables in the default address space.
for (Module::named_metadata_iterator I = M.named_metadata_begin(),
E = M.named_metadata_end();
I != E; I++) {
remapNamedMDNode(&M, I);
}
// Walk through the global variable initializers, and replace any use of
// original global variables in GVMap with a use of the corresponding copies
// in GVMap. The copies need to be bitcast to the original global variable
// types, as we cannot use cvta in global variable initializers.
for (GVMapTy::iterator I = GVMap.begin(), E = GVMap.end(); I != E;) {
GlobalVariable *GV = I->first;
GlobalVariable *NewGV = I->second;
// Remove GV from the map so that it can be RAUWed. Note that
// DenseMap::erase() won't invalidate any iterators but this one.
auto Next = std::next(I);
GVMap.erase(I);
I = Next;
Constant *BitCastNewGV = ConstantExpr::getPointerCast(NewGV, GV->getType());
// At this point, the remaining uses of GV should be found only in global
// variable initializers, as other uses have been already been removed
// while walking through the instructions in function definitions.
GV->replaceAllUsesWith(BitCastNewGV);
std::string Name = GV->getName();
GV->eraseFromParent();
NewGV->setName(Name);
}
assert(GVMap.empty() && "Expected it to be empty by now");
return true;
}
示例8: runOnSCC
bool PruneEH::runOnSCC(const std::vector<CallGraphNode *> &SCC) {
CallGraph &CG = getAnalysis<CallGraph>();
bool MadeChange = false;
// First pass, scan all of the functions in the SCC, simplifying them
// according to what we know.
for (unsigned i = 0, e = SCC.size(); i != e; ++i)
if (Function *F = SCC[i]->getFunction())
MadeChange |= SimplifyFunction(F);
// Next, check to see if any callees might throw or if there are any external
// functions in this SCC: if so, we cannot prune any functions in this SCC.
// If this SCC includes the unwind instruction, we KNOW it throws, so
// obviously the SCC might throw.
//
bool SCCMightUnwind = false, SCCMightReturn = false;
for (unsigned i = 0, e = SCC.size();
(!SCCMightUnwind || !SCCMightReturn) && i != e; ++i) {
Function *F = SCC[i]->getFunction();
if (F == 0 || (F->isDeclaration() && !F->getIntrinsicID())) {
SCCMightUnwind = true;
SCCMightReturn = true;
} else {
if (F->isDeclaration())
SCCMightReturn = true;
// Check to see if this function performs an unwind or calls an
// unwinding function.
for (Function::iterator BB = F->begin(), E = F->end(); BB != E; ++BB) {
if (isa<UnwindInst>(BB->getTerminator())) { // Uses unwind!
SCCMightUnwind = true;
} else if (isa<ReturnInst>(BB->getTerminator())) {
SCCMightReturn = true;
}
// Invoke instructions don't allow unwinding to continue, so we are
// only interested in call instructions.
if (!SCCMightUnwind)
for (BasicBlock::iterator I = BB->begin(), E = BB->end(); I != E; ++I)
if (CallInst *CI = dyn_cast<CallInst>(I)) {
if (Function *Callee = CI->getCalledFunction()) {
CallGraphNode *CalleeNode = CG[Callee];
// If the callee is outside our current SCC, or if it is not
// known to throw, then we might throw also.
if (std::find(SCC.begin(), SCC.end(), CalleeNode) == SCC.end()&&
!DoesNotUnwind.count(CalleeNode)) {
SCCMightUnwind = true;
break;
}
} else {
// Indirect call, it might throw.
SCCMightUnwind = true;
break;
}
}
if (SCCMightUnwind && SCCMightReturn) break;
}
}
}
// If the SCC doesn't unwind or doesn't throw, note this fact.
if (!SCCMightUnwind)
for (unsigned i = 0, e = SCC.size(); i != e; ++i)
DoesNotUnwind.insert(SCC[i]);
if (!SCCMightReturn)
for (unsigned i = 0, e = SCC.size(); i != e; ++i)
DoesNotReturn.insert(SCC[i]);
for (unsigned i = 0, e = SCC.size(); i != e; ++i) {
// Convert any invoke instructions to non-throwing functions in this node
// into call instructions with a branch. This makes the exception blocks
// dead.
if (Function *F = SCC[i]->getFunction())
MadeChange |= SimplifyFunction(F);
}
return MadeChange;
}
示例9: rewrite_omp_call_sites
/*
* Rewrite OpenMP call sites and their associated kernel functions -- the folloiwng pattern
call void @GOMP_parallel_start(void (i8*)* @_Z20initialize_variablesiPfS_.omp_fn.4, i8* %.omp_data_o.5571, i32 0) nounwind
call void @_Z20initialize_variablesiPfS_.omp_fn.4(i8* %.omp_data_o.5571) nounwind
call void @GOMP_parallel_end() nounwind
*/
void HeteroOMPTransform::rewrite_omp_call_sites(Module &M) {
SmallVector<Instruction *, 16> toDelete;
DenseMap<Value *, Value *> ValueMap;
for (Module::iterator I = M.begin(), E = M.end(); I != E; ++I){
if (!I->isDeclaration()) {
for (Function::iterator BBI = I->begin(), BBE = I->end(); BBI != BBE; ++BBI) {
bool match = false;
for (BasicBlock::iterator INSNI = BBI->begin(), INSNE = BBI->end(); INSNI != INSNE; ++INSNI) {
if (isa<CallInst>(INSNI)) {
CallSite CI(cast<Instruction>(INSNI));
if (CI.getCalledFunction() != NULL){
string called_func_name = CI.getCalledFunction()->getName();
if (called_func_name == OMP_PARALLEL_START_NAME && CI.arg_size() == 3) {
// change alloc to malloc_shared
// %5 = call i8* @_Z13malloc_sharedm(i64 20) ; <i8*> [#uses=5]
// %6 = bitcast i8* %5 to float* ; <float*> [#uses=2]
AllocaInst *AllocCall;
Value *arg_0 = CI.getArgument(0); // function
Value *arg_1 = CI.getArgument(1); // context
Value *loop_ub = NULL;
Function *function;
BitCastInst* BCI;
Function *kernel_function;
BasicBlock::iterator iI(*INSNI);
//BasicBlock::iterator iJ = iI+1;
iI++; iI++;
//BasicBlock::iterator iK = iI;
CallInst /**next,*/ *next_next;
if (arg_0 != NULL && arg_1 != NULL /*&& (next = dyn_cast<CallInst>(*iJ))*/
&& (next_next = dyn_cast<CallInst>(iI)) && (next_next->getCalledFunction() != NULL)
&& (next_next->getCalledFunction()->getName() == OMP_PARALLEL_END_NAME)
&& (BCI = dyn_cast<BitCastInst>(arg_1)) && (AllocCall = dyn_cast<AllocaInst>(BCI->getOperand(0)))
&& (function = dyn_cast<Function>(arg_0)) && (loop_ub = find_loop_upper_bound (AllocCall))
&& (kernel_function=convert_to_kernel_function (M, function))){
SmallVector<Value*, 16> Args;
Args.push_back(AllocCall->getArraySize());
Instruction *MallocCall = CallInst::Create(mallocFnTy, Args, "", AllocCall);
CastInst *MallocCast = CastInst::Create(Instruction::BitCast, MallocCall, AllocCall->getType(), "", AllocCall);
ValueMap[AllocCall] = MallocCast;
//AllocCall->replaceAllUsesWith(MallocCall);
// Add offload function
Args.clear();
Args.push_back(loop_ub);
Args.push_back(BCI);
Args.push_back(kernel_function);
if (offloadFnTy == NULL) {
init_offload_type(M, kernel_function);
}
Instruction *call = CallInst::Create(offloadFnTy, Args, "", INSNI);
if (find(toDelete.begin(), toDelete.end(), AllocCall) == toDelete.end()){
toDelete.push_back(AllocCall);
}
toDelete.push_back(&(*INSNI));
match = true;
}
}
else if (called_func_name == OMP_PARALLEL_END_NAME && CI.arg_size() == 0 && match) {
toDelete.push_back(&(*INSNI));
match = false;
}
else if (match) {
toDelete.push_back(&(*INSNI));
}
}
}
}
}
}
}
/* Replace AllocCalls by MallocCalls */
for(DenseMap<Value *, Value *>::iterator I = ValueMap.begin(), E = ValueMap.end(); I != E; I++) {
I->first->replaceAllUsesWith(I->second);
}
/* delete the instructions for get_omp_num_thread and get_omp_thread_num */
while(!toDelete.empty()) {
Instruction *g = toDelete.back();
toDelete.pop_back();
g->eraseFromParent();
}
}
示例10: mangler
/// InputFilename is a LLVM bitcode file. Read it using bitcode reader.
/// Collect global functions and symbol names in symbols vector.
/// Collect external references in references vector.
/// Return LTO_READ_SUCCESS if there is no error.
enum LTOStatus
LTO::readLLVMObjectFile(const std::string &InputFilename,
NameToSymbolMap &symbols,
std::set<std::string> &references)
{
Module *m = getModule(InputFilename);
if (!m)
return LTO_READ_FAILURE;
// Collect Target info
getTarget(m);
if (!Target)
return LTO_READ_FAILURE;
// Use mangler to add GlobalPrefix to names to match linker names.
// FIXME : Instead of hard coding "-" use GlobalPrefix.
Mangler mangler(*m, Target->getTargetAsmInfo()->getGlobalPrefix());
modules.push_back(m);
for (Module::iterator f = m->begin(), e = m->end(); f != e; ++f) {
LTOLinkageTypes lt = getLTOLinkageType(f);
LTOVisibilityTypes vis = getLTOVisibilityType(f);
if (!f->isDeclaration() && lt != LTOInternalLinkage
&& strncmp (f->getName().c_str(), "llvm.", 5)) {
int alignment = ( 16 > f->getAlignment() ? 16 : f->getAlignment());
LLVMSymbol *newSymbol = new LLVMSymbol(lt, vis, f, f->getName(),
mangler.getValueName(f),
Log2_32(alignment));
symbols[newSymbol->getMangledName()] = newSymbol;
allSymbols[newSymbol->getMangledName()] = newSymbol;
}
// Collect external symbols referenced by this function.
for (Function::iterator b = f->begin(), fe = f->end(); b != fe; ++b)
for (BasicBlock::iterator i = b->begin(), be = b->end();
i != be; ++i) {
for (unsigned count = 0, total = i->getNumOperands();
count != total; ++count)
findExternalRefs(i->getOperand(count), references, mangler);
}
}
for (Module::global_iterator v = m->global_begin(), e = m->global_end();
v != e; ++v) {
LTOLinkageTypes lt = getLTOLinkageType(v);
LTOVisibilityTypes vis = getLTOVisibilityType(v);
if (!v->isDeclaration() && lt != LTOInternalLinkage
&& strncmp (v->getName().c_str(), "llvm.", 5)) {
const TargetData *TD = Target->getTargetData();
LLVMSymbol *newSymbol = new LLVMSymbol(lt, vis, v, v->getName(),
mangler.getValueName(v),
TD->getPreferredAlignmentLog(v));
symbols[newSymbol->getMangledName()] = newSymbol;
allSymbols[newSymbol->getMangledName()] = newSymbol;
for (unsigned count = 0, total = v->getNumOperands();
count != total; ++count)
findExternalRefs(v->getOperand(count), references, mangler);
}
}
return LTO_READ_SUCCESS;
}
示例11: runOnSCC
bool PruneEH::runOnSCC(CallGraphSCC &SCC) {
SmallPtrSet<CallGraphNode *, 8> SCCNodes;
CallGraph &CG = getAnalysis<CallGraph>();
bool MadeChange = false;
// Fill SCCNodes with the elements of the SCC. Used for quickly
// looking up whether a given CallGraphNode is in this SCC.
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I)
SCCNodes.insert(*I);
// First pass, scan all of the functions in the SCC, simplifying them
// according to what we know.
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I)
if (Function *F = (*I)->getFunction())
MadeChange |= SimplifyFunction(F);
// Next, check to see if any callees might throw or if there are any external
// functions in this SCC: if so, we cannot prune any functions in this SCC.
// Definitions that are weak and not declared non-throwing might be
// overridden at linktime with something that throws, so assume that.
// If this SCC includes the unwind instruction, we KNOW it throws, so
// obviously the SCC might throw.
//
bool SCCMightUnwind = false, SCCMightReturn = false;
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end();
(!SCCMightUnwind || !SCCMightReturn) && I != E; ++I) {
Function *F = (*I)->getFunction();
if (F == 0) {
SCCMightUnwind = true;
SCCMightReturn = true;
} else if (F->isDeclaration() || F->mayBeOverridden()) {
SCCMightUnwind |= !F->doesNotThrow();
SCCMightReturn |= !F->doesNotReturn();
} else {
bool CheckUnwind = !SCCMightUnwind && !F->doesNotThrow();
bool CheckReturn = !SCCMightReturn && !F->doesNotReturn();
if (!CheckUnwind && !CheckReturn)
continue;
// Check to see if this function performs an unwind or calls an
// unwinding function.
for (Function::iterator BB = F->begin(), E = F->end(); BB != E; ++BB) {
if (CheckUnwind && isa<UnwindInst>(BB->getTerminator())) {
// Uses unwind!
SCCMightUnwind = true;
} else if (CheckReturn && isa<ReturnInst>(BB->getTerminator())) {
SCCMightReturn = true;
}
// Invoke instructions don't allow unwinding to continue, so we are
// only interested in call instructions.
if (CheckUnwind && !SCCMightUnwind)
for (BasicBlock::iterator I = BB->begin(), E = BB->end(); I != E; ++I)
if (CallInst *CI = dyn_cast<CallInst>(I)) {
if (CI->doesNotThrow()) {
// This call cannot throw.
} else if (Function *Callee = CI->getCalledFunction()) {
CallGraphNode *CalleeNode = CG[Callee];
// If the callee is outside our current SCC then we may
// throw because it might.
if (!SCCNodes.count(CalleeNode)) {
SCCMightUnwind = true;
break;
}
} else {
// Indirect call, it might throw.
SCCMightUnwind = true;
break;
}
}
if (SCCMightUnwind && SCCMightReturn) break;
}
}
}
// If the SCC doesn't unwind or doesn't throw, note this fact.
if (!SCCMightUnwind || !SCCMightReturn)
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I) {
Attributes NewAttributes = Attribute::None;
if (!SCCMightUnwind)
NewAttributes |= Attribute::NoUnwind;
if (!SCCMightReturn)
NewAttributes |= Attribute::NoReturn;
Function *F = (*I)->getFunction();
const AttrListPtr &PAL = F->getAttributes();
const AttrListPtr &NPAL = PAL.addAttr(~0, NewAttributes);
if (PAL != NPAL) {
MadeChange = true;
F->setAttributes(NPAL);
}
}
for (CallGraphSCC::iterator I = SCC.begin(), E = SCC.end(); I != E; ++I) {
// Convert any invoke instructions to non-throwing functions in this node
// into call instructions with a branch. This makes the exception blocks
// dead.
if (Function *F = (*I)->getFunction())
//.........这里部分代码省略.........
示例12: cloneFunctionWithoutDeadStore
/*
* Clone a given function removing dead stores
*/
Function* DeadStoreEliminationPass::cloneFunctionWithoutDeadStore(Function *Fn,
Instruction* caller, std::string suffix) {
Function *NF = Function::Create(Fn->getFunctionType(), Fn->getLinkage());
NF->copyAttributesFrom(Fn);
// Copy the parameter names, to ease function inspection afterwards.
Function::arg_iterator NFArg = NF->arg_begin();
for (Function::arg_iterator Arg = Fn->arg_begin(), ArgEnd = Fn->arg_end();
Arg != ArgEnd; ++Arg, ++NFArg) {
NFArg->setName(Arg->getName());
}
// To avoid name collision, we should select another name.
NF->setName(Fn->getName() + suffix);
// Fill clone content
ValueToValueMapTy VMap;
SmallVector<ReturnInst*, 8> Returns;
Function::arg_iterator NI = NF->arg_begin();
for (Function::arg_iterator I = Fn->arg_begin();
NI != NF->arg_end(); ++I, ++NI) {
VMap[I] = NI;
}
CloneAndPruneFunctionInto(NF, Fn, VMap, false, Returns);
// Remove dead stores
std::set<Value*> deadArgs = deadArguments[caller];
std::set<Value*> removeStoresTo;
Function::arg_iterator NFArgIter = NF->arg_begin();
for (Function::arg_iterator FnArgIter = Fn->arg_begin(); FnArgIter !=
Fn->arg_end(); ++FnArgIter, ++NFArgIter) {
Value *FnArg = FnArgIter;
if (deadArgs.count(FnArg)) {
removeStoresTo.insert(NFArgIter);
}
}
std::vector<Instruction*> toRemove;
for (Function::iterator BB = NF->begin(); BB != NF->end(); ++BB) {
for (BasicBlock::iterator I = BB->begin(); I != BB->end(); ++I) {
Instruction *inst = I;
if (!isa<StoreInst>(inst)) continue;
StoreInst *SI = dyn_cast<StoreInst>(inst);
Value *ptrOp = SI->getPointerOperand();
if (removeStoresTo.count(ptrOp)) {
DEBUG(errs() << "will remove this store: " << *inst << "\n");
toRemove.push_back(inst);
}
}
}
for (std::vector<Instruction*>::iterator it = toRemove.begin();
it != toRemove.end(); ++it) {
Instruction* inst = *it;
inst->eraseFromParent();
RemovedStores++;
}
// Insert the clone function before the original
Fn->getParent()->getFunctionList().insert(Fn, NF);
return NF;
}
示例13: runOnFunction
bool TailCallElim::runOnFunction(Function &F) {
// If this function is a varargs function, we won't be able to PHI the args
// right, so don't even try to convert it...
if (F.getFunctionType()->isVarArg()) return false;
TTI = &getAnalysis<TargetTransformInfo>();
BasicBlock *OldEntry = 0;
bool TailCallsAreMarkedTail = false;
SmallVector<PHINode*, 8> ArgumentPHIs;
bool MadeChange = false;
// CanTRETailMarkedCall - If false, we cannot perform TRE on tail calls
// marked with the 'tail' attribute, because doing so would cause the stack
// size to increase (real TRE would deallocate variable sized allocas, TRE
// doesn't).
bool CanTRETailMarkedCall = true;
// Find calls that can be marked tail.
AllocaCaptureTracker ACT;
for (Function::iterator BB = F.begin(), EE = F.end(); BB != EE; ++BB) {
for (BasicBlock::iterator I = BB->begin(), E = BB->end(); I != E; ++I) {
if (AllocaInst *AI = dyn_cast<AllocaInst>(I)) {
CanTRETailMarkedCall &= CanTRE(AI);
PointerMayBeCaptured(AI, &ACT);
// If any allocas are captured, exit.
if (ACT.Captured)
return false;
}
}
}
// Second pass, change any tail recursive calls to loops.
//
// FIXME: The code generator produces really bad code when an 'escaping
// alloca' is changed from being a static alloca to being a dynamic alloca.
// Until this is resolved, disable this transformation if that would ever
// happen. This bug is PR962.
if (ACT.UsesAlloca.empty()) {
for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB) {
if (ReturnInst *Ret = dyn_cast<ReturnInst>(BB->getTerminator())) {
bool Change = ProcessReturningBlock(Ret, OldEntry, TailCallsAreMarkedTail,
ArgumentPHIs, !CanTRETailMarkedCall);
if (!Change && BB->getFirstNonPHIOrDbg() == Ret)
Change = FoldReturnAndProcessPred(BB, Ret, OldEntry,
TailCallsAreMarkedTail, ArgumentPHIs,
!CanTRETailMarkedCall);
MadeChange |= Change;
}
}
}
// If we eliminated any tail recursions, it's possible that we inserted some
// silly PHI nodes which just merge an initial value (the incoming operand)
// with themselves. Check to see if we did and clean up our mess if so. This
// occurs when a function passes an argument straight through to its tail
// call.
if (!ArgumentPHIs.empty()) {
for (unsigned i = 0, e = ArgumentPHIs.size(); i != e; ++i) {
PHINode *PN = ArgumentPHIs[i];
// If the PHI Node is a dynamic constant, replace it with the value it is.
if (Value *PNV = SimplifyInstruction(PN)) {
PN->replaceAllUsesWith(PNV);
PN->eraseFromParent();
}
}
}
// At this point, we know that the function does not have any captured
// allocas. If additionally the function does not call setjmp, mark all calls
// in the function that do not access stack memory with the tail keyword. This
// implies ensuring that there does not exist any path from a call that takes
// in an alloca but does not capture it and the call which we wish to mark
// with "tail".
if (!F.callsFunctionThatReturnsTwice()) {
for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB) {
for (BasicBlock::iterator I = BB->begin(), E = BB->end(); I != E; ++I) {
if (CallInst *CI = dyn_cast<CallInst>(I)) {
if (!ACT.UsesAlloca.count(CI)) {
CI->setTailCall();
MadeChange = true;
}
}
}
}
}
return MadeChange;
}
示例14: gen_code_per_f
/**
* Generate code for
*/
void HeteroOMPTransform::gen_code_per_f (Function* NF, Function* F, Instruction *max_threads){
Function::arg_iterator FI = F->arg_begin();
Argument *ctxname = &*FI;
Function::arg_iterator DestI = NF->arg_begin();
DestI->setName(ctxname->getName());
Argument *ctx_name = &(*DestI);
DestI++;
DestI->setName("tid");
Argument *num_iters = &(*DestI);
#ifdef EXPLICIT_REWRITE
DenseMap<const Value*, Value *> ValueMap;
#else
ValueToValueMapTy ValueMap;
#endif
//get the old basic block and create a new one
Function::const_iterator BI = F->begin();
const BasicBlock &FB = *BI;
BasicBlock *NFBB = BasicBlock::Create(FB.getContext(), "", NF);
if (FB.hasName()){
NFBB->setName(FB.getName());
}
ValueMap[&FB] = NFBB;
//ValueMap[numiters] = num_iters;
ValueMap[ctxname] = ctx_name;
#if EXPLICIT_REWRITE
for (BasicBlock::const_iterator II = FB.begin(), IE = FB.end(); II != IE; ++II) {
Instruction *NFInst = II->clone(/*F->getContext()*/);
// DEBUG(dbgs()<<*II<<"\n");
if (II->hasName()) NFInst->setName(II->getName());
const Instruction *FInst = &(*II);
rewrite_instruction((Instruction *)FInst, NFInst, ValueMap);
NFBB->getInstList().push_back(NFInst);
ValueMap[II] = NFInst;
}
BI++;
for (Function::const_iterator /*BI=F->begin(),*/BE = F->end();BI != BE; ++BI) {
const BasicBlock &FBB = *BI;
BasicBlock *NFBB = BasicBlock::Create(FBB.getContext(), "", NF);
ValueMap[&FBB] = NFBB;
if (FBB.hasName()){
NFBB->setName(FBB.getName());
//DEBUG(dbgs()<<NFBB->getName()<<"\n");
}
for (BasicBlock::const_iterator II = FBB.begin(), IE = FBB.end(); II != IE; ++II) {
Instruction *NFInst = II->clone(/*F->getContext()*/);
if (II->hasName()) NFInst->setName(II->getName());
const Instruction *FInst = &(*II);
rewrite_instruction((Instruction *)FInst, NFInst, ValueMap);
NFBB->getInstList().push_back(NFInst);
ValueMap[II] = NFInst;
}
}
// Remap the instructions again to take care of forward jumps
for (Function::iterator BB = NF->begin(), BE=NF->end(); BB != BE; ++ BB) {
for (BasicBlock::iterator II = BB->begin(); II != BB->end(); ++II){
int opIdx = 0;
//DEBUG(dbgs()<<*II<<"\n");
for (User::op_iterator i = II->op_begin(), e = II->op_end(); i != e; ++i, opIdx++) {
Value *V = *i;
if (ValueMap[V] != NULL) {
II->setOperand(opIdx, ValueMap[V]);
}
}
}
}
#else
SmallVector<ReturnInst*, 8> Returns; // Ignore returns cloned.
CloneFunctionInto(NF, F, ValueMap, false, Returns, "");
#endif
//max_threads->dump();
/* Remap openmp omp_num_threads() and omp_thread_num() */
/*
* define internal void @_Z20initialize_variablesiPfS_.omp_fn.4(i8* nocapture %.omp_data_i) nounwind ssp {
* entry:
* %0 = bitcast i8* %.omp_data_i to i32* ; <i32*> [#uses=1]
* %1 = load i32* %0, align 8 ; <i32> [#uses=2]
* %2 = tail call i32 @omp_get_num_threads() nounwind readnone ; <i32> [#uses=2]
* %3 = tail call i32 @omp_get_thread_num() nounwind readnone ; <i32> [#uses=2]
%4 = sdiv i32 %1, %2
%5 = mul nsw i32 %4, %2
%6 = icmp ne i32 %5, %1
%7 = zext i1 %6 to i32
*/
vector<Instruction *> toDelete;
for (Function::iterator BB = NF->begin(), BE=NF->end(); BB != BE; ++ BB) {
for (BasicBlock::iterator II = BB->begin(); II != BB->end(); ++II){
if (isa<CallInst>(II)) {
CallSite CI(cast<Instruction>(II));
if (CI.getCalledFunction() != NULL){
//.........这里部分代码省略.........
示例15: runOnModule
//
// Method: runOnModule()
//
// Description:
// Entry point for this LLVM pass. Search for insert/extractvalue instructions
// that can be simplified.
//
// Inputs:
// M - A reference to the LLVM module to transform.
//
// Outputs:
// M - The transformed LLVM module.
//
// Return value:
// true - The module was modified.
// false - The module was not modified.
//
bool SimplifyEV::runOnModule(Module& M) {
// Repeat till no change
bool changed;
do {
changed = false;
for (Module::iterator F = M.begin(); F != M.end(); ++F) {
for (Function::iterator B = F->begin(), FE = F->end(); B != FE; ++B) {
for (BasicBlock::iterator I = B->begin(), BE = B->end(); I != BE;) {
ExtractValueInst *EV = dyn_cast<ExtractValueInst>(I++);
if(!EV)
continue;
Value *Agg = EV->getAggregateOperand();
if (!EV->hasIndices()) {
EV->replaceAllUsesWith(Agg);
DEBUG(errs() << "EV:");
DEBUG(errs() << "ERASE:");
DEBUG(EV->dump());
EV->eraseFromParent();
numErased++;
changed = true;
continue;
}
if (Constant *C = dyn_cast<Constant>(Agg)) {
if (isa<UndefValue>(C)) {
EV->replaceAllUsesWith(UndefValue::get(EV->getType()));
DEBUG(errs() << "EV:");
DEBUG(errs() << "ERASE:");
DEBUG(EV->dump());
EV->eraseFromParent();
numErased++;
changed = true;
continue;
}
if (isa<ConstantAggregateZero>(C)) {
EV->replaceAllUsesWith(Constant::getNullValue(EV->getType()));
DEBUG(errs() << "EV:");
DEBUG(errs() << "ERASE:");
DEBUG(EV->dump());
EV->eraseFromParent();
numErased++;
changed = true;
continue;
}
if (isa<ConstantArray>(C) || isa<ConstantStruct>(C)) {
// Extract the element indexed by the first index out of the constant
Value *V = C->getOperand(*EV->idx_begin());
if (EV->getNumIndices() > 1) {
// Extract the remaining indices out of the constant indexed by the
// first index
ExtractValueInst *EV_new = ExtractValueInst::Create(V,
EV->getIndices().slice(1),
"", EV);
EV->replaceAllUsesWith(EV_new);
DEBUG(errs() << "EV:");
DEBUG(errs() << "ERASE:");
DEBUG(EV->dump());
EV->eraseFromParent();
numErased++;
changed = true;
continue;
} else {
EV->replaceAllUsesWith(V);
DEBUG(errs() << "EV:");
DEBUG(errs() << "ERASE:");
DEBUG(EV->dump());
EV->eraseFromParent();
numErased++;
changed = true;
continue;
}
}
continue;
}
if (LoadInst * LI = dyn_cast<LoadInst>(Agg)) {
// if the Agg value came from a load instruction
// replace the extract value intruction with
// a gep and a load.
SmallVector<Value*, 8> Indices;
Type *Int32Ty = Type::getInt32Ty(M.getContext());
Indices.push_back(Constant::getNullValue(Int32Ty));
for (ExtractValueInst::idx_iterator I = EV->idx_begin(), E = EV->idx_end();
I != E; ++I) {
Indices.push_back(ConstantInt::get(Int32Ty, *I));
//.........这里部分代码省略.........