32 FD_DCG(
"EmbeddedcCodeGenerator(" <<
this <<
")::EmbeddedcCodeGenerator()");
38 FD_DCG(
"EmbeddedcCodeGenerator(" <<
this <<
")::~EmbeddedcCodeGenerator()");
43 FD_DCG(
"EmbeddedcCodeGenerator::Clear()");
56 FD_DCG(
"EmbeddedcCodeGenerator::DoReadTargetConfiguration()");
63 FD_DCG(
"EmbeddedcCodeGenerator::DoWriteTargetConfiguration()");
74 FCG_VERB1(
"EmbeddedcCodeGenerator::Compile(): prefer compiled bitmasks over bit-address maths");
82 FD_DCG(
"EmbeddedcCodeGenerator(" <<
this <<
")::DoGenerate()");
86 Comment(
"************************************************");
87 Comment(
"CodeGenerator: Target Embedded C ");
88 Comment(
"************************************************");
102 Output() <<
"}; /* end function " <<
mPrefix <<
"cyclic() */";
109 Comment(
"************************************************");
110 Comment(
"CodeGenerator: Generated Code Ends Here ");
111 Comment(
"************************************************");
121 Comment(
"************************************************");
122 Comment(
"* update timer states *");
123 Comment(
"************************************************");
131 <<
TargetAddress(
AA(
"timer_" + tit->second.mAddress +
"_cnt")) <<
" -= dec;";
163 Output() <<
"/* " << text <<
" */";
173 std::string res=
mPrefix+address;
183void EmbeddedcCodeGenerator::IntegerDeclare(
const AA& address){
189void EmbeddedcCodeGenerator::IntegerDeclare(
const AA& address,
int val){
195void EmbeddedcCodeGenerator::IntegerAssign(
const AA& address,
int val){
201void EmbeddedcCodeGenerator::IntegerAssign(
const AA& address,
const AX& expression){
207void EmbeddedcCodeGenerator::IntegerIncrement(
const AA& address,
int val) {
220 return AX(expression +
" / " + IntegerConstant(val));
225 return AX(expression +
" % " + IntegerConstant(val));
230 return AX(
"(" + WordConstant(1) +
" << " + expression +
")" );
235 return AX(
TargetAddress(address) +
" == " + IntegerConstant(val));
239CodePrimitives::AX EmbeddedcCodeGenerator::IntegerIsEq(
const AA& address,
const AX& expression) {
244CodePrimitives::AX EmbeddedcCodeGenerator::IntegerIsNotEq(
const AA& address,
const AX& expression) {
249CodePrimitives::AX EmbeddedcCodeGenerator::IntegerIsNotEq(
const AA& address,
int val) {
250 return AX(
TargetAddress(address) +
" != " + IntegerConstant(val));
254CodePrimitives::AX EmbeddedcCodeGenerator::IntegerIsGreater(
const AA& address,
int val) {
255 return AX(
TargetAddress(address) +
" > " + IntegerConstant(val));
260 return AX(
TargetAddress(address) +
" < " + IntegerConstant(val));
264bool EmbeddedcCodeGenerator::HasIntmaths(
void) {
270 AX res(ToStringInteger(val));
278 FCG_ERR(
"EmbeddedcCodeGenerator: unsupported integer data type [" <<
mIntegerType <<
"]");
283void EmbeddedcCodeGenerator::WordDeclare(
const AA& address){
289void EmbeddedcCodeGenerator::WordDeclare(
const AA& address, word_t val){
295void EmbeddedcCodeGenerator::WordAssign(
const AA& address, word_t val){
301void EmbeddedcCodeGenerator::WordAssign(
const AA& address,
const AX& expression){
307void EmbeddedcCodeGenerator::WordOr(
const AA& address, word_t val) {
313void EmbeddedcCodeGenerator::WordOr(
const AA& address,
const AX& expression) {
319void EmbeddedcCodeGenerator::WordOr(
const AA& address,
const AA& op1,
const AA& op2) {
325void EmbeddedcCodeGenerator::WordOr(
const AA& address,
const AA& op1, word_t op2) {
331void EmbeddedcCodeGenerator::WordAnd(
const AA& address, word_t val) {
337void EmbeddedcCodeGenerator::WordAnd(
const AA& address,
const AX& expression) {
343void EmbeddedcCodeGenerator::WordAnd(
const AA& address,
const AA& op1,
const AA& op2) {
349void EmbeddedcCodeGenerator::WordAnd(
const AA& address,
const AA& op1, word_t op2) {
355void EmbeddedcCodeGenerator::WordNand(
const AA& address,
const AX& expression) {
362 return AX(
"( " +
TargetAddress(address) +
" & " + WordConstant(0x01<<idx) +
" ) != 0");
367 return AX(
"( " +
TargetAddress(address) +
" & " + WordConstant(0x01<<idx) +
" ) == 0");
371CodePrimitives::AX EmbeddedcCodeGenerator::WordIsMaskSet(
const AA& address, word_t mask) {
372 return AX(
"( " +
TargetAddress(address) +
" & " + WordConstant(mask) +
" ) != 0");
377 return AX(
TargetAddress(address) +
" == " + WordConstant(val));
381CodePrimitives::AX EmbeddedcCodeGenerator::WordIsNotEq(
const AA& address, word_t val) {
382 return AX(
TargetAddress(address) +
" != " + WordConstant(val));
388 std::stringstream sstr;
389 sstr <<
"0x" << std::setbase(16) << std::setfill(
'0');
391 if(val==0) sstr << std::setw(2);
393 if(
mWordType ==
"unsigned char") { sstr << std::setw(2); val &=0xff; }
395 if(
mWordType ==
"unsigned char") sstr << val;
396 else if(
mWordType ==
"uint8_t") sstr << ((uint8_t) val) <<
"U";
397 else if(
mWordType ==
"unsigned short") sstr << ((
unsigned short) val) <<
"U";
398 else if(
mWordType ==
"unsigned int") sstr << ((
unsigned int) val) <<
"U";
399 else if(
mWordType ==
"uint16_t") sstr << ((uint16_t) val) <<
"U";
400 else if(
mWordType ==
"unsigned long") sstr << ((
unsigned long) val) <<
"UL";
401 else if(
mWordType ==
"uint32_t") sstr << ((uint32_t) val) <<
"UL";
402 else if(
mWordType ==
"unsigned long long") sstr << ((
unsigned long long) val) <<
"ULL";
403 else FCG_ERR(
"EmbeddedcCodeGenerator: unsupported word data type [" <<
mWordType <<
"]");
412 for(std::size_t i=0; i<val.length(); ++i) {
417 if(c==
'"') { res.append(
"\\\"");
continue; }
419 if(c==
'\\') { res.append(
"\\\\");
continue; }
421 if((c>=0x20) && (c<0x7f)) { res.append(1,c);
continue; };
423 FCG_ERR(
"EmbeddedcCodeGenerator: non-printable ascii or other encoding unsupported [" << val <<
"]");
431 std::stringstream strstr;
433 if(val.size()+offset<25) newline=25;
437 if(vit==val.size()+offset)
break;
438 if(vit< (
size_t) offset)
439 strstr << IntegerConstant(0);
441 strstr << IntegerConstant(val[vit-offset]);
443 if(vit==val.size()+offset)
break;
447 strstr << std::endl <<
" ";
452 return AX(strstr.str());
456void EmbeddedcCodeGenerator::CintarrayDeclare(
const AA& address,
int offset,
const std::vector<int>& val) {
458 FCG_ERR(
"EmbeddedcCodeGenerator::Cintarray(): ignoring empty const vector");
462 FCG_ERR(
"EmbeddedcCodeGenerator::Cintarray(): const vector exceeds addres range");
467 std::vector<int> oval(val.size()+offset,0);
468 for(
size_t i=0; i<val.size(); ++i)
469 oval[offset+i]=val[i];
475 Output() << IntarrayConstant(offset,val) <<
";";
482 return AA(address +
"[" + ToStringInteger(index) +
"]");
491bool EmbeddedcCodeGenerator::HasCintarray(
void) {
498 std::stringstream strstr;
500 if(val.size()+offset<25) newline=25;
504 if(vit==val.size()+offset)
break;
505 if(vit < (
size_t) offset)
506 strstr << WordConstant(0);
508 strstr << WordConstant(val[vit-offset]);
510 if(vit==val.size()+offset)
break;
514 strstr << std::endl <<
" ";
519 return AX(strstr.str());
523void EmbeddedcCodeGenerator::CwordarrayDeclare(
const AA& address,
int offset,
const std::vector<word_t>& val) {
525 FCG_ERR(
"EmbeddedcCodeGenerator::Cwordarray(): ignoring empty const vector");
529 FCG_ERR(
"EmbeddedcCodeGenerator::Cwordarray(): const vector exceeds addres range");
534 Output() << WordarrayConstant(offset,val) <<
";";
541 return AA(address +
"[" + ToStringInteger(index) +
"]");
550bool EmbeddedcCodeGenerator::HasCwordarray(
void) {
557 FCG_ERR(
"EmbeddedcCodeGenerator::Intarray(): ignoring empty const vector");
561 FCG_ERR(
"EmbeddedcCodeGenerator::Intarray(): vector exceeds address range");
566 Output() << IntarrayConstant(offset,val) <<
";";
574 FCG_ERR(
"EmbeddedcCodeGenerator::Intarray(): ignoring empty const vector");
578 FCG_ERR(
"EmbeddedcCodeGenerator::Intarray(): const vector exceeds address range");
587 return AA(address +
"[" + ToStringInteger(index) +
"]");
601void EmbeddedcCodeGenerator::WordarrayDeclare(
const AA& address,
int offset,
const std::vector<word_t>& val) {
603 FCG_ERR(
"EmbeddedcCodeGenerator::Wordarray(): ignoring empty const vector");
607 FCG_ERR(
"EmbeddedcCodeGenerator::Wordarray(): const vector exceeds addres range");
612 Output() << WordarrayConstant(offset,val) <<
";";
618void EmbeddedcCodeGenerator::WordarrayDeclare(
const AA& address,
int offset,
int len) {
620 FCG_ERR(
"EmbeddedcCodeGenerator::Wordarray(): ignoring empty const vector");
624 FCG_ERR(
"EmbeddedcCodeGenerator::Wordarray(): const vector exceeds addres range");
633 return AA(address +
"[" + ToStringInteger(index) +
"]");
642bool EmbeddedcCodeGenerator::HasWordarray(
void) {
648 std::stringstream strstr;
650 if(val.size()+offset <4) {
655 strstr <<
"{" << std::endl;
659 if(vit==val.size()+offset)
break;
660 if(vit < (
size_t)offset)
661 strstr << StringConstant(
"");
663 strstr << StringConstant(val[vit-offset]);
665 if(vit==val.size()+offset)
break;
674 return AX(strstr.str());
678void EmbeddedcCodeGenerator::CstrarrayDeclare(
const AA& address,
int offset,
const std::vector<std::string>& val) {
680 FCG_ERR(
"EmbeddedcCodeGenerator::Cstrarrayy(): ignoring empty string array");
684 FCG_ERR(
"EmbeddedcCodeGenerator::Cstrarray(): string array exceeds address range");
689 Output() << StrarrayConstant(offset,val) <<
";";
696 return AA(address +
"[" + ToStringInteger(index) +
"]");
705bool EmbeddedcCodeGenerator::HasCstrarray(
void) {
711void EmbeddedcCodeGenerator::IfTrue(
const AX& expression) {
712 Output() <<
"if( " << expression <<
" ) {";
718void EmbeddedcCodeGenerator::IfFalse(
const AX& expression) {
719 Output() <<
"if( ! ( " << expression <<
" ) ) {";
725void EmbeddedcCodeGenerator::IfWord(
const AX& expression) {
726 Output() <<
"if( " << expression <<
" ) {";
732void EmbeddedcCodeGenerator::IfElse(
void) {
740void EmbeddedcCodeGenerator::IfElseIfTrue(
const AX& expression) {
742 Output() <<
"} else if( " << expression <<
" ) {";
748void EmbeddedcCodeGenerator::IfEnd(
void) {
755void EmbeddedcCodeGenerator::SwitchBegin(
const AA& address){
761void EmbeddedcCodeGenerator::SwitchCase(
const AA& address,
int val){
763 Output() <<
"case " << IntegerConstant(val) <<
":";
769void EmbeddedcCodeGenerator::SwitchCases(
const AA& address,
int from,
int to){
772 SwitchCase(address, from);
776 for(
int val=from; val<=to; ++val) {
777 Output() <<
"case " << IntegerConstant(val) <<
":";
784void EmbeddedcCodeGenerator::SwitchCases(
const AA& address,
const std::set< int >& vals){
787 std::set< int >::const_iterator vit=vals.begin();
788 for(; vit!=vals.end(); ++ vit) {
789 Output() <<
"case " << IntegerConstant(*vit) <<
":";
796void EmbeddedcCodeGenerator::SwitchBreak(
void){
803void EmbeddedcCodeGenerator::SwitchEnd(
void){
815bool EmbeddedcCodeGenerator::HasMultiCase(
void) {
820void EmbeddedcCodeGenerator::LoopBegin(
void) {
827void EmbeddedcCodeGenerator::LoopBreak(
const AX& expression) {
828 Output() <<
"if( " << expression <<
" ) break;";
834void EmbeddedcCodeGenerator::LoopEnd(
void) {
840void EmbeddedcCodeGenerator::FunctionReturn(
void) {
847void EmbeddedcCodeGenerator::TimerDeclare(
const AA& address,
const std::string& litval) {
850 const char* first = litval.c_str();
851 strtol(first,&next,10);
853 if(*next!=
'f') err=
true;
854 if(!err)
if(*(++next)!=
't') err=
true;
855 if(!err)
if(*(++next)!=
'u') err=
true;
856 if(!err)
if(*(++next)!=0) err=
true;
858 FCG_ERR(
"EmbeddedcCodeGenerator: missmatched time literal "+ litval);
865void EmbeddedcCodeGenerator::TimerStart(
const AA& address) {
869void EmbeddedcCodeGenerator::TimerStop(
const AA& address) {
873void EmbeddedcCodeGenerator::TimerReset(
const AA& address,
const std::string& litval) {
874 int val=(int) strtol(litval.c_str(),NULL,10);
875 Output() <<
TargetAddress(AA(
"timer_"+address+
"_cnt")) <<
" = " << IntegerConstant(val) <<
";";
884void EmbeddedcCodeGenerator::RunActionSet(
const std::string& address) {
885 Output() << address <<
" = 1;" ;
888void EmbeddedcCodeGenerator::RunActionClr(
const std::string& address) {
889 Output() << address <<
" = 0;" ;
892void EmbeddedcCodeGenerator::RunActionExe(
const AX& expression) {
893 Output() << expression <<
";";
#define FAUDES_REGISTERCODEGENERATOR(ftype, ctype)
Class registration macro.
Code-generator for target C.
virtual void LineFeed(int lines=1)
LineFeed (convenience support for derived classes)
virtual const std::string & Name(void) const
Get objects's name (reimplementing base faudes::Type)
TimerIterator TimersBegin()
Access to timer records by iterator.
virtual void IndentInc()
Indentation (convenience support for derived classes)
TimerIterator TimersEnd()
Access to timer records by iterator.
int mWordSize
compressed boolean capacity of target type word
bool mMuteComments
mute comments
int mIntegerSize
compressed boolean capacity of target type integer
std::map< std::string, TimerConfiguration >::iterator TimerIterator
Access to timer records by iterator.
virtual std::ostream & Output(void)
Output stream.
static std::string VersionString(void)
Version (refers to macro COMPILEDES_VERSION, defined in cgp_codegenerator.h)
virtual void IndentDec()
Indentation (convenience support for derived classes)
Abstract address; see also Absstract_Addresses.
Abstract expression; see also Absstract_Addresses.
Execution semantics in terms of code primitives.
bool mBitAddressArithmetic
code option: compute bit and word address on target
std::string mStateUpdateHook
code option: state change hook
virtual void DoGenerateDeclarations(void)
cut-and-paste template for code snippet assembly
virtual void DoGenerateResetCode(void)
cut-and-paste template for code snippet assembly
virtual void LiteralAppend(void)
Cosmetic: append literally from configuration.
virtual void Comment(const std::string &text)
Target comments (see EmbeddedcCodeGenerator for consistent reimplementation pattern)
std::map< std::string, bitarray_rec > mBitarrays
Record of all declared bit-arrays.
virtual void DoReadTargetConfiguration(TokenReader &rTr)
re-implement token i/o for extra configuration
std::string mIntegerType
target data type for integer
virtual void DoGenerateCyclicCode(void)
cut-and-paste template for code snippet assembly
virtual void Clear(void)
Clear all data.
std::string mWordType
target data type for word
virtual void DoWriteTargetConfiguration(TokenWriter &rTw) const
re-implement token i/o for extra configuration
bool mArrayForBitmasks
code option: use const array to represent bit-masks
virtual void DoCompile(void)
virtual hook to extend compiled data
virtual void LiteralPrepend(void)
Cosmetic: prepend literally from configuration data.
std::string mPrefix
universal prefix (pseudo name space)
std::string mEventExecutionHook
code option: event exec hook
Implementation of code primitives by generic C-code.
void DoCompile(void)
add my preferences to DoCompile
void DoGenerate(void)
virtual hook for generate
virtual bool HasIntarray(void)
default int-array: not supported
virtual void DoWriteTargetConfiguration(TokenWriter &rTw) const
File i/o.
virtual void Comment(const std::string &text)
Target comments (see EmbeddedcCodeGenerator for consistent reimplementation pattern)
EmbeddedcCodeGenerator(void)
Constructor.
virtual void DoReadTargetConfiguration(TokenReader &rTr)
File i/o.
virtual AA IntarrayAccess(const AA &address, int index)
default int-array: not supported
virtual void Clear(void)
Clear all data.
virtual void DecrementTimers(void)
re-implemented/additional code blocks
virtual std::string TargetAddress(const AA &address)
abstract address conversion
virtual ~EmbeddedcCodeGenerator(void)
Explicit destructor.
virtual AX TargetExpression(const AA &address)
abstract address conversion
void InsertExecHooks(void)
Helper to insert target code for execution hooks.
virtual void IntarrayDeclare(const AA &address, int offset, int len)
default int-array: not supported