| 124 | } |
| 125 | |
| 126 | bool CFG::WhileEachBlockInReversePostOrder( |
| 127 | BasicBlock* bb, const std::function<bool(BasicBlock*)>& f) { |
| 128 | std::vector<BasicBlock*> po; |
| 129 | std::unordered_set<BasicBlock*> seen; |
| 130 | ComputePostOrderTraversal(bb, &po, &seen); |
| 131 | |
| 132 | for (auto current_bb = po.rbegin(); current_bb != po.rend(); ++current_bb) { |
| 133 | if (!IsPseudoExitBlock(*current_bb) && !IsPseudoEntryBlock(*current_bb)) { |
| 134 | if (!f(*current_bb)) { |
| 135 | return false; |
| 136 | } |
| 137 | } |
| 138 | } |
| 139 | return true; |
| 140 | } |
| 141 | |
| 142 | void CFG::ComputeStructuredSuccessors(Function* func) { |
| 143 | block2structured_succs_.clear(); |
no test coverage detected