/** a basic block is instrumented if it is one of the leaf nodes * in the immediate dominator tree of the control flow graph * or it has an outgoing edge to a basic block that it does * not dominate */ bool FCUseDominator::validateBasicBlock(BPatch_basicBlock* bb){ bool ret = false; BPatch_Vector<BPatch_basicBlock*> immediateDominates; bb->getImmediateDominates(immediateDominates); /** if it is a leaf node */ if(!immediateDominates.size()) ret = true; else{ /** or it has outgoing edge to basic block * it does not dominate */ BPatch_Set<BPatch_basicBlock*> allDom; bb->getAllDominates(allDom); BPatch_Vector<BPatch_basicBlock*> targets; bb->getTargets(targets); for(unsigned int j=0;j<targets.size();j++) if(!allDom.contains(targets[j])){ /** target is not in the set * basic block dominates */ ret = true; break; } } return ret; }
findInsns(const BPatch_Set<BPatch_opCode>& ops) : findLoads(false), findStores(false), findPrefetch(false) { BPatch_opCode* opa = new BPatch_opCode[ops.size()]; ops.elements(opa); for(unsigned int i=0; i<ops.size(); ++i) { switch(opa[i]) { case BPatch_opLoad: findLoads = true; break; case BPatch_opStore: findStores = true; break; case BPatch_opPrefetch: findPrefetch = true; break; } } delete[] opa; }
void BPatch_basicBlock::getAllPostDominates(BPatch_Set<BPatch_basicBlock*>& buffer){ std::set<BPatch_basicBlock *> tmp; getAllPostDominates(tmp); std::copy(tmp.begin(), tmp.end(), std::inserter(buffer.int_set, buffer.begin())); }
bool instrumentMemoryWrites(dynHandle *dh, BPatch_function *func) { BPatch_Set<BPatch_basicBlock*> allBlocks; BPatch_snippet incSnippet; BPatch_Set<BPatch_opCode> ops; BPatch_Set<BPatch_basicBlock*>::iterator iter; int bb_warn_cnt = 0, bb_pass_cnt = 0; sendMsg(config.outfd, ID_INST_MEM_WRITE, VERB2); sendMsg(config.outfd, ID_GET_CFG, VERB3); BPatch_flowGraph *appCFG = func->getCFG(); if (!appCFG) { sendMsg(config.outfd, ID_GET_CFG, VERB3, ID_FAIL, "Failure in BPatch_function::getCFG()"); goto fail; } else { sendMsg(config.outfd, ID_GET_CFG, VERB3, ID_PASS); } sendMsg(config.outfd, ID_INST_GET_BB, VERB3); if (!appCFG->getAllBasicBlocks(allBlocks)) { sendMsg(config.outfd, ID_INST_GET_BB, VERB3, ID_FAIL, "Failure in BPatch_flowGraph::getAllBasicBlocks()"); goto fail; } else if (allBlocks.size() == 0) { sendMsg(config.outfd, ID_INST_GET_BB, VERB3, ID_WARN, "No basic blocks found in function"); goto fail; } else { sendMsg(config.outfd, ID_INST_GET_BB, VERB3, ID_PASS); } if (! generateInstrumentation (dh, func, &incSnippet)) goto fail; ops.insert(BPatch_opStore); sendMsg(config.outfd, ID_INST_BB_LIST, VERB3); for (iter = allBlocks.begin(); iter != allBlocks.end(); iter++) { if (!shouldInsert()) continue; sendMsg(config.outfd, ID_INST_GET_BB_POINTS, VERB4); BPatch_Vector<BPatch_point*> *points = (*iter)->findPoint(ops); if (!points) { sendMsg(config.outfd, ID_INST_GET_BB_POINTS, VERB4, ID_WARN, "Failure in BPatch_basicBlock::findPoint()"); ++bb_warn_cnt; continue; } else if (points->size() == 0) { sendMsg(config.outfd, ID_INST_GET_BB_POINTS, VERB4, ID_WARN, "No instrumentation points found in basic block"); ++bb_warn_cnt; continue; } else { sendMsg(config.outfd, ID_INST_GET_BB_POINTS, VERB4, ID_PASS); } sendMsg(config.outfd, ID_INST_INSERT_CODE, VERB4); BPatchSnippetHandle *handle = dh->addSpace->insertSnippet(incSnippet, *points); if (!handle) { sendMsg(config.outfd, ID_INST_INSERT_CODE, VERB4, ID_FAIL, "Failure in BPatch_process::insertSnippet()"); ++bb_warn_cnt; continue; } else { sendMsg(config.outfd, ID_INST_INSERT_CODE, VERB4, ID_PASS); ++bb_pass_cnt; } } if (bb_warn_cnt) sendMsg(config.outfd, ID_INST_BB_LIST, VERB3, ID_WARN, sprintf_static("%d warning(s), %d passed.", bb_warn_cnt, bb_pass_cnt)); else sendMsg(config.outfd, ID_INST_BB_LIST, VERB3, ID_PASS); sendMsg(config.outfd, ID_INST_MEM_WRITE, VERB2, ID_PASS); return true; fail: sendMsg(config.outfd, ID_INST_MEM_WRITE, VERB2, ID_WARN, "Failure while instrumenting memory writes."); return false; }