// Currently the transfer function used by DFAGen is assumed to be: // Y = gen[n] U (X - kill[n]). OA_ptr<DataFlowSet> ManagerReachingDefs::transfer( OA_ptr<DataFlowSet> xdfset, StmtHandle stmt) { OA_ptr<ReachingDefsDFSet> xdfgenset; xdfgenset = xdfset.convert<ReachingDefsDFSet>(); OA_ptr<ReachingDefsDFSet> x; x = new ReachingDefsDFSet(*xdfgenset); // if debug mode is on print information about transfer function if (debug) { cout << "In transfer: " << endl; cout << "\t Stmt = " << mIR->toString(stmt) << endl; cout << "\t X = "; dumpset(x); } OA_ptr<DataFlowSet> genBaseObj = genSet(stmt, x); OA_ptr<ReachingDefsDFSet> gen = genBaseObj.convert<ReachingDefsDFSet>(); OA_ptr<DataFlowSet> killBaseObj = killSet(stmt, x); OA_ptr<ReachingDefsDFSet> kill = killBaseObj.convert<ReachingDefsDFSet>(); // Add gen[n] to Y OA_ptr<DataFlow::DataFlowSetImplIterator<StmtHandle > > genIter; genIter = new DataFlow::DataFlowSetImplIterator<StmtHandle > (gen); for(; genIter->isValid(); ++(*genIter)) { StmtHandle genVal; genVal = genIter->current(); mReachingDefsMap->insert(stmt, genVal); } // Add X - kill[n] to Y x->minusEqu(*kill); OA_ptr<DataFlow::DataFlowSetImplIterator<StmtHandle > > xIter; xIter = new DataFlow::DataFlowSetImplIterator<StmtHandle > (x); for(; xIter->isValid(); ++(*xIter)) { StmtHandle xVal; xVal = xIter->current(); mReachingDefsMap->insert(stmt, xVal); } // if debug mode is on print information about transfer function if(debug) { cout << "\t gen = "; dumpset(gen); cout << "\t kill = "; dumpset(kill); cout << "\t Y = "; dumpset(mReachingDefsMap->getReachingDefsSet(stmt)); } return mReachingDefsMap->getReachingDefsSet(stmt); }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void AggregateCopyPropagation::LocalCopyPropagation(Block* block, TOperandToIdDict& availableCopies) { BitVector killSet(infoList_.Count()); BitVector copySet(infoList_.Count()); // Unused here. // Try to use the original operand instead of the copy. // We need to recompute the 'kill' set, because copies available // at the block entry might be invalidated by 'store' and 'call'. for(auto instr = block->FirstInstruction(); instr; instr = instr->NextInstruction()) { if(auto callInstr = instr->As<CallInstr>()) { // This might be a call that kills copies. AddToKillSet(callInstr, killSet, copySet); ReplaceWithOriginal(callInstr, availableCopies, killSet); } else if(auto storeInstr = instr->As<StoreInstr>()) { AddToKillSet(storeInstr, killSet, copySet); } else if(auto loadInstr = instr->As<LoadInstr>()) { // Try to replace the operands with the original ones. ReplaceWithOriginal(loadInstr, availableCopies, killSet); } } }