void TestInstVisitor::visitSwitchInst(SwitchInst &I){ if (except){ return; } DynValEntry entry; size_t n = fread(&entry, sizeof(DynValEntry), 1, dlog); if (entry.entrytype == EXCEPTIONENTRY){ except = true; return; } assert(entry.entrytype == SWITCHENTRY); //printf("switch %d\n", entry.entry.switchstmt.cond); IntegerType *intType = IntegerType::get(getGlobalContext(), sizeof(int)*8); ConstantInt *caseVal = ConstantInt::get(intType, entry.entry.switchstmt.cond); SwitchInst::CaseIt caseIndex = I.findCaseValue(caseVal); TFP->setNextBB(I.getSuccessor(caseIndex.getSuccessorIndex())); }
/// getFeasibleSuccessors - Return a vector of booleans to indicate which /// successors are reachable from a given terminator instruction. void SparseSolver::getFeasibleSuccessors(TerminatorInst &TI, SmallVectorImpl<bool> &Succs, bool AggressiveUndef) { Succs.resize(TI.getNumSuccessors()); if (TI.getNumSuccessors() == 0) return; if (BranchInst *BI = dyn_cast<BranchInst>(&TI)) { if (BI->isUnconditional()) { Succs[0] = true; return; } LatticeVal BCValue; if (AggressiveUndef) BCValue = getOrInitValueState(BI->getCondition()); else BCValue = getLatticeState(BI->getCondition()); if (BCValue == LatticeFunc->getOverdefinedVal() || BCValue == LatticeFunc->getUntrackedVal()) { // Overdefined condition variables can branch either way. Succs[0] = Succs[1] = true; return; } // If undefined, neither is feasible yet. if (BCValue == LatticeFunc->getUndefVal()) return; Constant *C = LatticeFunc->GetConstant(BCValue, BI->getCondition(), *this); if (C == 0 || !isa<ConstantInt>(C)) { // Non-constant values can go either way. Succs[0] = Succs[1] = true; return; } // Constant condition variables mean the branch can only go a single way Succs[C->isNullValue()] = true; return; } if (isa<InvokeInst>(TI)) { // Invoke instructions successors are always executable. // TODO: Could ask the lattice function if the value can throw. Succs[0] = Succs[1] = true; return; } if (isa<IndirectBrInst>(TI)) { Succs.assign(Succs.size(), true); return; } SwitchInst &SI = cast<SwitchInst>(TI); LatticeVal SCValue; if (AggressiveUndef) SCValue = getOrInitValueState(SI.getCondition()); else SCValue = getLatticeState(SI.getCondition()); if (SCValue == LatticeFunc->getOverdefinedVal() || SCValue == LatticeFunc->getUntrackedVal()) { // All destinations are executable! Succs.assign(TI.getNumSuccessors(), true); return; } // If undefined, neither is feasible yet. if (SCValue == LatticeFunc->getUndefVal()) return; Constant *C = LatticeFunc->GetConstant(SCValue, SI.getCondition(), *this); if (C == 0 || !isa<ConstantInt>(C)) { // All destinations are executable! Succs.assign(TI.getNumSuccessors(), true); return; } SwitchInst::CaseIt Case = SI.findCaseValue(cast<ConstantInt>(C)); Succs[Case.getSuccessorIndex()] = true; }