OpenASIP  2.0
BFOptimization.cc
Go to the documentation of this file.
1 /*
2  Copyright (c) 2002-2014 Tampere University.
3 
4  This file is part of TTA-Based Codesign Environment (TCE).
5 
6  Permission is hereby granted, free of charge, to any person obtaining a
7  copy of this software and associated documentation files (the "Software"),
8  to deal in the Software without restriction, including without limitation
9  the rights to use, copy, modify, merge, publish, distribute, sublicense,
10  and/or sell copies of the Software, and to permit persons to whom the
11  Software is furnished to do so, subject to the following conditions:
12 
13  The above copyright notice and this permission notice shall be included in
14  all copies or substantial portions of the Software.
15 
16  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21  FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  DEALINGS IN THE SOFTWARE.
23  */
24 
25 /**
26  * @file BFOptimization.cc
27  *
28  * Definition of BFOptimization class.
29  *
30  * Base class for all optimizations and scheudling operations the
31  * BF2 instruction scheduler can perform. Contains an undo-mechanism
32  * To undo everything, and contains handling for scheudling mirror move
33  * to prolog/epilog in case of loop scheduling.
34  *
35  * @author Heikki Kultala 2014-2020(heikki.kultala-no.spam-tuni.fi)
36  * @note rating: red
37  */
38 
39 #include "BFOptimization.hh"
40 #include "BF2Scheduler.hh"
41 #include "SimpleResourceManager.hh"
42 #include "Move.hh"
43 #include "MoveGuard.hh"
44 #include "CodeGenerator.hh"
45 #include "Guard.hh"
46 #include "RegisterFile.hh"
47 #include "MoveNodeDuplicator.hh"
48 #include "Terminal.hh"
49 #include "BasicBlockScheduler.hh"
50 #include "Operation.hh"
51 #include "UniversalMachine.hh"
52 #include "ControlUnit.hh"
53 #include "Instruction.hh"
54 #include "Bus.hh"
55 #include "BF2ScheduleFront.hh"
57 #include "HWOperation.hh"
58 #include "FUPort.hh"
59 #include "TerminalImmediate.hh"
60 
61 //#define DEBUG_BUBBLEFISH_SCHEDULER
62 //#define DEBUG_LOOP_SCHEDULER
63 //#define CHECK_PROLOG_DDG
64 
65 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
66 #include "POMDisassembler.hh"
67 #define DEBUG_LOOP_SCHEDULER
68 #endif
69 
72  return static_cast<DataDependenceGraph*>(ddg().rootGraph());
73 }
74 const DataDependenceGraph& BFOptimization::ddg() const { return sched_.ddg();}
78  return sched_.prologRM();
79 }
82  return sched_.targetMachine();
83 }
84 
85 unsigned int BFOptimization::ii() const { return 0; }
86 
88  return sched_.duplicator();
89 }
90 
92  if (prologRM() == NULL) {
93  return false;
94  }
95  // TODO: better way to no prolog move for lbufc op
96  if (mn.move().isControlFlowMove() &&
97  !mn.move().isJump()) {
98  return false;
99  }
100  return true;
101 }
102 
103 bool BFOptimization::assign(int cycle, MoveNode& mn,
104  const TTAMachine::Bus* bus,
105  const TTAMachine::FunctionUnit* srcFU,
106  const TTAMachine::FunctionUnit* dstFU,
107  const TTAMachine::Bus* prologBus,
108  int immWriteCycle,
109  int prologImmWriteCycle,
110  const TTAMachine::ImmediateUnit* immu,
111  int immRegIndex,
112  bool ignoreGWC) {
113 
114  bool createdPrologCopy = false;
115 #ifdef DEBUG_LOOP_SCHEDULER
116  if (ii() != 0) {
117  std::cerr << "\t\t\t\tAssigning in loop sched: " << mn.toString()
118  << " to cycle: " << cycle << " imm write cycle: "
119  << immWriteCycle << std::endl;
120  }
121 #else
122 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
123  std::cerr << "\t\t\t\t\tAssigning mn: " << mn.toString()
124  << " imm write cycle: " << immWriteCycle << std::endl;
125 #endif
126 #endif
127  bool usePrologMN = usePrologMove(mn);
128  MoveNode* prologEpilogMN = NULL;
129  // TODO: why trying to assign all to prolog fails???
130  if (usePrologMN) {
131  auto a = createCopyForPrologEpilog(mn);
132  prologEpilogMN = a.first;
133  createdPrologCopy = a.second;
134  }
135 
136  // TODO: assert if too early due the integrated epilog and guard.
137  if (!(addJumpGuardIfNeeded(mn, cycle, ignoreGWC))) {
138  std::cerr << "Adding jump guard failed for node: "
139  << mn.toString() << std::endl;
140  ddg().writeToDotFile("adding_jump_guard_fail.dot");
141  assert(false);
142  }
143 
144 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
145  if (!rm().canAssign(
146  cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex)) {
147  std::cerr << "cannot assign move in assign: " << mn.toString()
148  << " cycle: " << cycle << std::endl;
149  TTAProgram::Move& m = mn.move();
150  std::cerr << "set bus: " << m.bus().name() << std::endl;
151  if (bus != NULL) {
152  std::cerr << "bus: " << bus->name() << std::endl;
153  }
154  if (srcFU != NULL) {
155  std::cerr << "src FU: " << srcFU->name() << std::endl;
156  }
157  if (dstFU != NULL) {
158  std::cerr << "dst FU: " << dstFU->name() << std::endl;
159  }
160 
161  std::cerr << "annotations:" << std::endl;
162  for (int i = 0 ; i < m.annotationCount(); i++) {
163  const TTAProgram::ProgramAnnotation& anno = m.annotation(i);
164  std::cerr << "\thas anno, id: " << anno.id()
165  << " data: " << anno.stringValue() << std::endl;
166  }
167  if (mn.isSourceOperation()) {
168  std::cerr << "Source op: " << mn.sourceOperation().toString()
169  << std::endl;
170  }
171  if (mn.isDestinationOperation()) {
172  std::cerr << "Destination op: "
173  << mn.destinationOperation().toString() << std::endl;
174  }
175  ddg().writeToDotFile("cannot_assign_on_assign.dot");
176  assert(false);
177  }
178 #endif
179 
180  rm().assign(
181  cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex);
182 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
183  std::cerr << "\t\t\t\t\tAssigned mn: " << mn.toString() << std::endl;
184 #endif
185  assert(bus == NULL || bus == &mn.move().bus());
186  if (usePrologMN) {
187  assignCopyToPrologEpilog(cycle, *prologEpilogMN, mn, prologBus,
188  prologImmWriteCycle);
189 #ifdef CHECK_PROLOG_DDG
190  checkPrologDDG(*prologEpilogMN);
191 #endif
192  }
193  return createdPrologCopy;
194 }
195 
196 void BFOptimization::unassign(MoveNode& mn, bool disposePrologCopy) {
197 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
198  std::cerr << "\t\t\t\t\tUnassigning mn: " << mn.toString()
199  << "dispose: " << disposePrologCopy << std::endl;
200 #endif
201  int cycle = mn.cycle();
202  rm().unassign(mn);
203  bool usePrologMN = usePrologMove(mn);
204  if (usePrologMN) {
205  unassignCopyFromPrologEpilog(mn, disposePrologCopy);
206  }
207  unsetJumpGuardIfNeeded(mn, cycle);
208 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
209  std::cerr << "\t\t\t\t\tUnassignined mn: " << mn.toString() << std::endl;
210 #endif
211 }
212 
213 int BFOptimization::rmEC(int cycle, MoveNode& mn,
214  const TTAMachine::Bus* bus,
215  const TTAMachine::FunctionUnit* srcFU,
216  const TTAMachine::FunctionUnit* dstFU,
217  const TTAMachine::Bus* prologBus,
218  int immWriteCycle,
219  int prologImmWriteCycle,
220  const TTAMachine::ImmediateUnit* immu,
221  int immRegIndex) {
222 #ifdef DEBUG_LOOP_SCHEDULER
223  if (ii()) {
224  std::cerr << "\t\t\t\t\tbfopt::rmec called, cycle: " << cycle
225  << " mn: " << mn.toString() <<
226  std::endl;
227 
228  }
229 #else
230 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
231  std::cerr << "\t\t\t\t\tCalling rmec for: " << mn.toString()
232  << " cycle: " << cycle << "dispose: "
233  << disposePrologCopy << std::endl;
234 #endif
235 #endif
236  if (!ii()) {
237  return rm().earliestCycle(
238  cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex);
239  }
240  // cannot add guard if already has guard. so limit cycle to 2nd round.
241  if (!mn.move().isUnconditional() && needJumpGuard(mn, cycle)) {
242  cycle = ii();
243  }
244 
245  MoveNode* prologMN = nullptr;
246  bool createdCopy = false;
247  bool usePrologMN = usePrologMove(mn);
248  if (usePrologMN) {
249  auto a = duplicator().duplicateMoveNode(mn, false, false);
250  prologMN = a.first;
251  createdCopy = a.second;
252  }
253 
254  bool setGuard = false;
255  int ec = rm().earliestCycle(
256  cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex);
257  if (ec == INT_MAX || ec == -1) {
258 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
259  std::cerr << "\t\t\t\t\trmec over with -1" << std::endl;
260 #endif
261  if (createdCopy) {
262  duplicator().disposeMoveNode(prologMN);
263  }
264  return ec;
265  }
266 
267  while (ec < (signed)(2*ii())) {
268  if (needJumpGuard(mn, ec)) {
269  if (ec < jumpGuardAvailableCycle(mn)) {
270  ec++;
271  continue;
272  }
273  if (!setGuard) {
274  assert(mn.move().isUnconditional());
275  setJumpGuard(mn);
276  setGuard = true;
277  continue;
278  }
279  } else { // no longer need jump guard.
280  if (setGuard) {
281  assert(!mn.move().isUnconditional());
282  unsetJumpGuard(mn);
283  setGuard = false;
284  continue;
285  }
286  }
287 
288  if (!setGuard) {
289  ec = rm().earliestCycle(
290  ec, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex);
291  if (ec == -1) {
292  break;
293  }
294  } else {
295  int newEC = rm().earliestCycle(
296  ec, mn, bus, srcFU, dstFU, immWriteCycle);
297  // if set guard, guard may reduce too much..
298  if (newEC > ec) {
299  ec = std::min(newEC, (signed)(ii()));
300  continue;
301  }
302  if (newEC == -1) {
303  ec = -1;
304  break;
305  }
306  }
307  if (ec == INT_MAX) {
308  break;
309  }
310 
311 
312  if (usePrologMN) {
313  bool assignedMN = false;
314  auto mySrcFU = srcFU;
315  auto myDstFU = dstFU;
316  auto myImmu = immu;
317  auto myImmReg = immRegIndex;
318  if (hasAmbiguousResources(mn)) {
319  rm().assign(ec, mn, bus, srcFU, dstFU, immWriteCycle, immu,
320  immRegIndex);
321  mySrcFU = sourceFU(mn);
322  myDstFU = destinationFU(mn);
323  if (mn.isSourceImmediateRegister()) {
324  myImmReg = mn.move().source().index();
325  myImmu = &mn.move().source().immediateUnit();
326  }
327  assignedMN = true;
328  }
329  bool ok = prologRM()->canAssign(
330  ec + BF2Scheduler::PROLOG_CYCLE_BIAS, *prologMN, prologBus,
331  mySrcFU, myDstFU, prologImmWriteCycle, myImmu, myImmReg);
332  if (assignedMN) {
333  rm().unassign(mn);
334  }
335  if (!ok) {
336  ec++;
337  continue;
338  } else {
339  break;
340  }
341  } else { // no prolog
342  if (createdCopy) {
343  duplicator().disposeMoveNode(prologMN);
344  }
345  if (setGuard) {
346  unsetJumpGuard(mn);
347  }
348  return ec;
349  }
350  }
351  if (createdCopy) {
352  duplicator().disposeMoveNode(prologMN);
353  }
354  if (setGuard) {
355  unsetJumpGuard(mn);
356  }
357 #ifdef DEBUG_LOOP_SCHEDULER
358  std::cerr << "\t\t\t\t\trmec over" << std::endl;
359 #endif
360  return ec;
361 }
362 
363 int BFOptimization::rmLC(int cycle, MoveNode& mn,
364  const TTAMachine::Bus* bus,
365  const TTAMachine::FunctionUnit* srcFU,
366  const TTAMachine::FunctionUnit* dstFU,
367  const TTAMachine::Bus* prologBus,
368  int immWriteCycle,
369  int prologImmWriteCycle,
370  const TTAMachine::ImmediateUnit* immu,
371  int immRegIndex) {
372 #ifdef DEBUG_LOOP_SCHEDULER
373  if (ii()) {
374  std::cerr << "\t\t\t\t\tbfopt::rmlc called, cycle: " << cycle
375  << " mn: " << mn.toString() << std::endl;
376  }
377 #else
378 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
379  std::cerr << "\t\t\t\t\tbfopt::rmlc called, cycle: " << cycle
380  << " mn: " << mn.toString() << std::endl;
381 #endif
382 #endif
383  int lc = cycle;
384  bool setGuard = false;
385  MoveNode* prologMN = NULL;
386  bool createdCopy = false;
387  bool usePrologMN = usePrologMove(mn);
388  if (usePrologMN) {
389  auto a = duplicator().duplicateMoveNode(mn, false, false);
390  prologMN = a.first;
391  createdCopy = a.second;
392  }
393 
394  while (lc >= 0) {
395  lc = rm().latestCycle(lc,mn, bus, srcFU, dstFU, immWriteCycle);
396 #ifdef DEBUG_LOOP_SCHEDULER
397  if (ii()) {
398  std::cerr << "\t\t\t\t\tgot lc from rm: " << lc << std::endl;
399  }
400 #else
401 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
402  std::cerr << "\t\t\t\t\tgot lc from rm: " << lc << std::endl;
403 #endif
404 #endif
405  if (lc == -1) {
406  break;
407  }
408  if (needJumpGuard(mn, lc)) {
409 #ifdef DEBUG_LOOP_SCHEDULER
410  std::cerr << "\t\t\t\t\tNeed jump guard for mn: "
411  << mn.toString() << " cycle: " << lc << std::endl;
412 #endif
413  if (lc < jumpGuardAvailableCycle(mn)) {
414 #ifdef DEBUG_LOOP_SCHEDULER
415  std::cerr << "\t\t\t\t\tjump guard not yet available so "
416  << "cannot schedule this ever" << std::endl;
417 #endif
418  if (createdCopy) {
419  duplicator().disposeMoveNode(prologMN);
420  }
421  if (setGuard) {
422  unsetJumpGuard(mn);
423  }
424  return -1;
425  }
426  if (!setGuard) {
427  // cannot add guard if already has guard.
428  if (!mn.move().isUnconditional()) {
429  if (createdCopy) {
430  duplicator().disposeMoveNode(prologMN);
431  }
432  return -1;
433  }
434  setJumpGuard(mn);
435  setGuard = true;
436  continue;
437  }
438  }
439  if (usePrologMN) {
440  // then check that this can be assigned to prolog/epilog
441  // need to use the correct FU - only way to get it is to
442  // assign loop move first
443  bool assignedMN = false;
444  auto mySrcFU = srcFU;
445  auto myDstFU = dstFU;
446  auto myImmu = immu;
447  auto myImmReg = immRegIndex;
448 
449  if (hasAmbiguousResources(mn)) {
450  rm().assign(lc, mn, bus, srcFU, dstFU, immWriteCycle);
451  mySrcFU = sourceFU(mn);
452  myDstFU = destinationFU(mn);
453  if (mn.isSourceImmediateRegister()) {
454  myImmReg = mn.move().source().index();
455  myImmu = &mn.move().source().immediateUnit();
456  }
457  assignedMN = true;
458  }
459  bool ok = prologRM()->canAssign(
460  lc + BF2Scheduler::PROLOG_CYCLE_BIAS, *prologMN, prologBus,
461  mySrcFU, myDstFU, prologImmWriteCycle, myImmu, myImmReg);
462  if (assignedMN) {
463  rm().unassign(mn);
464  }
465  if (!ok) {
466 #ifdef DEBUG_LOOP_SCHEDULER
467  std::cerr << "prolog RM cannot assign to cycle: "
468  << lc << std::endl;
469  std::cerr << "instr in prolog rm: " <<
471  *prologRM()->instruction(
473 #endif
474  lc--;
475  continue;
476  } else {
477  break;
478  }
479  } else { // not in a prolog.
480  if (createdCopy) {
481  duplicator().disposeMoveNode(prologMN);
482  }
483  return lc;
484  }
485  }
486  if (createdCopy) {
487  duplicator().disposeMoveNode(prologMN);
488  }
489  if (setGuard) {
490  unsetJumpGuard(mn);
491  }
492  return lc;
493 }
494 
496  const TTAMachine::Bus* bus,
497  const TTAMachine::FunctionUnit* srcFU,
498  const TTAMachine::FunctionUnit* dstFU,
499  const TTAMachine::Bus* prologBus,
500  int immWriteCycle,
501  int prologImmWriteCycle,
502  const TTAMachine::ImmediateUnit* immu,
503  int immRegIndex,
504  bool ignoreGuardWriteNode) {
505 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
506  if (ii()) {
507  std::cerr << "\t\t\t\t\tCalling BFOpt::canassign for: "
508  << mn.toString() << " cycle: " << cycle << std::endl;
509  } else {
510  std::cerr << "\t\t\t\t\tCalling BFOpt::canassign for: "
511  << mn.toString() << " cycle: " << cycle << std::endl;
512  }
513  if (bus) {
514  std::cerr << "\t\t\t\t\t\tBus: " << bus->name() << std::endl;
515  }
516  if (prologBus) {
517  std::cerr << "\t\t\t\t\t\tProlog bus: " << prologBus->name()
518  << std::endl;
519  }
520  if (srcFU) {
521  std::cerr << "\t\t\t\t\t\tSrc FU: " << srcFU->name() << std::endl;
522  }
523  if (dstFU) {
524  std::cerr << "\t\t\t\t\t\tDst FU: " << dstFU->name() << std::endl;
525  }
526  if (mn.isDestinationOperation()) {
527  std::cerr << "\t\t\t\t\t\tDst po: "
528  << mn.destinationOperation().toString() << std::endl;
529  }
530 #endif
531  bool addGuard = needJumpGuard(mn, cycle);
532  if (addGuard) {
533 #ifdef DEBUG_LOOP_SCHEDULER
534  std::cerr << "\t\t\t\t\t\tNeed jump guard, cycle: " << cycle
535  << "ii: " << ii() << std::endl;
536 #endif
537  // cannot add guard if already has guard.
538  if (!mn.move().isUnconditional()) {
539 #ifdef DEBUG_LOOP_SCHEDULER
540  std::cerr << "\t\t\t\t\tcanassin over with uncond" << std::endl;
541 #endif
542  return false;
543  }
544  if (cycle < jumpGuardAvailableCycle(mn) && !ignoreGuardWriteNode) {
545 #ifdef DEBUG_LOOP_SCHEDULER
546  std::cerr << "\t\t\t\t\tjump guard not yet available so"
547  << " cannot scheudle this." << std::endl;
548  std::cerr << "\t\t\t\t\t\tAvailable on cycle: "
549  << jumpGuardAvailableCycle(mn) << std::endl;
550 #endif
551  return false;
552  }
553  setJumpGuard(mn);
554  }
555  bool ok = rm().canAssign(
556  cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu, immRegIndex);
557 #ifdef DEBUG_LOOP_SCHEDULER
558  if (ii()) {
559  std::cerr << "\t\t\t\t\t for this: " << ok << " , what about prolog?"
560  << std::endl;
561  }
562 #endif
563 
564  // then test assigning to prolog
565  bool usePrologMN = usePrologMove(mn);
566  if (ok && usePrologMN) {
567  // may not have the added jump guard when duplicating.
568  if (addGuard) unsetJumpGuard(mn);
569  auto a = duplicator().duplicateMoveNode(mn, false, false);
570  if (addGuard) setJumpGuard(mn);
571  MoveNode* prologMN = a.first;
572 #ifdef DEBUG_LOOP_SCHEDULER
573  std::cerr << "\t\t\t\t\t\tProlog mn: " << prologMN->toString()
574  << std::endl;
575 #endif
576  bool assignedMN = false;
577  if (hasAmbiguousResources(mn)) {
578  rm().assign(cycle, mn, bus, srcFU, dstFU, immWriteCycle, immu,
579  immRegIndex);
580  srcFU = sourceFU(mn);
581  dstFU = destinationFU(mn);
582  if (mn.isSourceImmediateRegister()) {
583  immRegIndex = mn.move().source().index();
584  immu = &mn.move().source().immediateUnit();
585  }
586  assignedMN = true;
587  }
588  ok &= prologRM()->canAssign(
589  BF2Scheduler::PROLOG_CYCLE_BIAS + cycle, *prologMN, prologBus,
590  srcFU, dstFU, prologImmWriteCycle, immu, immRegIndex);
591  if (assignedMN) {
592  rm().unassign(mn);
593  }
594  if (a.second) { //disposePrologCopy) {
595  duplicator().disposeMoveNode(prologMN);
596  }
597  }
598  unsetJumpGuardIfNeeded(mn, cycle);
599 
600 #ifdef DEBUG_LOOP_SCHEDULER
601  if (ii()) {
602  std::cerr << "\t\t\t\t\tcanassin over:" << ok << std::endl;
603  }
604 #else
605 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
606  std::cerr << "\t\t\t\t\tcanassin over:" << ok << std::endl;
607 #endif
608 #endif
609  return ok;
610 }
611 
613 #ifdef DEBUG_LOOP_SCHEDULER
614  std::cerr << "\t\t\t\t\tsetting jump guard to: " << mn.toString()
615  << std::endl;
616 #endif
617 
618  if (!mn.move().isUnconditional()) {
619  std::cerr << "Cannot set jump guard because already conditional: "
620  << mn.toString() << std::endl;
621  }
622  assert(mn.move().isUnconditional());
623 
624  assert(!dynamic_cast<const TTAMachine::PortGuard*>(
625  &sched_.jumpGuard()->guard()));
626 
627  TTAProgram::MoveGuard* newGuard = sched_.jumpGuard()->copy();
628 // TTAProgram::CodeGenerator::createInverseGuard(*sched_.jumpGuard());
629 
630  mn.move().setGuard(newGuard);
631 
632 /*
633  TTAMachine::Guard& g = newGuard->guard();
634  TTAMachine::RegisterGuard* rg =
635  dynamic_cast<TTAMachine::RegisterGuard*>(&g);
636 
637 
638 
639 
640  TCEString regName;
641  regName << rg->registerFile()->name() << "." <<
642  rg->registerIndex();
643 
644  DataDependenceEdge* e = new DataDependenceEdge(
645  DataDependenceEdge::EDGE_REGISTER,
646  DataDependenceEdge::DEP_RAW,
647  regName,
648  true, // guard
649  false, // true_alias mem dep
650  false, // tail pseudo
651  false, // head pseudo
652  1); // loop depth
653  ddg().connectNodes(*sched_.guardWriteNode(), mn,*e);
654 
655 */
656 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
657  std::cerr << "\t\t\t\t\tset jump guard: " << mn.toString() << std::endl;
658 #endif
659 
660 }
661 
663 #ifdef DEBUG_LOOP_SCHEDULER
664  std::cerr << "\t\t\t\t\tunsetting jump guard from: "
665  << mn.toString() << std::endl;
666 #endif
668  mn.move().setGuard(NULL);
669 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
670  std::cerr << "\t\t\t\t\tunset jump guard: " << mn.toString() << std::endl;
671 #endif
672 }
673 
675  MoveNode& mn) {
676  auto a = duplicator().duplicateMoveNode(mn, true, true);
677  prologMoves_[&mn] = a.first;
678  return a; //prologMN;
679 }
680 
682  TTAProgram::Move& m = prologMN.move();
683 
684  if (loopMN.isSourceOperation()) {
687  TTAProgram::Terminal& source = loopMN.move().source();
688  assert(source.isFUPort());
689  std::string fuName = source.functionUnit().name();
690 #ifdef DEBUG_LOOP_SCHEDULER
691  std::cerr << "\t\tSetting src Fu anno, loop MN: "
692  << loopMN.toString() << " prolog MN: "
693  << prologMN.toString() << std::endl;
694 #endif
695  //TODO: which is the correct annotation here?
698  fuName);
699  m.setAnnotation(srcUnit);
700  }
701 }
702 
704  TTAProgram::Move& m = prologMN.move();
705 
706  if (loopMN.isDestinationOperation()) {
709  TTAProgram::Terminal& dest = loopMN.move().destination();
710  assert(dest.isFUPort());
711  std::string fuName = dest.functionUnit().name();
712 #ifdef DEBUG_LOOP_SCHEDULER
713  std::cerr << "\t\tSetting dst Fu anno, loop MN: "
714  << loopMN.toString() << " prolog MN: "
715  << prologMN.toString() << std::endl;
716 #endif
717  //TODO: which is the correct annotation here?
720  fuName);
721  m.setAnnotation(dstUnit);
722  }
723 }
724 
727  return fuOfTerminal(mn.move().source());
728 }
729 
732  return fuOfTerminal(mn.move().destination());
733 }
734 
737  if (!t.isFUPort())
738  return NULL;
739  return &t.functionUnit();
740 }
741 
743  setPrologSrcFUAnno(prologMN, loopMN);
744  setPrologDstFUAnno(prologMN, loopMN);
745 }
746 
748  int cycle, MoveNode& prologMN, MoveNode& oldMN,
749  const TTAMachine::Bus* prologBus,
750  int prologImmWriteCycle) {
751 
752  const TTAMachine::ImmediateUnit* immu = nullptr;
753  int immRegIndex = -1;
754  if (oldMN.isSourceImmediateRegister()) {
755  immRegIndex = oldMN.move().source().index();
756  immu = &oldMN.move().source().immediateUnit();
757  }
758 
759 #ifdef DEBUG_LOOP_SCHEDULER
760  std::cerr << "\t\t\t\t\tAssigning copy to prolog: " << cycle
761  << " " << prologMN.toString() <<
762  " prolog cycle: " << cycle + BF2Scheduler::PROLOG_CYCLE_BIAS
763  << std::endl;
764 
765  if (!prologRM()->canAssign(
766  BF2Scheduler::PROLOG_CYCLE_BIAS + cycle, prologMN, prologBus,
767  sourceFU(oldMN), destinationFU(oldMN), prologImmWriteCycle,
768  immu, immRegIndex)) {
769  TTAProgram::Move& m = prologMN.move();
770 
771  std::cerr << std::endl << "Cannot assign move to prolog! "
772  << prologMN.toString() << std::endl << std::endl;
773  std::cerr << "Preassigned bus: " << m.bus().name() << std::endl;
774  if (prologBus != nullptr) {
775  std::cerr << "prolog bus: " << prologBus->name() << std::endl;
776  }
777  std::cerr << "Cycle: " << cycle << " prolog cycle: "
778  << cycle + BF2Scheduler::PROLOG_CYCLE_BIAS << std::endl;
779 
780  if (prologMN.isDestinationOperation()) {
781  std::cerr << "destpo: "
782  << prologMN.destinationOperation().toString()
783  << std::endl;
784  }
785 
786  ddg().writeToDotFile("cannot_assign_prolog.dot");
787  prologDDG()->writeToDotFile("prologddg.dot");
788  int sc = prologRM()->smallestCycle();
789  int lc = prologRM()->largestCycle();
790  for (int i = sc; i <= lc; i++) {
791  std::cerr << "\t" << i << "\t"
792  << prologRM()->instruction(i)->toString() << std::endl;
793  }
794 
795  assert(false && "Cannot asign copy to prolog");
796  }
797 #endif
798 
799  prologRM()->assign(
800  BF2Scheduler::PROLOG_CYCLE_BIAS + cycle, prologMN, prologBus,
801  sourceFU(oldMN), destinationFU(oldMN), prologImmWriteCycle,
802  immu, immRegIndex);
803 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
804  std::cerr << "\t\tAassigned copy to prolog, original mn: "
805  << oldMN.toString()
806  << " copy: " << prologMN.toString() << std::endl;
807 #endif
808 }
809 
811  MoveNode& mn, bool disposePrologCopy) {
812 #ifdef DEBUG_LOOP_SCHEDULER
813  std::cerr << "\t\tUnassigning copy from prolog, original mn: "
814  << mn.toString() << "dispose: "
815  << disposePrologCopy << std::endl;
816 #endif
817  MoveNode* copy = prologMoves_[&mn];
818  if (copy != NULL) {
819  prologRM()->unassign(*copy);
820  prologMoves_.erase(&mn);
821 #ifdef DEBUG_LOOP_SCHEDULER
822  std::cerr << "\t\t\tcopy after unassign: " << copy->toString()
823  << std::endl;
824 #endif
825  if (disposePrologCopy) {
826  duplicator().disposeMoveNode(copy);
827  }
828  // TODO: program ops memory leak now
829 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
830  } else {
831  std::cerr << "\t\t\tCopy not found." << std::endl;
832 #endif
833  }
834 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
835  std::cerr << "\t\tUnassigned copy from prolog, original mn: "
836  << mn.toString() << std::endl;
837 #endif
838  prologMoves_.erase(&mn);
839 }
840 
841 std::map<MoveNode*, MoveNode*, MoveNode::Comparator>
843 
845  prologMoves_.clear();
846 }
847 
849  const MoveNode& mn, const TTAMachine::Machine& mach) {
850  if (!mn.isDestinationOperation()) {
851  return NULL;
852  }
854  return BasicBlockScheduler::findTrigger(po, mach);
855 }
856 
858  return
859  !op.usesMemory() &&
860  !op.hasSideEffects() &&
861  !op.isControlFlowOperation() &&
862  op.affectsCount() == 0;
863 }
864 
866  if (!mn.isDestinationOperation()) {
867  return false;
868  }
869  const MoveNode* trig = getSisterTrigger(mn, targetMachine());
870  // operand writes can be always speculated
871  if (&mn != trig && trig != NULL) {
872  return true;
873  }
874  const Operation& op = mn.destinationOperation().operation();
875  return canBeSpeculated(op);
876 }
877 
878 bool BFOptimization::needJumpGuard(const MoveNode& mn, int cycle){
879  if (cycle >= (int)(ii())) {
880  return false;
881  }
882 
883  return !canBeSpeculated(mn);
884 }
885 
886 /**
887  * Returns false if needs guard but guard not available yet
888  */
890  bool ignoreGuardWriteCycle) {
891  if (needJumpGuard(mn, cycle)) {
892  if (jumpGuardAvailableCycle(mn) > cycle && !ignoreGuardWriteCycle) {
893 #ifdef DEBUG_LOOP_SCHEDULER
894  std::cerr << "jump guard available at "
896  << " , not in cycle: " << cycle << std::endl;
897 #endif
898  return false;
899  }
900  if (!mn.move().isUnconditional()) {
901 #ifdef DEBUG_BUBBLEFISH_SCHEDULER
902  std::cerr << "Cannot add guard to already-conditional move "
903  << std::endl;
904 #endif
905  return false;
906  }
907  setJumpGuard(mn);
908  }
909  return true;
910 }
911 
913  if (needJumpGuard(mn, cycle)) {
914  unsetJumpGuard(mn);
915  }
916 }
917 
919 
921 #ifdef DEBUG_LOOP_SCHEDULER
922  std::cerr << "jump node is null or guard operation!" << std::endl;
923 #endif
924  return INT_MAX;
925  }
926  if (sched_.guardWriteNode() == NULL) {
927 #ifdef DEBUG_LOOP_SCHEDULER
928  std::cerr << "Guard write node not known!" << std::endl;
929 #endif
930  return INT_MAX;
931  }
932  if (&mn == sched_.guardWriteNode()) {
933 #ifdef DEBUG_LOOP_SCHEDULER
934  std::cerr << "I AM guard write node!" << std::endl << std::endl;
935 #endif
936  return 0;
937  }
938  if (!sched_.guardWriteNode()->isScheduled()) {
939 #ifdef DEBUG_LOOP_SCHEDULER
940  std::cerr << "guardwrite node is null or not sched:"
941  << sched_.guardWriteNode()->toString() << std::endl;
942 #endif
943  return INT_MAX;
944  }
945 
946  int glat = sched_.guardWriteNode()->move().destination().registerFile().
947  guardLatency()+
949 
950  return glat+ sched_.guardWriteNode()->cycle() - ii();
951 }
952 
955 }
956 
958  if (mn.isSourceOperation() &&
959  (mn.move().annotationCount(
961  && (mn.move().annotationCount(
963  return true;
964  }
965  if (mn.isDestinationOperation() &&
966  (mn.move().annotationCount(
968  && (mn.move().annotationCount(
970  return true;
971  }
972  // LIMM unit may be ambiguous resource
973  if (mn.isSourceConstant())
974  return true;
975 
976  return false;
977 }
978 
980 
981  auto& move = mn.move();
982  if (!move.source().isImmediate()) {
983  return false;
984  }
985 
986  if (!mn.isDestinationOperation()) {
987  return false;
988  }
989 
992 
994  for (int i = 0; i < po.inputMoveCount(); i++) {
995  MoveNode& input = po.inputMove(i);
996  auto& inputMove = input.move();
997  if (input.move().destination().isFUPort() && input.isScheduled()) {
998  auto& fu = inputMove.destination().functionUnit();
999  auto hwop = fu.operation(po.operation().name());
1000  auto port = hwop->port(move.destination().operationIndex());
1001  if (!port->noRegister()) {
1002  return false;
1003  }
1004  if (inputMove.source().isImmediate()) {
1005  simmCount--;
1006  }
1007  if (inputMove.source().isImmediateRegister()) {
1008  limmCount--;
1009  }
1010  // all ways to transport immediate used.
1011  if (simmCount + limmCount < 1) {
1012  return true;
1013  }
1014  // needs LIMM but no LIMM available, only too narrow SIMMs available.
1015  if (limmCount < 1 &&
1017  static_cast<TTAProgram::TerminalImmediate&>(
1018  move.source()), *port,
1019  move.isUnconditional()
1020  ? nullptr
1021  : &move.guard().guard())) {
1022  return true;
1023  }
1024  }
1025  }
1026  return false;
1027 }
1028 
1031 
1032  auto& move = mn.move();
1033  if (!move.source().isGPR()) {
1034  return nullptr;
1035  }
1036 
1037  auto& rf = move.source().registerFile();
1038  int freeRFPorts = rf.maxReads();
1039 
1040  if (!move.destination().isFUPort() || !mn.isDestinationOperation()) {
1041  return nullptr;
1042  }
1043 
1045  for (int i = 0; i < po.inputMoveCount(); i++) {
1046  MoveNode& input = po.inputMove(i);
1047  auto& inputMove = input.move();
1048  if (input.move().destination().isFUPort() && input.isScheduled()) {
1049  auto& fu = inputMove.destination().functionUnit();
1050  auto hwop = fu.operation(po.operation().name());
1051  auto port = hwop->port(move.destination().operationIndex());
1052  if (!port->noRegister()) {
1053  return nullptr;
1054  }
1055  if (inputMove.source().isGPR() &&
1056  &inputMove.source().registerFile() == &rf) {
1057  freeRFPorts--;
1058  if (freeRFPorts < 1) {
1059  return &rf;
1060  }
1061  }
1062  }
1063  }
1064  return nullptr;
1065 }
1066 
1069  return false;
1071  return false;
1072  }
1073  if (immCountPreventsScheduling(mn)) {
1074  return false;
1075  }
1076  return true;
1077 }
1078 
1080  auto oEdges = prologDDG()->outEdges(prologEpilogMN);
1081  auto iEdges = prologDDG()->inEdges(prologEpilogMN);
1082 
1083  for (auto e: oEdges) {
1084  if (!e->isRAW())
1085  continue;
1086  MoveNode& head = prologDDG()->headNode(*e);
1087  if (head.isScheduled() && head.cycle() <= prologEpilogMN.cycle()) {
1088  prologDDG()->writeToDotFile("illegal_assign_in_prolog.dot");
1089 
1090  ddg().writeToDotFile("mainddg.dot");
1091 
1092  std::cerr << "Illegal assign of: " << prologEpilogMN.toString()
1093  << std::endl;
1094  assert(false);
1095  }
1096  }
1097 
1098  for (auto e: iEdges) {
1099  if (!e->isRAW())
1100  continue;
1101  MoveNode& tail = prologDDG()->tailNode(*e);
1102  if (tail.isScheduled() && tail.cycle() >= prologEpilogMN.cycle()) {
1103  prologDDG()->writeToDotFile("illegal_assign_in_prolog.dot");
1104 
1105  ddg().writeToDotFile("mainddg.dot");
1106 
1107  std::cerr << "Illegal assign(2) of: " << prologEpilogMN.toString()
1108  << std::endl;
1109  assert(false);
1110  }
1111  }
1112 }
1113 
1114 #ifdef CHECK_DDG_EQUALITY
1115 void BFOptimization::getDDGSnapshot() {
1116  if (id() < CHECK_DDG_EQUALITY) {
1117  return;
1118  }
1119 
1120  ddgECount_ = ddg().edgeCount();
1121  ddgString_ = ddg().dotString();
1122  if (prologDDG() != nullptr) {
1123  prologDDGString_ = prologDDG()->dotString();
1124  prologDDGECount_ = prologDDG()->edgeCount();
1125  prologDDGNCount_ = prologDDG()->nodeCount();
1126  }
1127 }
1128 
1129 /**
1130  * Checks that DDG edge and node counts are same before the optimization
1131  * and after reverting it.
1132  */
1133 void BFOptimization::checkDDGEquality() {
1134 
1135  if (id() < CHECK_DDG_EQUALITY) {
1136  return;
1137  }
1138  int ddgECount = ddg().edgeCount();
1139  auto ddgst = ddg().dotString();
1140  if (ddgECount != ddgECount_ ) { //(ddgst != ddgString_) {
1141  std::cerr << "ddg changed! id:" << id() << std::endl;
1142 
1143  std::ofstream output("before.dot");
1144  output << ddgString_;
1145  output.close();
1146 
1147  ddg().writeToDotFile("after.dot");
1148  assert(false);
1149  }
1150  if (prologDDGString_ != "") {
1151  if (prologDDG()->edgeCount() != prologDDGECount_ ||
1152  prologDDG()->nodeCount() != prologDDGNCount_) {
1153 
1154  std::cerr << "prolog ddg changed! id: " << id() << std::endl;
1155 
1156  std::ofstream output("before.dot");
1157  output << prologDDGString_;
1158  output.close();
1159 
1160  prologDDG()->writeToDotFile("after.dot");
1161  assert(false);
1162  }
1163  }
1164 }
1165 
1166 void BFOptimization::undo() {
1167  Reversible::undo();
1168  checkDDGEquality();
1169 }
1170 #endif
ProgramOperation::operation
const Operation & operation() const
Definition: ProgramOperation.cc:590
TTAProgram::Terminal::isFUPort
virtual bool isFUPort() const
Definition: Terminal.cc:118
BFOptimization::unassign
virtual void unassign(MoveNode &mn, bool disposePrologCopy=true)
Definition: BFOptimization.cc:196
BFOptimization::sourceFU
const TTAMachine::FunctionUnit * sourceFU(const MoveNode &mn)
Definition: BFOptimization.cc:726
DataDependenceGraph::removeIncomingGuardEdges
void removeIncomingGuardEdges(MoveNode &node)
Definition: DataDependenceGraph.cc:5466
SimpleResourceManager::canAssign
virtual bool canAssign(int cycle, MoveNode &node, const TTAMachine::Bus *bus=NULL, const TTAMachine::FunctionUnit *srcFU=NULL, const TTAMachine::FunctionUnit *dstFU=NULL, int immWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1) const override
Definition: SimpleResourceManager.cc:186
BFOptimization::assign
virtual bool assign(int cycle, MoveNode &, const TTAMachine::Bus *bus=nullptr, const TTAMachine::FunctionUnit *srcFU_=nullptr, const TTAMachine::FunctionUnit *dstFU=nullptr, const TTAMachine::Bus *prologBus=nullptr, int immWriteCycle=-1, int prologImmWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1, bool ignoreGuardWriteCycle=false)
Definition: BFOptimization.cc:103
BoostGraph::tailNode
virtual Node & tailNode(const Edge &edge) const
TTAMachine::Component::name
virtual TCEString name() const
Definition: MachinePart.cc:125
SimpleResourceManager::largestCycle
virtual int largestCycle() const override
Definition: SimpleResourceManager.cc:463
BFOptimization::duplicator
MoveNodeDuplicator & duplicator() const
Definition: BFOptimization.cc:87
MoveNode::toString
std::string toString() const
Definition: MoveNode.cc:576
MachineConnectivityCheck.hh
Operation::hasSideEffects
virtual bool hasSideEffects() const
Definition: Operation.cc:272
TTAProgram::Terminal::index
virtual int index() const
Definition: Terminal.cc:274
machine
TTAMachine::Machine * machine
the architecture definition of the estimated processor
Definition: EstimatorCmdLineUI.cc:59
BoostGraph::headNode
virtual Node & headNode(const Edge &edge) const
MoveNodeDuplicator
Definition: MoveNodeDuplicator.hh:38
TTAProgram::Terminal::registerFile
virtual const TTAMachine::RegisterFile & registerFile() const
Definition: Terminal.cc:225
BFOptimization::RFReadPortCountPreventsScheduling
const TTAMachine::RegisterFile * RFReadPortCountPreventsScheduling(const MoveNode &mn)
Definition: BFOptimization.cc:1030
MoveNode::isDestinationOperation
bool isDestinationOperation() const
BFOptimization::unsetJumpGuardIfNeeded
void unsetJumpGuardIfNeeded(MoveNode &mn, int cycle)
Definition: BFOptimization.cc:912
BFOptimization::ii
unsigned int ii() const
Definition: BFOptimization.cc:85
SimpleResourceManager::smallestCycle
virtual int smallestCycle() const override
Definition: SimpleResourceManager.cc:480
TTAProgram::Move::isUnconditional
bool isUnconditional() const
Definition: Move.cc:154
MachineConnectivityCheck::canTransportImmediate
static bool canTransportImmediate(const TTAProgram::TerminalImmediate &immediate, const TTAMachine::BaseRegisterFile &destRF, const TTAMachine::Guard *guard=NULL)
Definition: MachineConnectivityCheck.cc:181
TTAProgram::ProgramAnnotation::stringValue
std::string stringValue() const
Definition: ProgramAnnotation.cc:90
BFOptimization::needJumpGuard
bool needJumpGuard(const MoveNode &mn, int cycle)
Definition: BFOptimization.cc:878
TTAMachine::Bus
Definition: Bus.hh:53
BFOptimization::setPrologFUAnnos
void setPrologFUAnnos(MoveNode &prologMN, MoveNode &loopMN)
Definition: BFOptimization.cc:742
TTAProgram::AnnotatedInstructionElement::setAnnotation
void setAnnotation(const ProgramAnnotation &annotation)
Definition: AnnotatedInstructionElement.cc:79
BF2Scheduler::targetMachine
const TTAMachine::Machine & targetMachine() const
Definition: BF2Scheduler.hh:127
TTAProgram::Move::destination
Terminal & destination() const
Definition: Move.cc:323
BF2Scheduler::ddg
DataDependenceGraph & ddg()
Definition: BF2Scheduler.hh:100
BF2Scheduler::prologDDG
DataDependenceGraph * prologDDG()
Definition: BF2Scheduler.hh:102
TTAProgram::Instruction::toString
std::string toString() const
Definition: Instruction.cc:576
TTAProgram::Move::bus
const TTAMachine::Bus & bus() const
Definition: Move.cc:373
BFOptimization::getSisterTrigger
static MoveNode * getSisterTrigger(const MoveNode &mn, const TTAMachine::Machine &mach)
Definition: BFOptimization.cc:848
ProgramOperation
Definition: ProgramOperation.hh:70
TTAProgram::Move::setGuard
void setGuard(MoveGuard *guard)
Definition: Move.cc:360
MoveNode
Definition: MoveNode.hh:65
MoveNode::isSourceConstant
bool isSourceConstant() const
Definition: MoveNode.cc:238
BFOptimization::hasAmbiguousResources
bool hasAmbiguousResources(MoveNode &mn) const
Definition: BFOptimization.cc:957
BUMoveNodeSelector
Definition: BUMoveNodeSelector.hh:70
MachineConnectivityCheck::canTransportMove
static bool canTransportMove(const MoveNode &moveNode, const TTAMachine::Machine &machine, bool ignoreGuard=false)
Definition: MachineConnectivityCheck.cc:1843
SimpleResourceManager::assign
virtual void assign(int cycle, MoveNode &node, const TTAMachine::Bus *bus=NULL, const TTAMachine::FunctionUnit *srcFU=NULL, const TTAMachine::FunctionUnit *dstFU=NULL, int immWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1) override
Definition: SimpleResourceManager.cc:221
Terminal.hh
BFOptimization::rmEC
virtual int rmEC(int cycle, MoveNode &mn, const TTAMachine::Bus *bus=nullptr, const TTAMachine::FunctionUnit *srcFU=nullptr, const TTAMachine::FunctionUnit *dstFU=nullptr, const TTAMachine::Bus *prologBus=nullptr, int immWriteCycle=-1, int prologImmWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1)
Definition: BFOptimization.cc:213
BoostGraph::edgeCount
int edgeCount() const
Operation::name
virtual TCEString name() const
Definition: Operation.cc:93
BasicBlockScheduler.hh
SimpleResourceManager::unassign
virtual void unassign(MoveNode &node) override
Definition: SimpleResourceManager.cc:252
BFOptimization::checkPrologDDG
void checkPrologDDG(MoveNode &prologEpilogMN)
Definition: BFOptimization.cc:1079
BFOptimization::fuOfTerminal
const TTAMachine::FunctionUnit * fuOfTerminal(const TTAProgram::Terminal &t)
Definition: BFOptimization.cc:736
BFOptimization::targetMachine
const TTAMachine::Machine & targetMachine() const
Definition: BFOptimization.cc:81
BFOptimization::sched_
BF2Scheduler & sched_
Definition: BFOptimization.hh:103
BF2Scheduler::duplicator
MoveNodeDuplicator & duplicator()
Definition: BF2Scheduler.hh:106
BFOptimization::canBeSpeculated
bool canBeSpeculated(const Operation &op)
Definition: BFOptimization.cc:857
MoveNode::isSourceImmediateRegister
bool isSourceImmediateRegister() const
Definition: MoveNode.cc:223
MoveNodeDuplicator::duplicateMoveNode
std::pair< MoveNode *, bool > duplicateMoveNode(MoveNode &mn, bool addToDDG, bool ignoreSameBBBackEdges)
Definition: MoveNodeDuplicator.cc:106
POMDisassembler.hh
BasicBlockScheduler::findTrigger
static MoveNode * findTrigger(const ProgramOperation &po, const TTAMachine::Machine &mach)
Definition: BasicBlockScheduler.cc:2094
MoveNode::sourceOperation
ProgramOperation & sourceOperation() const
Definition: MoveNode.cc:453
assert
#define assert(condition)
Definition: Application.hh:86
TTAMachine::FunctionUnit
Definition: FunctionUnit.hh:55
TTAMachine::HWOperation::port
virtual FUPort * port(int operand) const
Definition: HWOperation.cc:320
UniversalMachine.hh
TTAProgram::ProgramAnnotation::ANN_ALLOWED_UNIT_SRC
@ ANN_ALLOWED_UNIT_SRC
Candidate units can be passed for resource manager for choosing the source/destination unit of the mo...
Definition: ProgramAnnotation.hh:112
BFOptimization::usePrologMove
bool usePrologMove(const MoveNode &mn)
Definition: BFOptimization.cc:91
TTAProgram::ProgramAnnotation::id
ProgramAnnotation::Id id() const
Definition: ProgramAnnotation.cc:111
MoveNode::isGuardOperation
bool isGuardOperation() const
Definition: MoveNode.cc:181
TTAProgram::ProgramAnnotation::ANN_CONN_CANDIDATE_UNIT_SRC
@ ANN_CONN_CANDIDATE_UNIT_SRC
Src. unit candidate.
Definition: ProgramAnnotation.hh:115
DataDependenceGraph::dotString
virtual TCEString dotString() const
Dot printing related methods.
Definition: DataDependenceGraph.cc:1562
TTAMachine::Machine::controlUnit
virtual ControlUnit * controlUnit() const
Definition: Machine.cc:345
TTAMachine::RegisterFile::maxReads
virtual int maxReads() const
Definition: RegisterFile.cc:123
MoveNode::cycle
int cycle() const
Definition: MoveNode.cc:421
BFOptimization::prologRM
SimpleResourceManager * prologRM() const
Definition: BFOptimization.cc:77
HWOperation.hh
BF2Scheduler.hh
TTAProgram::Move::isControlFlowMove
bool isControlFlowMove() const
Definition: Move.cc:233
BoostGraph::rootGraph
BoostGraph * rootGraph()
BFOptimization::prologDDG
DataDependenceGraph * prologDDG()
Definition: BFOptimization.cc:75
Instruction.hh
MoveNodeDuplicator::disposeMoveNode
void disposeMoveNode(MoveNode *newMN)
Definition: MoveNodeDuplicator.cc:53
BF2ScheduleFront::mightBeReady
void mightBeReady(MoveNode &n) override
Definition: BF2ScheduleFront.cc:701
Reversible::undo
virtual void undo()
Definition: Reversible.cc:69
BF2Scheduler::jumpGuard
TTAProgram::MoveGuard * jumpGuard()
Definition: BF2Scheduler.cc:1087
BFOptimization::assignCopyToPrologEpilog
void assignCopyToPrologEpilog(int cycle, MoveNode &mn, MoveNode &loopMN, const TTAMachine::Bus *prologBus, int prologImmWriteCycle)
Definition: BFOptimization.cc:747
BFOptimization::setPrologSrcFUAnno
void setPrologSrcFUAnno(MoveNode &prologMN, MoveNode &loopMN)
Definition: BFOptimization.cc:681
BFOptimization::rootDDG
DataDependenceGraph * rootDDG()
Definition: BFOptimization.cc:71
BFOptimization::createCopyForPrologEpilog
std::pair< MoveNode *, bool > createCopyForPrologEpilog(MoveNode &mn)
Definition: BFOptimization.cc:674
BF2Scheduler::selector
BUMoveNodeSelector & selector()
Definition: BF2Scheduler.hh:105
MachineConnectivityCheck::maxSIMMCount
static int maxSIMMCount(const TTAMachine::Machine &targetMachine)
Definition: MachineConnectivityCheck.cc:2019
SimpleResourceManager::earliestCycle
virtual int earliestCycle(MoveNode &node, const TTAMachine::Bus *bus=NULL, const TTAMachine::FunctionUnit *srcFU=NULL, const TTAMachine::FunctionUnit *dstFU=NULL, int immWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1) const override
Definition: SimpleResourceManager.cc:278
Guard.hh
BF2ScheduleFront.hh
Operation.hh
MoveNode::isSourceOperation
bool isSourceOperation() const
Definition: MoveNode.cc:168
TTAProgram::Terminal::immediateUnit
virtual const TTAMachine::ImmediateUnit & immediateUnit() const
Definition: Terminal.cc:240
BFOptimization::setPrologDstFUAnno
void setPrologDstFUAnno(MoveNode &prologMN, MoveNode &loopMN)
Definition: BFOptimization.cc:703
BFOptimization::ddg
DataDependenceGraph & ddg()
Definition: BFOptimization.cc:70
BFOptimization::prologMoves_
static std::map< MoveNode *, MoveNode *, MoveNode::Comparator > prologMoves_
Definition: BFOptimization.hh:146
TTAProgram::Move
Definition: Move.hh:55
Bus.hh
BFOptimization::destinationFU
const TTAMachine::FunctionUnit * destinationFU(const MoveNode &mn)
Definition: BFOptimization.cc:731
BFOptimization::jumpGuardAvailableCycle
int jumpGuardAvailableCycle(const MoveNode &mn)
Definition: BFOptimization.cc:918
BFOptimization::canBeScheduled
bool canBeScheduled(const MoveNode &mn)
Definition: BFOptimization.cc:1067
BFOptimization::rm
SimpleResourceManager & rm() const
Definition: BFOptimization.cc:76
ProgramOperation::inputMoveCount
int inputMoveCount() const
Definition: ProgramOperation.cc:600
Operation
Definition: Operation.hh:59
MoveNodeDuplicator.hh
BoostGraph::inEdges
virtual EdgeSet inEdges(const Node &node) const
BFOptimization::setJumpGuard
void setJumpGuard(MoveNode &mn)
Definition: BFOptimization.cc:612
GraphBase::writeToDotFile
virtual void writeToDotFile(const TCEString &fileName) const
BF2Scheduler::prologRM
SimpleResourceManager * prologRM()
Definition: BF2Scheduler.hh:104
BF2Scheduler::PROLOG_CYCLE_BIAS
static const int PROLOG_CYCLE_BIAS
Definition: BF2Scheduler.hh:209
TTAProgram::Terminal::functionUnit
virtual const TTAMachine::FunctionUnit & functionUnit() const
Definition: Terminal.cc:251
Operation::usesMemory
virtual bool usesMemory() const
Definition: Operation.cc:232
TTAProgram::TerminalImmediate
Definition: TerminalImmediate.hh:44
BoostGraph::outEdges
virtual EdgeSet outEdges(const Node &node) const
MoveNode::destinationOperation
ProgramOperation & destinationOperation(unsigned int index=0) const
TTAProgram::AnnotatedInstructionElement::annotation
ProgramAnnotation annotation(int index, ProgramAnnotation::Id id=ProgramAnnotation::ANN_UNDEF_ID) const
Definition: AnnotatedInstructionElement.cc:100
BFOptimization::clearPrologMoves
static void clearPrologMoves()
Definition: BFOptimization.cc:844
MoveNode::move
TTAProgram::Move & move()
ProgramOperation::toString
std::string toString() const
Definition: ProgramOperation.cc:746
POMDisassembler::disassemble
static std::string disassemble(const TTAProgram::Move &move)
Definition: POMDisassembler.cc:629
BFOptimization::addJumpGuardIfNeeded
bool addJumpGuardIfNeeded(MoveNode &mn, int cycle, bool ignoreGuardWriteCycle=false)
Definition: BFOptimization.cc:889
BF2Scheduler::rm
SimpleResourceManager & rm()
Definition: BF2Scheduler.hh:103
CodeGenerator.hh
BF2Scheduler::currentFront
BF2ScheduleFront * currentFront()
Definition: BF2Scheduler.hh:188
TerminalImmediate.hh
BF2Scheduler::jumpNode
MoveNode * jumpNode()
Definition: BF2Scheduler.hh:192
BFOptimization::unassignCopyFromPrologEpilog
void unassignCopyFromPrologEpilog(MoveNode &mh, bool disposePrologCopy=true)
Definition: BFOptimization.cc:810
BFOptimization::rmLC
virtual int rmLC(int cycle, MoveNode &mn, const TTAMachine::Bus *bus=nullptr, const TTAMachine::FunctionUnit *srcFU=nullptr, const TTAMachine::FunctionUnit *dstFU=nullptr, const TTAMachine::Bus *prologBus=nullptr, int immWriteCycle=-1, int prologImmWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1)
Definition: BFOptimization.cc:363
RegisterFile.hh
FUPort.hh
ControlUnit.hh
DataDependenceGraph
Definition: DataDependenceGraph.hh:67
SimpleResourceManager::latestCycle
virtual int latestCycle(MoveNode &node, const TTAMachine::Bus *bus=NULL, const TTAMachine::FunctionUnit *srcFU=NULL, const TTAMachine::FunctionUnit *dstFU=NULL, int immWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1) const override
Definition: SimpleResourceManager.cc:349
BFOptimization::selector
BUMoveNodeSelector & selector()
Definition: BFOptimization.cc:80
BFOptimization::unsetJumpGuard
void unsetJumpGuard(MoveNode &mn)
Definition: BFOptimization.cc:662
TTAProgram::Terminal
Definition: Terminal.hh:60
SimpleResourceManager.hh
MoveNode::isScheduled
bool isScheduled() const
Definition: MoveNode.cc:409
TTAProgram::Move::source
Terminal & source() const
Definition: Move.cc:302
SimpleResourceManager
Definition: SimpleResourceManager.hh:58
TTAProgram::MoveGuard::copy
MoveGuard * copy() const
Definition: MoveGuard.cc:96
BFOptimization::immCountPreventsScheduling
bool immCountPreventsScheduling(const MoveNode &mn)
Definition: BFOptimization.cc:979
TTAMachine::PortGuard
Definition: Guard.hh:99
TTAMachine::FunctionUnit::operation
virtual HWOperation * operation(const std::string &name) const
Definition: FunctionUnit.cc:363
TTAMachine::RegisterFile
Definition: RegisterFile.hh:47
BF2Scheduler::guardWriteNode
MoveNode * guardWriteNode()
Definition: BF2Scheduler.hh:191
TTAProgram::MoveGuard::guard
const TTAMachine::Guard & guard() const
Definition: MoveGuard.cc:86
TTAProgram::ProgramAnnotation
Definition: ProgramAnnotation.hh:49
TTAProgram::Move::isJump
bool isJump() const
Definition: Move.cc:164
TTAProgram::AnnotatedInstructionElement::removeAnnotations
void removeAnnotations(ProgramAnnotation::Id id=ProgramAnnotation::ANN_UNDEF_ID)
Definition: AnnotatedInstructionElement.cc:146
Move.hh
TTAMachine::ControlUnit::globalGuardLatency
int globalGuardLatency() const
TTAProgram::MoveGuard
Definition: MoveGuard.hh:47
BoostGraph::nodeCount
int nodeCount() const
Reversible::id
int id()
Definition: Reversible.hh:43
Operation::affectsCount
virtual int affectsCount() const
Definition: Operation.cc:402
BFOptimization::canAssign
virtual bool canAssign(int cycle, MoveNode &mn, const TTAMachine::Bus *bus=nullptr, const TTAMachine::FunctionUnit *srcFU=nullptr, const TTAMachine::FunctionUnit *dstFU=nullptr, const TTAMachine::Bus *prologBus=nullptr, int immWriteCycle=-1, int prologImmWriteCycle=-1, const TTAMachine::ImmediateUnit *immu=nullptr, int immRegIndex=-1, bool ignoreGWN=false)
Definition: BFOptimization.cc:495
BFOptimization::mightBeReady
virtual void mightBeReady(MoveNode &mn)
Definition: BFOptimization.cc:953
BFOptimization.hh
ProgramOperation::inputMove
MoveNode & inputMove(int index) const
Definition: ProgramOperation.cc:621
TTAMachine::Machine
Definition: Machine.hh:73
Operation::isControlFlowOperation
virtual bool isControlFlowOperation() const
Definition: Operation.cc:294
TTAProgram::AnnotatedInstructionElement::annotationCount
int annotationCount(ProgramAnnotation::Id id=ProgramAnnotation::ANN_UNDEF_ID) const
Definition: AnnotatedInstructionElement.cc:133
SimpleResourceManager::instruction
virtual TTAProgram::Instruction * instruction(int cycle) const override
Definition: SimpleResourceManager.cc:442
TTAProgram::ProgramAnnotation::ANN_CONN_CANDIDATE_UNIT_DST
@ ANN_CONN_CANDIDATE_UNIT_DST
Dst. unit candidate.
Definition: ProgramAnnotation.hh:116
MoveGuard.hh
TTAMachine::ImmediateUnit
Definition: ImmediateUnit.hh:50
MachineConnectivityCheck::maxLIMMCount
static int maxLIMMCount(const TTAMachine::Machine &targetMachine)
Definition: MachineConnectivityCheck.cc:2009