84 const unsigned int ii) :
87 cachedSize_(INT_MIN), maxCycle_(INT_MAX), ddg_(NULL), fu_(fu),
88 operandShareCount_(0) {
103 abortWithError(
"Wrong use of canAssign, use also third parameter!");
125 OperandWriteVector::const_iterator j = operandWrites.find(modCycle);
126 if (j != operandWrites.end()) {
131 for (ResultMap::const_iterator rri =
resultRead_.begin();
134 unsigned int resultReadCount = resultRead.rbegin()->first;
135 if (modCycle < (
int)resultReadCount &&
136 (MapTools::valueForKeyNoThrow<ResultHelperPair>(
137 resultRead, modCycle)).first.po != NULL) {
142 if (modCycle >= (
int)
size()) {
147 (MapTools::valueForKeyNoThrow<ResourceReservationVector>(
149 std::string msg =
"Execution pipeline is missing resources!";
154 MapTools::valueForKeyNoThrow<ResourceReservationVector>(
156 if (rrv.size() == 0) {
162 if (rr.first != NULL) {
188 OperandWriteVector::const_iterator j = operandWrites.find(modCycle);
189 if (j == operandWrites.end()) {
194 if (mnpp.first == NULL ||
195 (!mnpp.first->move().isUnconditional() &&
196 mnpp.second == NULL)) {
220 if (rhp.first.po == NULL) {
223 if (rhp.first.realCycle == realCycle &&
224 rhp.first.po == &po) {
227 if (rhp.second.po == NULL) {
249 if (oup.first.po == NULL) {
252 if (oup.first.realCycle == realCycle &&
253 oup.first.po == &po) {
256 if (oup.second.po == NULL) {
276 int resultCycle = triggerCycle + hwop.
latency(outIndex);
292 int operandUseCycle = triggerCycle + hwop.
slack(i+1);
313 if (rhp.first.po == &po) {
316 if (rhp.first.count == 0) {
317 if (rhp.second.count == 0) {
318 resultWriten.erase(rrMod);
321 rhp.first = rhp.second;
326 assert(rhp.second.po == &po);
329 if (rhp.second.count == 0) {
342 OperandUseVector::iterator i = operandUsed.find(modCycle);
343 assert(i != operandUsed.end());
345 if (mnpp.first.po == &po) {
346 if (mnpp.second.po == NULL) {
347 operandUsed.erase(i);
349 mnpp.first = mnpp.second;
350 mnpp.second.po = NULL;
353 if (mnpp.second.po == &po) {
354 mnpp.second.po = NULL;
370 int resultCycle = triggerCycle + hwop.
latency(outIndex);
386 int resultCycle = triggerCycle + hwop.
slack(i+1);
393 abortWithError(
"Execution Pipeline Resource needs 3 arguments assign");
432 unsigned int readCount = resultRead.
size();
433 if (readCount <= modCycle) {
434 resultRead[modCycle] =
439 for (
unsigned int i = readCount; i <= modCycle; i++) {
441 resultRead.push_back(
452 if (rhp.first.po == NULL) {
455 if (rhp.first.po == pOp) {
458 if (rhp.second.po == NULL) {
461 if (rhp.second.po == pOp) {
464 assert(0 &&
"result read of invalid op");
476 std::pair<MoveNode*, int>(&node,cycle));
493 std::cerr <<
"\t\t\tAssigning destination: " << node.
toString() << std::endl;
503 std::string opName =
"";
508 std::cerr <<
"\t\t\t\tis trigger!" << std::endl;
516 std::string msg =
"Using non opcodeSetting triggering move. ";
524 for (
unsigned int j = 0 ;
535 if (rr.first != NULL) {
536 assert(rr.second == NULL&&
"Resource already in use?");
554 if (mnpp.first == NULL) {
557 if (mnpp.second != NULL || !
exclusiveMoves(mnpp.first, &node, cycle)) {
558 std::string msg =
name() +
" had previous operation ";
559 msg += mnpp.first->destinationOperation().toString() +
"\n ";
560 msg += mnpp.first->toString() +
" in inst.index " ;
562 msg +=
" other trigger: ";
563 msg += mnpp.first->toString();
583 abortWithError(
"Execution Pipeline Resource needs 3 arguments unassign");
608 if (node.
cycle() != cycle) {
610 "Trying to unassign node from different cycle "
611 "then it was assigned to!");
627 unsigned int resultReady =
637 if (resultReadPair.first.po == &po) {
639 resultReadPair.first.count--;
640 if (resultReadPair.first.count == 0) {
641 if (resultReadPair.second.count == 0) {
643 resultRead.erase(modCycle);
645 resultReadPair.first = resultReadPair.second;
646 resultReadPair.second.count = 0;
647 resultReadPair.second.realCycle = modCycle;
648 resultReadPair.second.po = NULL;
652 if (resultReadPair.second.po == &po) {
654 resultReadPair.second.count--;
655 if (resultReadPair.second.count == 0) {
656 resultReadPair.second.realCycle = modCycle;
657 resultReadPair.second.po = NULL;
665 #pragma GCC diagnostic ignored "-Wunused-variable"
681 std::cerr <<
"\tUnassigning destination: " << node.
toString() << std::endl;
686 std::cerr <<
"\t\tNot dest operatioN!" << std::endl;
699 std::cerr <<
"\t\t assigned destinations not contain!" << std::endl;
708 assert (mnpp.first != NULL);
709 if (mnpp.second == &node) {
712 assert(mnpp.first == &node);
713 mnpp.first = mnpp.second;
721 std::cerr <<
"\t\t not trigger!" << std::endl;
735 std::string opName =
"";
742 std::string msg =
"Trying to unassign operation \'";
744 msg +=
"\' not supported on FU!";
753 std::string msg =
"Unassigning operation longer then scope!";
769 if (rr.first == &node) {
772 "unassigning pipeline res not used by this op");
774 rr.first = rr.second;
777 if (rr.second == &node) {
780 "unassigning pipeline res not used by this op");
789 #pragma GCC diagnostic warning "-Wunused-variable"
799 for (
auto i = inEdges.begin(); i != inEdges.end(); i++) {
829 std::cerr <<
"\t\t\tcanAssignSource called for: " << node.
toString() <<
" on cycle: "
830 << cycle << std::endl;
832 int outputIndex = -1;
850 std::cerr <<
"too long latency overlappingloop" << std::endl;
862 if (resultReady != INT_MAX) {
863 if (port.
noRegister() && resultReady != cycle) {
867 if (cycle < resultReady) {
872 std::cerr <<
"\tresult not yet ready" << std::endl;
878 int triggerCycle = (trigger != NULL && trigger->
isPlaced()) ?
879 trigger->
cycle() : -1;
882 trigger, triggerCycle) &&
884 resultReady, *po,
resultPort, *trigger, triggerCycle);
889 std::cerr <<
"Other op writing result at same cycle, this is illgal" << std::endl;
900 std::cerr <<
"\t\t\t\t\ttrigger needs negative cycle" << std::endl;
909 if (allResults.
count() >1) {
911 std::cerr <<
"\t\t\t\tSame op has multiple results." << std::endl;
914 for (
int i = 0; i < allResults.
count(); i++) {
916 if (&res == &node || !res.
isPlaced()) {
919 int resCycle = res.
cycle();
923 resultReady = std::min(resultReady, resCycle);
925 std::cerr <<
"\t\t\t\t\tother result, of node: "
927 <<
" used at cycle: " << resCycle << std::endl;
929 if (trigger == NULL) {
933 resCycle, cycle, node,
resultPort, trigger,-1)) {
937 if (resultReady != INT_MAX && resultReady < cycle) {
939 std::cerr <<
"\t\t\t\tChecking if res not overwritten."
943 cycle, resultReady, node,
resultPort, trigger, -1)) {
947 std::cerr <<
"\t\t\t\tres not overwritten." << std::endl;
953 int triggerCycle = (trigger != NULL && trigger->
isPlaced()) ?
954 trigger->
cycle() : -1;
962 std::cerr <<
"\t\t\t\tcheck if result allowed at this cycle?" << std::endl;
965 cycle, *po,
resultPort, *trigger, triggerCycle)) {
970 std::cerr <<
"\t\t\t\tcheck if result causes trigger between opshares?" << std::endl;
993 bool triggers)
const {
1000 std::cerr <<
"\t\t\tCanAssignDestination called for: " << node.
toString()
1001 <<
" Cycle: " << cycle <<
" PO: "
1004 std::cerr <<
"\t\t\t\tTriggers." << std::endl;
1046 std::cerr <<
"\t\tOperand too late" << std::endl;
1059 std::cerr <<
"\t\tTrigger too early" << std::endl;
1066 std::cerr <<
"\t\t\t\tCanAssignDestination is trigger: "
1067 << node.
toString() <<
" Cycle: " << cycle << std::endl;
1073 std::cerr <<
"\t\t\t\t\tTrigger too late for results" << std::endl;
1081 std::cerr <<
"\t\t\t\tOperands overwritten" << std::endl;
1089 std::cerr <<
"\t\t\t\tResources prevent trigger" << std::endl;
1106 const MoveNode& mn,
int cycle)
const {
1108 std::cerr <<
"\t\tTesting operand not overwritten by other ops: " <<
1109 mn.
toString() <<
" cycle: " << cycle << std::endl;
1114 if (trigger == &mn) {
1116 std::cerr <<
"\t\t\tmn is trigger, no need to check overwrite" << std::endl;
1120 if (trigger == NULL || !trigger->
isPlaced()) {
1122 std::cerr <<
"\t\t\ttrigger null or not scheduled on PO: "
1128 int triggerCycle = trigger->
cycle();
1138 int operandWriteCycle,
1150 std::cerr <<
"\t\t\tOperandOverWritten called for: " << operand.
toString()
1152 <<
" trigger: " << trigger.
toString() <<
"owc: "
1153 << operandWriteCycle <<
" tc: " << triggerCycle << std::endl;
1160 int operandUseCycle = triggerCycle + hwop.
slack(opIndex);
1163 if (operandUseCycle - operandWriteCycle >= (
int)ii) {
1165 std::cerr <<
"\t\t\t\tOperand LR over loop iteration(2): " << ii
1172 std::cerr <<
"\t\t\t\tTesting port: " << port.
name() << std::endl;
1181 std::cerr <<
"\t\t\t\tOperandWriteCycle: " << operandWriteCycle << std::endl
1182 <<
"\t\t\t\tOperandUseCycle: " << operandUseCycle << std::endl;
1185 for (
int j = operandWriteCycle; j <= operandUseCycle; j++) {
1187 std::cerr <<
"\t\t\t\tTesting if overwritten in cycle: " << j << std::endl;
1190 OperandWriteVector::const_iterator owi = operandWritten.find(modCycle);
1191 if (owi == operandWritten.end()) {
1195 if (mnpp.first != NULL && mnpp.first != &operand &&
1198 std::cerr <<
"\t\t\t\t\tOverwritten by: " << mnpp.first->toString() << std::endl;
1202 if (mnpp.second != NULL && mnpp.second != &operand &&
1205 std::cerr <<
"\t\t\t\t\tOverwritten(2) by: " << mnpp.second->toString() << std::endl;
1211 std::cerr <<
"\t\t\tNot overwritten" << std::endl;
1217 int triggerCycle,
const MoveNode& trigger)
const {
1220 std::cerr <<
"\t\tTesting op overwrite for: " << po.
toString() <<
" cycle: " << triggerCycle << std::endl;
1224 if (&inputMove == &trigger) {
1229 triggerCycle, triggerCycle, po, inputMove, trigger)) {
1234 int operandWriteCycle = inputMove.
cycle();
1236 operandWriteCycle, triggerCycle, po, inputMove, trigger)) {
1245 int cycle,
const MoveNode& node)
const {
1253 std::string opName =
"";
1282 for (
unsigned int i = 0; i < rLat &&
canAssign; i++) {
1284 for (
unsigned int j = 0 ; j < nRes; j++) {
1288 if (((
unsigned int)(cycle + i)) >
1297 std::vector<std::vector<bool> >
1298 assigned(nRes, std::vector<bool>(rLat,
false));
1300 unsigned int curSize =
size();
1302 for (
unsigned int i = 0; i < rLat &&
canAssign; i++) {
1305 if (ii == INT_MAX) {
1306 if (modci >= curSize) {
1312 if (fupSize <= modci) {
1329 if (rr.first != NULL) {
1331 if (rr.second == NULL &&
1333 assigned[j][i] =
true;
1340 assigned[j][i] =
true;
1350 if (assigned[j][i]) {
1354 if (rr.first == &node) {
1355 assert(rr.second == NULL);
1356 rr.first = rr.second;
1359 if (rr.second == &node) {
1362 assert(0&&
"assignment to undo not found");
1431 if (length == -1 || (dstCount == 0 && srcCount ==0)) {
1435 int stoppingCycle = length;
1438 stoppingCycle = std::min(stoppingCycle, dstMin);
1442 stoppingCycle = std::min(stoppingCycle, srcMin);
1445 for (
int i = length; i >= stoppingCycle; i--) {
1446 ResourceReservationTable::const_iterator iter =
1452 if (rrv.size() == 0) {
1458 if (rr.first != NULL) {
1497 if (maxResults> maximum) {
1498 maximum = maxResults;
1501 return std::max(maximum, (
int)(
size()) - 1);
1507 min = std::min(min, srcMin);
1511 min = std::min(min, dstMin);
1518 for (
int i = resultWriten.
size() -1; i >= min; i--) {
1520 MapTools::valueForKeyNoThrow<ResultHelperPair>(
1522 if (rhp.first.po != NULL) {
1523 if (
int(rhp.first.realCycle) > highest) {
1524 highest = rhp.first.realCycle;
1526 if (rhp.second.po != NULL) {
1527 if (
int(rhp.second.realCycle) > highest) {
1528 highest = rhp.second.realCycle;
1534 for (ResultMap::const_iterator rri =
resultRead_.begin();
1537 for (
int i = resultRead.
size() -1; i >= min ; i--) {
1539 MapTools::valueForKeyNoThrow<ResultHelperPair>(
1541 if (rrp.first.po != NULL) {
1542 if (
int(rrp.first.realCycle) > highest) {
1543 highest = rrp.first.realCycle;
1545 if (rrp.second.po != NULL) {
1546 if (
int(rrp.second.realCycle) > highest) {
1547 highest = rrp.second.realCycle;
1570 MapTools::valueForKeyNoThrow<ResultHelperPair>(
1571 rwi->second, modCycle);
1573 if (rhp.first.count != 0) {
1574 assert(rhp.first.po != NULL);
1575 if (rhp.first.po != &po &&
1577 rhp.first.po->triggeringMove(), trigger, INT_MAX)) {
1580 if (rhp.second.po != &po && rhp.second.count != 0) {
1581 assert(rhp.second.po != NULL);
1583 rhp.second.po->triggeringMove(), trigger, INT_MAX)) {
1604 int cycle,
const MoveNode& node,
const MoveNode* trigger,
int triggerCycle)
1619 "Trying to get next result for move that is not"
1620 " in ProgramOperation");
1624 if (trigger == NULL) {
1634 unsigned int rwSize = resultWriten.
size();
1635 for (
unsigned int i = cycle; i < cycle + ii; i++) {
1638 if (rwSize <= modi) {
1639 if (ii == INT_MAX) {
1647 MapTools::valueForKeyNoThrow<ResultHelperPair>(resultWriten,modi);
1648 if (rhp.first.count != 0) {
1649 assert(rhp.first.po != NULL);
1650 if (rhp.first.po != sourcePo &&
1652 rhp.first.po->triggeringMove(), trigger,
1654 return rhp.first.realCycle;
1656 if (rhp.second.po != sourcePo && rhp.second.count != 0) {
1657 assert(rhp.second.po != NULL);
1659 rhp.second.po->triggeringMove(), trigger,
1661 return rhp.second.realCycle;
1681 if (trigger == NULL || !trigger->
isPlaced()) {
1683 std::cerr <<
"\t\t\t\tTrigger NULL or not scheduled: "
1699 std::cerr <<
"\t\t\t\treturning -1 at end of rrcycle() " << std::endl;
1721 #ifdef NO_OVERCOMMIT
1724 if (mn1 == NULL || mn2 == NULL || !mn1->
isMove() || !mn2->
isMove()) {
1745 (!mn2->
isPlaced() && (mn1->
cycle() == cycle || cycle == INT_MAX))) {
1786 const MoveNode& trigger,
int cycle)
const {
1795 int resultCycle = cycle + hwop.
latency(outIndex);
1798 resultCycle, po, port, trigger, cycle)) {
1822 int resultCycle = cycle + hwop.
latency(outIndex);
1826 std::cerr <<
"\t\t\t\tresult move: " << mn.
toString()
1827 <<
" schedule too late: " << resultCycle << std::endl;
1832 mn.
cycle(), resultCycle, mn, port, &trigger, cycle)) {
1855 const MoveNode& trigger,
int triggerCycle)
1859 if (&trigger != NULL) {
1860 std::cerr <<
"\t\tChecking that result for po: " << po.
toString() <<
" allowed at cycle "
1861 << resultCycle <<
" , trigger: " << trigger.
toString() <<
" at cycle: " << triggerCycle << std::endl;
1863 std::cerr <<
"\t\tChecking that result for po: " << po.
toString() <<
" allowed at cycle "
1864 << resultCycle <<
" , trigger: NULL at cycle: " << triggerCycle << std::endl;
1872 rri->second : empty;
1879 unsigned int rrSize = resultRead.
size();
1881 for (
unsigned int i = rrMod; i < rrMod + ii; i++) {
1883 bool modiLooped = modi < rrMod;
1885 if (modi >= rrSize) {
1886 if (ii == INT_MAX) {
1895 MapTools::valueForKeyNoThrow<ResultHelperPair>(resultRead, modi);
1896 if (resultReadPair.first.count > 0) {
1898 if (resultReadPair.first.po != &po) {
1899 assert (resultReadPair.first.po != NULL);
1903 resultReadPair.first.po->triggeringMove();
1905 if (resultReadPair.first.po == &po) {
1912 if (otherReady == -1) {
1916 bool orLooped = or2Mod > (int)modi;
1919 std::cerr <<
"\t\t\tOther po: " << resultReadPair.first.po->toString() << std::endl;
1920 std::cerr <<
"\t\t\tOther ready: " << otherReady << std::endl;
1921 std::cerr <<
"\t\t\tRR cycle: " << rrMod << std::endl;
1922 std::cerr <<
"\t\t\tOther ready mod: " << or2Mod << std::endl;
1925 if (modiLooped == orLooped) {
1926 if ((or2Mod <= (
int)rrMod && or2Mod != -1) &&
1927 (triggerCycle == -1 || or2Mod != -1)) {
1929 std::cerr <<
"\t\t\t\tfail(1)" << std::endl;
1933 if (otherTrigger != NULL &&
1940 if (or2Mod >= (
int)rrMod && (triggerCycle == -1 || or2Mod != -1)) {
1942 std::cerr <<
"\t\t\t\tfail(2)" << std::endl;
1946 if (otherTrigger != NULL &&
1956 if (resultReadPair.second.count > 0) {
1958 resultReadPair.second.po->triggeringMove();
1960 if (resultReadPair.second.po == &po) {
1967 bool orLooped = or2Mod > (int)modi;
1970 if (modiLooped == orLooped) {
1971 if (or2Mod <= (
int)rrMod &&
1972 (triggerCycle == -1 || or2Mod != -1)) {
1974 std::cerr <<
"\t\t\t\tfail(3)" << std::endl;
1978 if (otherTrigger != NULL &&
1985 if (or2Mod >= (
int)rrMod &&
1986 (triggerCycle == -1 || or2Mod != -1)) {
1988 std::cerr <<
"\t\t\t\tfail(4)" << std::endl;
1992 if (otherTrigger != NULL &&
2049 int resultReadCycle,
int resultReadyCycle,
2051 const MoveNode* trigger,
int triggerCycle)
const {
2073 if (otherResult == INT_MAX && ii != INT_MAX) {
2079 if (orMod < (
int)rrMod) {
2081 if (modCycle < rrMod && orMod <= (
int)modCycle) {
2089 if ((rrMod != INT_MAX && orMod != INT_MAX && modCycle < rrMod) ||
2090 orMod <= (
int)modCycle) {
2093 std::cerr <<
"\t\t\t\tresultnotoverwritten returning fail, rrmod:"
2094 << rrMod <<
" ormod: " << orMod <<
" modcycle: "
2095 << modCycle << std::endl;
2114 auto owi2 = owv.find(modCycle);
2115 if (owi2 != owv.end()) {
2116 auto mnpp = owi2->second;
2117 if (mnpp.first != NULL &&
2120 std::cerr <<
"MN of other op: " << mnpp.first->toString()
2121 <<
" writing to same port at same cycle"
2134 std::cerr <<
"\t\tTesting " << mn.
toString() <<
" that operand at port: "
2135 << port.
name() <<
" allowed at cycle: " << cycle << std::endl;
2142 OperandUseMap::const_iterator rui =
operandsUsed_.find(&port);
2148 size_t operandUsedSize = operandUsed.
size();
2152 "Trying to get next result for move that is not "
2153 "in ProgramOperation");
2157 int nextOperandUseCycle = cycle;
2159 OperandUseVector::const_iterator i =
2160 operandUsed.find(nextOperandUseModCycle);
2164 std::cerr <<
"\t\t\tTesting use from cycle: " << nextOperandUseCycle << std::endl;
2166 if (i != operandUsed.end()) {
2168 std::cerr <<
"\t\t\t\tcycle " << nextOperandUseCycle <<
" not empty." << std::endl;
2171 if (operandUse.
po != NULL) {
2174 if (opUseTrigger != NULL) {
2176 std::cerr <<
"\t\t\t\tFound using trigger: " << opUseTrigger->
toString() << std::endl;
2182 mn, port, cycle, operandUse, nextOperandUseModCycle,
2186 if (opUseTrigger == NULL ||
2188 bool allScheduled =
true;
2190 for (
int i = 0; i < imc; i++) {
2192 allScheduled =
false;
2203 if (operandUse2.
po != NULL) {
2209 mn, port, cycle, operandUse2,
2210 nextOperandUseModCycle,
2218 nextOperandUseCycle++;
2220 if (ii == INT_MAX && nextOperandUseCycle >= (
int)operandUsedSize) {
2224 if (nextOperandUseCycle - cycle >= (
int)ii) {
2228 i = operandUsed.find(nextOperandUseModCycle);
2237 int operandWriteCycle,
2241 std::cerr <<
"\t\t\t\tChecking operand allowed for port: " << port.
name() <<
" owc: " << operandWriteCycle <<
" ouc: " << operandUseModCycle <<
" po: " << operandUse.
po->
toString() << std::endl;
2248 std::cerr <<
"\t\t\t\t\tInput node using same port: " << mn.
toString() << std::endl;
2250 bool isCurrOp =
false;
2265 if (operandUseModCycle <
2268 operandUseModCycle ||
2278 operandUseModCycle) {
2295 if (trigger == &mn) {
2297 std::cerr <<
"\t\t\tmn is trigger, no need to check overwrite" << std::endl;
2301 if (trigger == NULL || !trigger->
isPlaced()) {
2309 int slack = hwop.
slack(opIndex);
2312 if (cycle != trigger->
cycle() + slack) {
2316 if (cycle > trigger->
cycle() + slack) {
2332 std::cerr <<
"\t\t\t\tTesting if trigger too early for: " << trigger.
toString() <<
" PO: " << po.
toString() << std::endl;
2337 std::cerr <<
"\t\t\t\tTesting operand: " << mn.
toString() << std::endl;
2341 std::cerr <<
"\t\t\t\tCycle: " << mn.
cycle() <<
", ";
2350 <<
")=" << slack <<
", noReg=" << fuPort.
noRegister()
2355 if (cycle != mn.
cycle() - slack) {
2359 if (cycle < mn.
cycle() - slack) {
2374 for (
int i = 1; i <= inputCount; i++) {
2398 __FILE__, __LINE__,
__func__,
"Not a result read move.");
2401 int latestTrigger = INT_MAX;
2419 int latency = hwop.
latency(outputIndex);
2420 latestTrigger = std::min(latestTrigger, resultCycle - latency);
2422 return latestTrigger;
2429 int triggerCycle = -1;
2430 std::set<ProgramOperation*, ProgramOperation::Comparator> poSet;
2435 triggerCycle = std::max(triggerCycle, trigger->
cycle());
2440 for (
int i = cycle; i <= triggerCycle; i++) {
2448 auto oupIter = opUse->second.find(modCycle);
2449 if (oupIter == opUse->second.end())
2452 auto& oup = oupIter->second;
2454 if (oup.first.po == NULL)
2461 if (oup.second.po == NULL) {
2489 const MoveNode& mn,
int cycle)
const {
2502 if (trigger ==
nullptr || trigger->
isScheduled()) {
2509 int latency = hwop.
latency(outputIndex);
2510 int latestTriggerCycle = cycle - latency;
2512 std::map<const TTAMachine::Port*, const MoveNode*> usedOperandPorts;
2519 auto& rv = rvi->second;
2521 int smallestCycle = (*rv.begin()).first;
2522 int earliestAllowedResReady = -1;
2524 for (
int c = cycle-1;c >= smallestCycle;c--) {
2526 auto ri = rv.find(mc);
2527 if (ri == rv.end()) {
2530 auto res = ri->second;
2534 if (rh1.
po !=
nullptr && rh1.
po != &po) {
2537 earliestAllowedResReady = rc +1;
2542 if (rh2.
po !=
nullptr && rh2.
po != &po) {
2545 earliestAllowedResReady = rc +1;
2551 if (earliestAllowedResReady == -1) {
2555 int earliestTriggerCycle = earliestAllowedResReady - latency;
2558 if (earliestTriggerCycle > latestTriggerCycle &&
2564 std::cerr <<
"\t\t\t\tEarliest allowed res ready: "
2565 << earliestAllowedResReady << std::endl;
2566 std::cerr <<
"\t\t\t\tEarliestTrigger cycle: "
2567 << earliestTriggerCycle << std::endl;
2568 std::cerr <<
"\t\t\t\tLatestTrigger cycle: "
2569 << latestTriggerCycle << std::endl;
2573 for (
int c = latestTriggerCycle; c >= earliestTriggerCycle && !ok ; c--) {
2581 const int inputIndex =
2585 auto inPort = hwop.
port(inputIndex);
2586 if (!inPort->isTriggering()) {
2590 std::cerr <<
"\t\t\t\t\tOperand not allowed at cycle: " << c << std::endl;
2612 std::map<const TTAMachine::FUPort*, std::set<int> > myActualResultCycles;
2615 std::map<const TTAMachine::FUPort*, std::pair<int, int> > myResultCycles;
2619 int lastTriggerCycle = -1;
2621 const MoveNode* prevOutmove =
nullptr;
2622 int prevLatency = 0;
2627 if (trigger !=
nullptr && trigger->
isScheduled()) {
2629 if (trigger->
cycle() > lastTriggerCycle) {
2630 lastTriggerCycle = trigger->
cycle();
2631 prevOutmove =
nullptr;
2645 int latency = hwop.
latency(outputIndex);
2646 auto outPort = hwop.
port(outputIndex);
2647 auto outPortIter = myResultCycles.find(outPort);
2649 if (outPortIter == myResultCycles.end()) {
2651 myResultCycles[outPort] = std::make_pair(INT_MAX, -1);
2659 myResultCycles[outPort].second = std::max(
2660 myResultCycles[outPort].second, outMove.
cycle());
2662 myResultCycles[outPort].first = std::min(
2663 myResultCycles[outPort].first, outMove.
cycle());
2666 myActualResultCycles[outPort].insert(
2669 if (trigger ==
nullptr || !trigger->
isScheduled()) {
2670 int optimalTriggerCycle = outMove.
cycle() - latency;
2671 if (optimalTriggerCycle > lastTriggerCycle) {
2675 if (prevOutmove ==
nullptr) {
2677 prevOutmove = &outMove;
2678 prevLatency = latency;
2684 int prevTriggerCycle =
2685 prevOutmove->
cycle() - prevLatency;
2686 lastTriggerCycle = prevTriggerCycle + 1;
2688 prevOutmove = &outMove;
2689 prevLatency = latency;
2693 int resultReady = trigger->
cycle() + latency;
2694 for (
int i = outMove.
cycle(); i >= resultReady; i--) {
2695 myActualResultCycles[outPort].insert(
2701 if (trigger !=
nullptr && trigger->
isScheduled()) {
2702 myActualResultCycles[outPort].insert(
2705 myResultCycles[outPort].second = std::max(
2706 myResultCycles[outPort].second,
2707 trigger->
cycle() + latency);
2709 myResultCycles[outPort].first = std::min(
2710 myResultCycles[outPort].first,
2711 trigger->
cycle() + latency);
2719 for (
auto p : myResultCycles) {
2721 auto& myActualResCycles = myActualResultCycles[p.first];
2725 int myFirstResultCycle = p.second.first;
2726 int myLastResultCycle = p.second.second;
2736 auto& resVec = rri->second;
2738 for (
auto& res : resVec) {
2739 int anotherResCycle = res.first;
2741 assert(anotherResCycle == anotherResModCycle);
2744 if (myActualResCycles.find(anotherResModCycle)
2745 == myActualResCycles.end()) {
2747 if (myLastModResult < myFirstModResult) {
2749 if (anotherResModCycle < myFirstModResult &&
2750 anotherResModCycle > myLastModResult)
2754 if (anotherResModCycle < myFirstModResult ||
2755 anotherResModCycle > myLastModResult)
2759 auto& foo = res.second;
2762 if (rh1.
po !=
nullptr) {
2769 int outIndex = hwop.
io(*p.first);
2770 int latency = hwop.
latency(outIndex);
2771 bool foundWorkingCycle =
false;
2775 myActualResCycles.end(); i--) {
2776 int otherTriggerCycle = i - latency;
2778 &mn, trigger, cycle, cycle, lastTriggerCycle,
2779 otherTriggerCycle)) {
2780 foundWorkingCycle =
true;
2784 if (!foundWorkingCycle) {
2790 if (rh2.
po !=
nullptr) {
2797 int outIndex = hwop.
io(*p.first);
2798 int latency = hwop.
latency(outIndex);
2799 bool foundWorkingCycle =
false;
2802 myActualResCycles.find(i) == myActualResCycles.end();
2804 assert (i > myFirstResultCycle);
2805 int otherTriggerCycle = i - latency;
2807 &mn, trigger, cycle, cycle, lastTriggerCycle,
2808 otherTriggerCycle)) {
2809 foundWorkingCycle =
true;
2813 if (!foundWorkingCycle) {
2824 int rangeFirst,
int rangeLast,
int targetCycle)
const {
2830 if (rangeFirstMod <= rangeLastMod) {
2831 return targetCycleMod >= rangeFirstMod &&
2832 targetCycleMod <= rangeLastMod;
2834 return targetCycleMod >= rangeFirstMod ||
2835 targetCycleMod <= rangeLastMod;
2845 int rangeFirst,
int rangeLast,
int targetCycle)
const {
2891 if (fu !=
nullptr) {
2895 auto p = hwop->
port(i);