Go to the documentation of this file.
72 #include "tce_config.h"
91 enum class AccessMode : unsigned char { read, write };
92 enum class ExtensionMode : unsigned char { sign, zero };
93 enum class MAUOrder : unsigned char { littleEndian, bigEndian };
95 struct MemoryOperationDescription {
96 AccessMode accessMode;
98 ExtensionMode extensionMode;
108 std::map<TCEString, MemoryOperationDescription, TCEString::ICLess>
111 {AccessMode::read, 1, ExtensionMode::sign, MAUOrder::bigEndian}},
113 {AccessMode::read, 1, ExtensionMode::zero, MAUOrder::bigEndian}},
115 {AccessMode::read, 2, ExtensionMode::sign, MAUOrder::bigEndian}},
117 {AccessMode::read, 2, ExtensionMode::zero, MAUOrder::bigEndian}},
119 {AccessMode::read, 4, ExtensionMode::sign, MAUOrder::bigEndian}},
121 {AccessMode::read, 1, ExtensionMode::sign, MAUOrder::littleEndian}},
123 {AccessMode::read, 1, ExtensionMode::zero, MAUOrder::littleEndian}},
125 {AccessMode::read, 2, ExtensionMode::sign, MAUOrder::littleEndian}},
127 {AccessMode::read, 2, ExtensionMode::zero, MAUOrder::littleEndian}},
129 {AccessMode::read, 4, ExtensionMode::sign, MAUOrder::littleEndian}},
132 {AccessMode::write, 1, ExtensionMode::zero, MAUOrder::littleEndian}},
134 {AccessMode::write, 2, ExtensionMode::zero, MAUOrder::littleEndian}},
136 {AccessMode::write, 4, ExtensionMode::zero, MAUOrder::littleEndian}},
138 {AccessMode::write, 1, ExtensionMode::zero, MAUOrder::bigEndian}},
140 {AccessMode::write, 2, ExtensionMode::zero, MAUOrder::bigEndian}},
142 {AccessMode::write, 4, ExtensionMode::zero, MAUOrder::bigEndian}}
164 bool fuResourceConflictDetection,
166 bool dynamicCompilation,
167 bool basicBlockPerFile,
168 bool functionPerFile,
172 handleCycleEnd_(handleCycleEnd),
173 dynamicCompilation_(dynamicCompilation),
174 basicBlockPerFile_(basicBlockPerFile),
175 functionPerFile_(functionPerFile),
176 instructionNumber_(0), instructionCounter_(0),
178 isProcedureBegin_(true), currentProcedure_(0),
179 lastInstructionOfBB_(0),
180 className_(
TCEString(
"CompiledSimulationEngine_") + globalSymbolSuffix),
181 os_(NULL), symbolGen_(globalSymbolSuffix),
182 conflictDetectionGenerator_(
183 machine_, symbolGen_, fuResourceConflictDetection),
184 needGuardPipeline_(
false), globalSymbolSuffix_(globalSymbolSuffix) {
201 for (
int i = 0; i < busNav.
count(); i++) {
234 mainFile_ =
"CompiledSimulationEngine.cc";
252 std::string includes;
253 for (std::vector<std::string>::iterator it = includePaths.begin();
254 it != includePaths.end(); ++it) {
255 includes +=
"-I" + *it +
" ";
259 <<
"sources = $(wildcard *.cpp)" << endl
260 <<
"objects = $(patsubst %.cpp,%.o,$(sources))" << endl
261 <<
"dobjects = $(patsubst %.cpp,%.so,$(sources))" << endl
262 <<
"includes = " << includes << endl
270 <<
"all: CompiledSimulationEngine.so" << endl << endl
272 <<
"CompiledSimulationEngine.so: CompiledSimulationEngine.hh.gch "
273 <<
"$(dobjects) CompiledSimulationEngine.cc" << endl
274 <<
"\t#@echo Compiling CompiledSimulationEngine.so" << endl
275 <<
"\t$(CC) $(cppflags) -O0 $(includes) CompiledSimulationEngine.cc "
276 <<
"-c -o CompiledSimulationEngine.o" << endl
277 <<
"\t$(CC) $(soflags) CompiledSimulationEngine.o -o CompiledSimulationEngine.so"
279 <<
"$(dobjects): %.so: %.cpp CompiledSimulationEngine.hh.gch" << endl
283 <<
"\t$(CC) -c $(cppflags) $(opt_flags) $(includes) $< -o $@.o" << endl
284 <<
"\t$(CC) $(soflags) $(opt_flags) -lgcc $@.o -o $@" << endl
285 <<
"\t@rm -f $@.so.o" << endl
289 <<
"CompiledSimulationEngine.hh.gch:" << endl
290 <<
"\t$(CC) $(cppflags) $(opt_flags) $(includes) "
291 <<
"-xc++-header CompiledSimulationEngine.hh" << endl
295 <<
"\t@rm -f $(dobjects) CompiledSimulationEngine.so CompiledSimulationEngine.hh.gch" << endl;
356 *
os_ <<
"// " <<
className_ <<
" Generated automatically by ttasim" << endl
357 <<
"#ifndef _AUTO_GENERATED_COMPILED_SIMULATION_H_" << endl
358 <<
"#define _AUTO_GENERATED_COMPILED_SIMULATION_H_" << endl
359 <<
"#include \"SimValue.hh\"" << endl
360 <<
"#include \"DirectAccessMemory.hh\"" << endl
361 <<
"#include \"OSAL.hh\"" << endl
362 <<
"#include \"Operation.hh\"" << endl
363 <<
"#include \"OperationPool.hh\"" << endl
364 <<
"#include \"OperationContext.hh\"" << endl
365 <<
"#include \"CompiledSimulation.hh\"" << endl
366 <<
"#include \"BaseType.hh\"" << endl
367 <<
"#include \"MathTools.hh\"" << endl
373 *
os_ <<
"class " <<
className_ <<
" : public CompiledSimulation {" << endl
374 <<
"public:" << endl;
378 for (
int i = 0; i < fus.
count(); ++i) {
393 *
os_ <<
"\t" <<
"OperationContext "
398 *
os_ <<
"\t" <<
"DirectAccessMemory& "
406 *
os_ <<
"\t" <<
"Operation& "
415 for (
size_t j = 0; j < outPorts.size(); ++j) {
416 *
os_ <<
"\t" <<
"FUResultType "
439 for (
int i = 0; i < ius.
count(); ++i) {
450 for (
int i = 0; i < rfs.
count(); ++i) {
460 for (
int i = 0; i < buses.
count(); ++i) {
461 const Bus& bus = *buses.
item(i);
477 *
os_ <<
"EXPORT virtual ~" <<
className_ <<
"() { }" << endl << endl;
478 *
os_ <<
"EXPORT virtual void simulateCycle();" << endl << endl <<
"}; // end class" << endl;
480 *
os_ <<
"extern \"C\" EXPORT void updateFUOutputs_"
483 *
os_ << endl << endl <<
"#endif // include once" << endl << endl;
499 <<
"(const TTAMachine::Machine& machine," << endl
500 <<
"InstructionAddress entryAddress," << endl
501 <<
"InstructionAddress lastInstruction," << endl
502 <<
"SimulatorFrontend& frontend," << endl
503 <<
"CompiledSimController& controller," << endl
504 <<
"MemorySystem& memorySystem," << endl
505 <<
"bool dynamicCompilation,"
506 <<
"ProcedureBBRelations& procedureBBRelations)";
525 for (AddressMap::const_iterator it =
bbStarts_.begin();
527 *
os_ <<
"\t" <<
"extern \"C\" EXPORT void "
529 <<
"(void*);" << endl;
536 *
os_ <<
" : " << endl
537 <<
"CompiledSimulation(machine, entryAddress, lastInstruction, "
538 <<
"frontend, controller, memorySystem, dynamicCompilation, "
539 <<
"procedureBBRelations),"
547 for (
int i = 0; i < fus.
count(); i++) {
551 *
os_ <<
"\t" << context <<
".setCycleCountVariable(cycleCount_);"
558 *
os_ <<
"\t" << operation <<
".createState(" << context <<
");"
564 *
os_ <<
"\t" << context <<
".setMemory(&"
572 <<
"}" << endl << endl;
575 *
os_ <<
"// Simulation code:" << endl
576 <<
"EXPORT void " <<
className_ <<
"::simulateCycle() {"
580 *
os_ <<
"\t// jump dispatcher" << endl
581 <<
"\tjumpTargetFunc_ = getSimulateFunction(jumpTarget_);" << endl
582 <<
"\t(jumpTargetFunc_)(this);" << endl << endl;
585 <<
"}" << endl << endl;
624 for (
int i = 0; i < cfg.
nodeCount(); ++i) {
638 <<
"splitting a bb " << blockStart <<
" to " << end
639 <<
" with size " << end - blockStart << std::endl;
641 for (; blockStart < end; blockStart = blockEnd + 1) {
655 bbEnds_[blockEnd] = blockStart;
659 <<
"small block: " << blockStart <<
" to "
660 << blockEnd << std::endl;
666 blockStart = blockEnd + 1;
667 if (blockStart <= end) {
670 <<
"leftover block: " << blockStart <<
" to "
711 *
os_ <<
"/* PROGRAM EXIT */" << endl
712 <<
"engine.programCounter_ = " << address <<
";" << endl
713 <<
"engine.isFinished_ = true; return;" << endl;
723 *
os_ <<
"/* Updates all FU outputs to correct the visible machine state */" << endl
724 <<
"extern \"C\" EXPORT void updateFUOutputs_"
729 for (
int i = 0; i < fus.
count(); ++i) {
732 for (
size_t j = 0; j < outPorts.size(); ++j) {
751 *
os_ <<
"/* Class getter function */" << endl
752 <<
"extern \"C\" EXPORT CompiledSimulation* "
754 <<
"\tconst TTAMachine::Machine& machine," << endl
755 <<
"\tInstructionAddress entryAddress," << endl
756 <<
"\tInstructionAddress lastInstruction," << endl
757 <<
"\tSimulatorFrontend& frontend," << endl
758 <<
"\tCompiledSimController& controller," << endl
759 <<
"\tMemorySystem& memorySystem," << endl
760 <<
"\tbool dynamicCompilation," << endl
761 <<
"\tProcedureBBRelations& procedureBBRelations) {" << endl
763 <<
"(machine, entryAddress, lastInstruction, frontend, controller, "
764 <<
"memorySystem, dynamicCompilation, procedureBBRelations); "
765 << endl <<
"}" << endl << endl;
776 return std::string(
"\thaltSimulation(__FILE__, __LINE__, __FUNCTION__, \""
777 + message +
"\");\n");
784 *
os_ << endl <<
"void inline advanceClocks() {" << endl;
790 *
os_ << endl <<
"}" << endl;
818 for (OperationSymbolDeclarations::iterator it =
usedOperations_.begin();
820 *
os_ <<
"\t," << it->second
821 <<
"(operationPool_.operation(\"" << it->first <<
"\"))" << endl;
829 for (
int i = 0; i < fus.
count(); ++i) {
832 for (
size_t j = 0; j < outPorts.size(); ++j) {
838 if (fus.
count() > 0) {
845 for (
int i = 0; i < fus.
count(); i++) {
849 <<
"(FUMemory(\"" << fu.
name() <<
"\"))" << endl;
852 *
os_ <<
" {" << endl;
860 for (SimValueSymbolDeclarations::const_iterator it =
862 string symbolName = it->first;
863 *
os_ <<
"\t" <<
"addSymbol(\"" << symbolName <<
"\", "
864 << symbolName <<
");" << endl;
878 for (SimValueSymbolDeclarations::const_iterator it =
880 *
os_ <<
"\t" <<
"SimValue " << it->first <<
";" << endl;
890 *
os_ <<
"\t" <<
"resizeJumpTable(lastInstruction_ + 1);" << endl;
894 for (AddressMap::const_iterator it =
bbStarts_.begin();
896 *
os_ <<
"\t" <<
"setJumpTargetFunction(" << it->first <<
", &"
924 std::stringstream ss;
925 ss <<
"engine.jumpTarget_ = "
927 if (op.
name() ==
"call") {
942 std::stringstream ss;
944 ss << endl <<
"/* Operation: " << op.
name() <<
", latency: "
945 << op.
latency() <<
" */" << endl;
951 if (op.
name() !=
"jump" && op.
name() !=
"call") {
952 ss <<
"#define context "
955 <<
"#define opPool_ engine.operationPool_" << endl
957 <<
"#undef context" << endl
958 <<
"#undef opPool_" << endl
976 std::stringstream ss;
978 std::vector<string> operandSymbols;
982 for (
int i = 1; op.
port(i) != NULL; ++i) {
985 operandSymbols.push_back(outputSymbol);
986 ss <<
"SimValue " << outputSymbol
987 <<
"(" << op.
port(i)->
width() <<
");" << endl;
990 operandSymbols.push_back(inputSymbol);
995 ss <<
"SimValue* " << operandTable <<
"[] = {";
996 for (
size_t i = 0; i < operandSymbols.size(); ++i) {
997 ss <<
"&" << operandSymbols.at(i);
998 if (i < operandSymbols.size() - 1) {
1007 if (op.
name() !=
"jump" && op.
name() !=
"call") {
1009 <<
".simulateTrigger(" << operandTable <<
", "
1014 for (
int i = 1; op.
port(i) != NULL; ++i) {
1038 std::stringstream ss;
1039 string guardSymbolName;
1050 }
else if (
dynamic_cast<const PortGuard*
>(&guard) != NULL) {
1054 ss << endl <<
"#error unknown guard type!" << endl;
1072 " = !(MathTools::fastZeroExtendTo("
1073 << guardSymbolName <<
".uIntWordValue(), " <<
1074 guardSymbolName <<
".width()) == 0u);";
1092 std::stringstream ss;
1093 string guardSymbolName;
1102 }
else if (
dynamic_cast<const PortGuard*
>(&guard) != NULL) {
1106 ss << endl <<
"#error unknown guard type!" << endl;
1120 ss << endl <<
"if (";
1160 <<
" Generated automatically by ttasim" << endl
1161 <<
"#include \"" <<
headerFile_ <<
"\"" << endl << endl;
1169 startAddress().location();
1173 procedureStart, address));
1180 *
os_ << endl <<
"extern \"C\" EXPORT void "
1182 <<
"(void* eng) {" << endl;
1189 for (
int addr = address; bbEndAddr == -1; addr++) {
1195 *
os_ <<
"/* First instruction of BB - initialize address of next BB"
1197 *
os_ <<
"engine.jumpTarget_ = " << bbEndAddr + 1 <<
";" << endl;
1205 *
os_ <<
"engine.advanceClocks();" << endl;
1218 *
os_ <<
" = " << value <<
"u;";
1222 std::set<std::string> gotResults;
1223 DelayedAssignments::iterator it =
1226 *
os_ <<
"engine.clearFUResults(" << it->second.fuResultSymbol <<
");" << endl;
1227 *
os_ << it->second.targetSymbol <<
" = " << it->second.sourceSymbol
1228 <<
";" << std::endl;
1229 gotResults.insert(it->second.targetSymbol);
1234 bool endGuardBracket =
false;
1237 std::vector<CompiledSimMove> lateMoves;
1241 for (
int i = 0; i < instruction.
moveCount(); ++i) {
1242 const Move& move = instruction.
move(i);
1249 const Move& move = instruction.
move(i);
1257 if (move.
source().
isFUPort() && gotResults.find(moveSource) == gotResults.end() &&
1263 gotResults.insert(moveSource);
1268 endGuardBracket =
true;
1279 bool dependingMove =
false;
1280 for (
int j = instruction.
moveCount() - 1; j > 0 && i != j; --j) {
1283 dependingMove =
true;
1285 lateMoves.push_back(lateMove);
1297 moveSource +=
".sIntWordValue()";
1299 moveSource +=
".uIntWordValue()";
1303 if (!dependingMove) {
1304 *
os_ << moveDestination <<
" = " << moveSource <<
"; ";
1310 if (endGuardBracket) {
1312 endGuardBracket =
false;
1316 endGuardBracket =
false;
1319 for (
int i = 0; i < instruction.
moveCount(); ++i) {
1320 const Move& move = instruction.
move(i);
1340 endGuardBracket =
true;
1344 gotResults.end() &&
dynamic_cast<const ControlUnit*
>(
1359 if (endGuardBracket) {
1360 *
os_ <<
"}" << endl;
1361 endGuardBracket =
false;
1369 for (
int i = 0; i < instruction.
moveCount(); ++i) {
1370 const Move& move = instruction.
move(i);
1390 endGuardBracket =
true;
1394 gotResults.end() &&
dynamic_cast<const ControlUnit*
>(
1409 if (endGuardBracket) {
1410 *
os_ <<
"}" << endl;
1411 endGuardBracket =
false;
1428 *
os_ <<
" = SIntWord("<< value <<
");";
1431 *
os_ <<
" = " << value <<
"u;";
1436 for (std::vector<CompiledSimMove>::const_iterator it = lateMoves.begin();
1437 it != lateMoves.end(); ++it) {
1438 *
os_ << it->copyFromBusCode();
1440 if (it->destination().isGPR()) {
1449 *
os_ <<
"/* NOP */" << endl;
1454 *
os_ <<
"engine.cycleEnd();" << endl;
1457 *
os_ <<
"engine.cycleCount_++;" << endl;
1459 AddressMap::iterator bbEnd =
bbEnds_.find(address);
1465 *
os_ <<
"++engine.bbExecCounts_[" << bbStart <<
"];" << endl;
1476 <<
"if (engine.cycleCount_ >= engine.cyclesToSimulate_) {" << endl
1477 <<
"\t" <<
"engine.stopRequested_ = true;" << endl
1479 <<
"(engine);" << endl
1482 *
os_ <<
"{ engine.programCounter_ = engine.jumpTarget_; "
1483 <<
"engine.lastExecutedInstruction_ = " << address
1484 <<
"; return; }" << endl;
1490 *
os_ << endl <<
"} /* end function */" << endl << endl;
1504 vector<string> operands;
1505 string source =
"EXEC_OPERATION(";
1508 for (
int i = 1; op.
port(i) != NULL; ++i) {
1523 std::string simCode =
1526 for (
int i = 1, tmp = 1; op.
port(i) != NULL; ++i) {
1529 std::string outValueStr;
1532 size_t ovLen = outputStr.length() + 3;
1533 while (simCode.find(outputStr +
" = ") != string::npos) {
1534 std::size_t begin = simCode.find(outputStr+
" = ");
1535 std::size_t end = simCode.find(
";", begin);
1536 outValueStr = simCode.substr(begin+ovLen,(end-begin-ovLen));
1537 simCode.erase(begin, end-begin);
1540 if (outValueStr.empty()) {
1541 std::string msg =
"Machine has bound outport not used by op: ";
1543 msg +=
" port index: ";
1551 if (simCode.find(outValueStr) == string::npos) {
1555 while(simCode.find(outValueStr) != string::npos) {
1556 string::iterator it = simCode.begin() + simCode.find(outValueStr);
1557 simCode.replace(it, it + outValueStr.length(), tempVariable);
1568 while (simCode.find(
"SimValue tmp") != string::npos) {
1569 std::size_t begin = simCode.find(
"SimValue tmp");
1570 std::size_t end = simCode.find(
";", begin);
1571 std::string tmpName = simCode.substr(begin+9,(end-begin-9));
1574 while(simCode.find(tmpName) != string::npos) {
1575 string::iterator it = simCode.begin() + simCode.find(tmpName);
1576 simCode.replace(it,it + tmpName.length(), tempVariable);
1595 const MemoryOperationDescription& memOpDesc = supportedMemoryOps.at(
1597 method =
"fastWrite";
1598 if (memOpDesc.mauCount > 1) {
1599 method += std::to_string(memOpDesc.mauCount) +
"MAUs";
1600 if (memOpDesc.mauOrder == MAUOrder::littleEndian) {
1609 return memory +
"." + method +
"(" + address +
", " + dataToWrite +
");";
1620 std::stringstream ss;
1625 string extensionMode =
"SIGN_EXTEND";
1626 string resultSignExtend;
1629 const MemoryOperationDescription& memOpDesc = supportedMemoryOps.at(
1631 method =
"fastRead";
1632 if (memOpDesc.mauCount > 1) {
1633 method += std::to_string(memOpDesc.mauCount) +
"MAUs";
1634 if (memOpDesc.mauOrder == MAUOrder::littleEndian) {
1643 if (memOpDesc.extensionMode == ExtensionMode::sign) {
1644 extensionMode =
"SIGN_EXTEND";
1646 extensionMode =
"ZERO_EXTEND";
1649 resultSignExtend = temp +
" = " + extensionMode
1650 +
"(" + temp +
", (" + MAUSize +
"*"
1651 + std::to_string(memOpDesc.mauCount) +
"));";
1653 ss <<
"ULongWord " << temp <<
"; " << memory +
"." << method <<
"("
1654 << address <<
", " << temp <<
"); ";
1656 ss << resultSignExtend <<
" ";
1684 const std::string& value,
1687 std::stringstream ss;
1693 const bool resultInSameBasicBlock = bbEnd->first ==
1694 bbEnds_.lower_bound(writeTime)->first;
1696 const int bbStart = bbEnd->second;
1697 bool staticSimulationPossible =
false;
1710 && (writeTime > lastWrite)) {
1711 staticSimulationPossible =
true;
1714 && staticSimulationPossible; ++i) {
1717 for (
int j = 0; j < instr.
moveCount(); ++j) {
1722 staticSimulationPossible =
false;
1729 if (staticSimulationPossible) {
1735 <<
", " <<
"engine.cycleCount_, " << value <<
", " << latency <<
");";
1736 if (writeTime > lastWrite) {
1753 const std::string& destination,
1754 const std::string& resultSymbol) {
1755 std::stringstream ss;
1757 ss <<
"engine.FUResult(" << destination <<
", " << resultSymbol
1758 <<
", engine.cycleCount_);" << endl;
1772 for (
int i = 0; i < fus.
count(); ++i) {
1787 std::vector<TTAMachine::Port*>
1790 std::vector<TTAMachine::Port*> ports;
1791 for (
int i = 0; i < fu.
portCount(); ++i) {
1793 ports.push_back(fu.
port(i));
1800 std::ostream& stream) {
1803 const std::string& regName = i->first;
1804 for (
int j = i->second -1 ; j > 0; j--) {
1805 stream <<
"guard_pipeline_" << regName <<
"_" << j <<
" = "
1806 <<
"guard_pipeline_" << regName <<
"_" << j -1
1807 <<
";" << std::endl;
1813 std::ostream& stream) {
1816 const std::string& regName = i->first;
1817 for (
int j = 0; j < i->second ; j++) {
1818 stream <<
"bool guard_pipeline_" + regName <<
"_" << j <<
1827 std::string regName =
"RF_" + rf->
name() +
"_" +
1831 return "engine.guard_pipeline_RF_" +
1839 const std::string& regSymbolName, std::ostream& stream) {
1840 std::string tmpString;
1841 std::string tmpString2;
1843 const string tmpRef1 = regSymbolName;
1847 const string& tmpRef2 = (tmpRef1.find(
"engine.") == 0) ?
1848 tmpString2 = tmpRef1.substr(7) :
1853 stream <<
"engine.guard_pipeline_" << tmpRef2 <<
"_0 "
1854 <<
" = !(MathTools::fastZeroExtendTo("
1855 << tmpRef1 <<
".uIntWordValue(), "
1856 << tmpRef1 <<
".width()) == 0u);" << std::endl;
1870 for (
auto& pair : supportedMemoryOps) {
1871 result.insert(pair.first);
1879 auto it = supportedMemoryOps.find(opName);
1880 if (it == supportedMemoryOps.end())
return false;
1882 return (it->second.accessMode == AccessMode::write);
1887 auto it = supportedMemoryOps.find(opName);
1888 if (it == supportedMemoryOps.end())
return false;
1890 return (it->second.accessMode == AccessMode::read);
std::string headerFile_
Header filename.
std::map< std::string, std::string > usedGuardSymbols_
Temporary list of the used guard bool symbols per instruction.
std::set< InstructionAddress > exitPoints_
Program exit point addresses.
static const char * COMPILED_SIM_SO_FLAGS
flags used when compiling .so files
std::string immediateRegisterSymbol(const TTAProgram::Terminal &terminal) const
virtual bool isFUPort() const
std::string guardPipelineTopSymbol(const TTAMachine::RegisterGuard &guard)
static TCETools::CIStringSet supportedMemoryOperations()
int instructionNumber_
Absolute instruction # being processed.
void generateInstruction(const TTAProgram::Instruction &instruction)
bool isTriggering() const
std::map< InstructionAddress, InstructionAddress > procedureStart
Procedure start per basic block starts.
Operation & operation(const char *name)
bool isProcedureBegin_
Are we at the beginning of a new procedure?
UInt32 InstructionAddress
virtual AddressMap basicBlocks() const
std::string handleOperationWithoutDag(const TTAMachine::HWOperation &op)
virtual StringSet createdFiles() const
virtual TCEString name() const
GuardPipeline guardPipeline_
void generateConstructorCode()
int procedureCount() const
TTAMachine::Machine * machine
the architecture definition of the estimated processor
std::map< InstructionAddress, InstructionAddress > AddressMap
A type for storing address-to-address combinations.
Node & node(const int index) const
std::string detectConflicts(const TTAMachine::HWOperation &op)
int registerIndex() const
FunctionUnit * parentUnit() const
InstructionAddress originalEndAddress() const
std::string generateTriggerCode(const TTAMachine::HWOperation &op)
ProcedureBBRelations procedureBBRelations_
Basic blocks relations to procedures and vice versa.
std::string portSymbol(const TTAMachine::Port &port) const
bool isUnconditional() const
std::string lastGuardBool_
name of the last used guard variable
void generateConstructorParameters()
std::string operationSymbol(const std::string &operationName, const TTAMachine::FunctionUnit &fu) const
std::string generateGuardRead(const TTAProgram::Move &move)
std::string busSymbol(const TTAMachine::Bus &bus) const
virtual int width() const =0
Terminal & destination() const
void generateFUOutputUpdater()
void generateJumpTableCode()
const TTAMachine::Machine & machine_
The machine used for simulation.
std::string DAMemorySymbol(const TTAMachine::FunctionUnit &fu) const
void generateAdvanceClockCode()
bool handleCycleEnd_
Should we let frontend handle each cycle end.
std::string returnAddressSymbol(const TTAMachine::ControlUnit &gcu) const
static const char * COMPILED_SIM_CPP_FLAGS
cpp flags used for compiled simulation
std::string operationContextSymbol(const TTAMachine::FunctionUnit &fu) const
virtual BaseFUPort * port(const std::string &name) const
virtual AddressSpace * addressSpace() const
static bool isStoreOperation(const std::string &opName)
static std::ostream & logStream()
const TTAProgram::Procedure * currentProcedure_
Pointer to the current Procedure being processed.
std::vector< TTAMachine::Port * > fuOutputPorts(const TTAMachine::FunctionUnit &fu) const
bool conflictDetectionEnabled() const
virtual int maxLatency() const
static std::string toString(const T &source)
unsigned maxInstructionsPerFile_
Maximum number of instructions per engine source code file, computed from the instruction width (bus ...
StringSet createdFiles_
A list of the code files created during the process.
virtual int numberOfRegisters() const
std::string currentFileName_
Name of the current file being processed.
#define assert(condition)
std::string guardBoolSymbol() const
std::string handleJump(const TTAMachine::HWOperation &op)
Instruction & instructionAt(InstructionAddress address) const
virtual FUPort * port(int operand) const
std::string generateGuardCondition(const TTAProgram::Move &move)
virtual bool isImmediateRegister() const
SimValueSymbolDeclarations declaredSymbols_
A list of all symbols that are declared after the program code is ready.
CompiledSimCodeGenerator(const TTAMachine::Machine &machine, const TTAProgram::Program &program, const TTASimulationController &controller, bool fuResourceConflictDetection, bool handleCycleEnd, bool dynamicCompilation, bool basicBlockPerFile=false, bool functionPerFile=true, const TCEString &globalSymbolPrefix="")
virtual ControlUnit * controlUnit() const
int moveCounter_
How many moves have we been through with?
void generateSymbolDeclarations()
bool handleRegisterWrite(const std::string ®SymbolName, std::ostream &stream)
const std::string & name() const
InstructionAddress lastInstructionOfBB_
last instruction of the current basic block
std::string basicBlockSymbol(InstructionAddress startAddress) const
virtual int instructionCount() const
virtual ImmediateUnitNavigator immediateUnitNavigator() const
virtual std::set< InstructionAddress > findProgramExitPoints(const TTAProgram::Program &program, const TTAMachine::Machine &machine) const
std::string generateFUResultRead(const std::string &destination, const std::string &resultSymbol)
static std::vector< std::string > includeDirPaths()
std::string copyToBusCode() const
std::map< InstructionAddress, std::string > basicBlockFiles
Basic block starts and their corresponding .cpp files.
SpecialRegisterPort * specialRegisterPort(int index) const
FUResultWrites lastFUWrites_
Last known FU result writes.
ConflictDetectionCodeGenerator conflictDetectionGenerator_
Conflict detection code generator.
std::string registerSymbol(const TTAProgram::Terminal &terminal) const
DelayedAssignments delayedFUResultWrites_
Delayed FU Result assignments.
MoveGuard & guard() const
std::string generateAddFUResult(const TTAMachine::FUPort &resultPort, const std::string &value, int latency)
void generateGuardPipelineVariables(std::ostream &stream)
int specialRegisterPortCount() const
std::string handleOperation(const TTAMachine::HWOperation &op)
virtual FunctionUnitNavigator functionUnitNavigator() const
std::string notifyOfConflicts()
void generateShutdownCode(InstructionAddress address)
virtual bool isGPR() const
const TTAMachine::ControlUnit & gcu_
GCU.
virtual int operationCount() const
void generateHeaderAndMainCode()
virtual const TTAMachine::ImmediateUnit & immediateUnit() const
void enablePrefix(const std::string &prefix)
InstructionAddress location() const
std::string mainFile_
Main source filename. This includes the constructor and the simulateCycle().
std::string FUResultSymbol(const TTAMachine::Port &port) const
static std::string createSimulationCode(const OperationDAG &dag, std::vector< std::string > *varReplacements=NULL)
static int longestGuardLatency(const TTAMachine::Machine &mach)
OperationPool operationPool_
The operation pool.
BasicBlockStarts basicBlockStarts
All basic block start addresses per procedure start.
virtual int operationPortCount() const
virtual bool isOutput() const
Guard * guard(int index) const
virtual int portCount() const
Immediate & immediate(int i) const
static const std::string DIRECTORY_SEPARATOR
virtual const TTAMachine::FunctionUnit & functionUnit() const
std::ostream * os_
Current output stream i.e. the above file.
unsigned int unsignedValue() const
virtual int width() const
virtual int dagCount() const
std::string generateTempVariable() const
virtual RegisterFileNavigator registerFileNavigator() const
std::string updateSymbolDeclarations()
std::string className_
Name of the class to be created.
std::fstream currentFile_
Current file being processed.
virtual bool isInverted() const
std::set< std::string > StringSet
A type for std::string sets.
find Finds info of the inner loops in the false
void findBasicBlocks() const
OperationSymbolDeclarations usedOperations_
A list of used operations.
unsigned maxInstructionsPerSimulationFunction_
Max for each simulation function.
bool functionPerFile_
Should the generator start with a new file after function end.
virtual std::string name() const
FunctionUnit * parentUnit() const
std::string targetDirectory_
Directory where to write the source files of the engine.
AddressMap bbStarts_
The basic block map referred by start of the block as a key.
int immediateCount() const
virtual const TTAMachine::HWOperation * hwOperation() const
virtual BusNavigator busNavigator() const
std::string symbolDeclaration(const TTAMachine::FunctionUnit &fu)
virtual void generateToDirectory(const std::string &dirName)
virtual bool isInput() const
static bool isLoadOperation(const std::string &opName)
virtual Instruction & instructionAtIndex(int index) const
Terminal & source() const
bool dynamicCompilation_
Is this a dynamic compiled simulation?
CompiledSimSymbolGenerator symbolGen_
The symbol generator.
virtual const TTAMachine::Port & port() const
AddressMap bbEnds_
The basic block map referred by end of the block as a key.
ComponentType * item(int index) const
static TCEString registerName(const TTAMachine::RegisterFile &rf, int index, char delim='.')
virtual HWOperation * operation(const std::string &name) const
find Finds info of the inner loops in the program
virtual ProcedureBBRelations procedureBBRelations() const
virtual int guardLatency() const
A struct for tracking basic blocks and their relation to their procedures.
void generateGuardPipelineAdvance(std::ostream &stream)
Instruction & lastInstruction() const
void generateSimulationGetter()
const TTAMachine::Guard & guard() const
virtual FUPort * operationPort(const std::string &name) const
const TTASimulationController & simController_
The simulator frontend.
int globalGuardLatency() const
bool basicBlockPerFile_
Should the generator generate only one basic block per code file.
std::string moveOperandSymbol(const TTAProgram::Terminal &terminal, const TTAProgram::Move &move) const
std::string generateLoadTrigger(const TTAMachine::HWOperation &op)
virtual int width() const
std::string generateStoreTrigger(const TTAMachine::HWOperation &op)
const RegisterFile * registerFile() const
int instructionCounter_
Istruction counter for checking how many instructions to put per file.
void generateSimulationCode()
Procedure & procedure(int index) const
std::string advanceClockCode()
virtual OperationDAG & dag(int index) const
void updateDeclaredSymbolsList()
InstructionAddress originalStartAddress() const
TCEString globalSymbolSuffix_
std::string generateHaltCode(const std::string &message="")
const TTAProgram::Program & program_
The simulated program.
void generateProcedureCode(const TTAProgram::Procedure &procedure)
virtual int width() const
StringSet declaredFunctions_
A set of all the declared functions.
std::string extraInitialization()
virtual ~CompiledSimCodeGenerator()
void addDeclaredSymbol(const std::string &name, int width)