diff --git a/src/Transformations/MoveOperators/move_operators.cpp b/src/Transformations/MoveOperators/move_operators.cpp index a92ece2..ec468b5 100644 --- a/src/Transformations/MoveOperators/move_operators.cpp +++ b/src/Transformations/MoveOperators/move_operators.cpp @@ -522,72 +522,54 @@ static bool reorderOperatorsInBasicBlockUsingDeps( return false; } - map originalIndex; + map newIndex; + map movesCount; + vector order = ops; for (int i = 0; i < (int)ops.size(); ++i) - originalIndex[ops[i]] = i; - - map> moveAfter; - set moved; + { + newIndex[ops[i]] = i; + movesCount[ops[i]] = 0; + } for (SgStatement* st : ops) { auto itDeps = operatorsDependencies.find(st); - if (itDeps == operatorsDependencies.end() || itDeps->second.empty()) - continue; - - SgStatement* lastDep = nullptr; - int lastDepIdx = -1; - for (SgStatement* dep : itDeps->second) + if (itDeps != operatorsDependencies.end() && !itDeps->second.empty()) { - auto itIdx = originalIndex.find(dep); - if (itIdx != originalIndex.end() && itIdx->second > lastDepIdx) + SgStatement* lastDep = nullptr; + int lastDepIdx = -1; + for (SgStatement* dep : itDeps->second) { - lastDep = dep; - lastDepIdx = itIdx->second; + auto itIdx = newIndex.find(dep); + if (itIdx != newIndex.end() && itIdx->second > lastDepIdx) + { + lastDep = dep; + lastDepIdx = itIdx->second; + } + } + if (lastDep && lastDep != st) + { + const int stPos = newIndex[st]; + const int ldPos = newIndex[lastDep]; + if (stPos > ldPos) + { + auto itSt = find(order.begin(), order.end(), st); + auto itLd = find(order.begin(), order.end(), lastDep); + if (itSt == order.end() || itLd == order.end()) + return false; + order.erase(itSt); + itLd = find(order.begin(), order.end(), lastDep); + if (itLd == order.end()) + return false; + order.insert(itLd + 1 + movesCount[lastDep], st); + for (int i = 0; i < (int)order.size(); ++i) + newIndex[order[i]] = i; + movesCount[lastDep] += 1; + } } } - if (!lastDep || lastDep == st) - continue; - - moveAfter[lastDep].push_back(st); - moved.insert(st); } - vector order; - order.reserve(ops.size()); - set emitted; - set active; - bool invalidOrder = false; - - function emitStatement = [&](SgStatement* st) - { - if (!st || invalidOrder || emitted.count(st)) - return; - if (active.count(st)) - { - invalidOrder = true; - return; - } - - active.insert(st); - emitted.insert(st); - order.push_back(st); - - auto itMovedAfter = moveAfter.find(st); - if (itMovedAfter != moveAfter.end()) - for (SgStatement* dependent : itMovedAfter->second) - emitStatement(dependent); - - active.erase(st); - }; - - for (SgStatement* st : ops) - if (!moved.count(st)) - emitStatement(st); - - if (invalidOrder || order.size() != ops.size()) - return false; - bool changed = false; for (size_t i = 0; i < ops.size(); ++i) if (ops[i] != order[i])