35 void usage(
const std::string& rMessage=
"") {
 
   38     std::cerr << rMessage << std::endl;
 
   39     std::cout << 
"" << std::endl;
 
   42   std::cerr << std::endl;
 
   43   std::cerr << 
"utility to generates c code from an rti-file to " << std::endl;
 
   44   std::cerr << 
"1) register faudes-types and -functions with the run-time interface," << std::endl;
 
   45   std::cerr << 
"2) extract c declarations for bindings interface code." << std::endl;
 
   46   std::cerr << std::endl;
 
   47   std::cerr << 
"usage:" << std::endl;
 
   48   std::cerr << 
" rti2code [-swig|-loader] <rti input file> <output basename>" << std::endl;
 
   49   std::cerr << 
" rti2code -merge <rti input files> <output rti-file>" << std::endl;
 
   50   std::cerr << std::endl;
 
   51   std::cerr << 
"[note: the -loader flag will produce .h/.cpp files to instantiate prototypes" << std::endl;
 
   52   std::cerr << 
"[note: the -swig flag will produce a .i file for swig include" << std::endl;
 
   53   std::cerr << 
"[note: the -flat flag circumvents an issue with SWIG pre 4.1.0]" << std::endl;
 
   62 int main(
int argc, 
char *argv[]) {
 
   72   for(; pos<argc; pos++) {
 
   73     std::string option(argv[pos]);
 
   75     if((option==
"-?") || (option==
"--help")) {
 
   80     if(option==
"-loader") {
 
   95     if(option==
"-merge") {
 
  100     if(option.c_str()[0]==
'-') {
 
  101       usage(
"unknown option "+ option);
 
  109   if(merge && (loader || swig)) {
 
  110     usage(
"mismatching options: either merge or code generation");
 
  112   if(!merge && !(loader || swig)) {
 
  113     usage(
"mismatching options: either merge or code generation");
 
  116     usage(
"mismatching options: flat is only applicable to swig");
 
  118   if(merge && (argc-pos <2)) {
 
  119     usage(
"mismatching agruments: to few files to merge");
 
  121   if(!merge && (argc-pos !=2)) {
 
  122     usage(
"mismatching agruments: need one source and one destination for code generation");
 
  128     for(; pos< argc-1; pos++) {
 
  133     if(std::string(argv[argc-1]) != 
"-") {
 
  145   std::ofstream rtiheader;
 
  146   std::ofstream rticode;
 
  147   std::ofstream swigheader;
 
  149     rtiheader.open((std::string(argv[pos])+
".h").c_str(), std::ios::out);
 
  150     rticode.open((std::string(argv[pos])+
".cpp").c_str(), std::ios::out);
 
  153     swigheader.open((std::string(argv[pos])+
".i").c_str(), std::ios::out);
 
  158     rtiheader << 
"/* rti2code: autogenerated libFAUDES rti registration: "; 
 
  160     rticode   << 
"/* rti2code: autogenerated libFAUDES rti registration: "; 
 
  164     swigheader << 
"/* rti2code: autogenerated libFAUDES swig bindings declarations: "; 
 
  170     rticode << 
"namespace faudes {" << std::endl;
 
  171     rticode << 
"/* Auto-register faudes types */" << std::endl;
 
  180       std::string ctype=tit->second->CType();
 
  181       std::string ftype=tit->second->Name();
 
  183       if(ctype==
"") 
continue;
 
  185       size_t pos=ctype.find(
"faudes::");
 
  186       if(pos!=std::string::npos) 
 
  187         ctype=ctype.substr(std::string(
"faudes::").length());
 
  189       if(!tit->second->AutoRegistered()) 
continue;
 
  191       std::cout << 
"rti2code: generating auto-registration code for \"" << ftype << 
"\"" << std::endl;
 
  193       std::string rtiname = std::string(
"gRti") + 
ToStringInteger(tcnt) + 
"Register" + ftype;
 
  194       rticode << 
"AutoRegisterType<" << ctype << 
"> " << rtiname << 
"(\"" << ftype <<
"\");";
 
  195       rticode << std::endl;
 
  197       if(tit->second->ElementTag()!=
"") {
 
  198         rtiname = std::string(
"gRti") + 
ToStringInteger(tcnt) + 
"ElementTag" + ftype;
 
  199         rticode << 
"AutoRegisterElementTag<" << ctype << 
"> " << rtiname << 
"(\"" << ftype << 
 
  200           "\", \"" << tit->second->ElementTag() << 
"\");";
 
  201         rticode << std::endl;
 
  204       if(tit->second->ElementType()!=
"") {
 
  205         rtiname = std::string(
"gRti") + 
ToStringInteger(tcnt) + 
"ElementType" + ftype;
 
  206         rticode << 
"AutoRegisterElementType<" << ctype << 
"> " << rtiname << 
"(\"" << ftype << 
 
  207           "\", \"" << tit->second->ElementType() << 
"\");";
 
  208         rticode << std::endl;
 
  215     rticode << 
"} // namespace" << std::endl;
 
  220     rtiheader << 
"namespace faudes {" << std::endl;
 
  221     rtiheader << 
"void LoadRegisteredTypes(void);" << std::endl;
 
  222     rtiheader << 
"} // namespace" << std::endl;
 
  227     rticode << 
"namespace faudes {" << std::endl;
 
  228     rticode << 
"/* Register faudes types */" << std::endl;
 
  229     rticode << 
"void LoadRegisteredTypes(void) {" << std::endl;
 
  237       std::string ctype=tit->second->CType();
 
  239       if(ctype==
"") 
continue;
 
  241       size_t pos=ctype.find(
"faudes::");
 
  242       if(pos!=std::string::npos) 
 
  243         ctype=ctype.substr(std::string(
"faudes::").length());
 
  245       std::cout << 
"rti2code: generating registration code for \"" << tit->second->Name() << 
"\"" << std::endl;
 
  247       rticode << 
"  TypeRegistry::G()->Insert<" << ctype << 
">(\"" << tit->second->Name() <<
"\");";
 
  248       rticode << std::endl;
 
  254     rticode << 
"}" << std::endl;
 
  255     rticode << 
"} // namespace" << std::endl;
 
  261     rtiheader << 
"namespace faudes {" << std::endl;
 
  262     rtiheader << 
"void LoadRegisteredFunctions(void);" << std::endl;
 
  263     rtiheader << 
"} // namespace" << std::endl;
 
  268     rticode << 
"namespace faudes {" << std::endl;
 
  269     rticode << 
"/* Register faudes functions */" << std::endl;
 
  270     rticode << 
"void LoadRegisteredFunctions(void) {" << std::endl;
 
  275     rtiheader << 
"namespace faudes {" << std::endl;
 
  285     std::string ctype=fdef->
CType();
 
  286     std::string fname = fdef->
Name();  
 
  288     if(ctype==
"") 
continue;
 
  290     size_t pos=ctype.find(
"faudes::");
 
  291     if(pos!=std::string::npos) 
 
  292       ctype=ctype.substr(std::string(
"faudes::").length());
 
  295       std::cout << 
"rti2cocde: function registration: " << fname << 
": no signatures" << std::endl;
 
  299     std::vector< std::vector<std::string> > cparams;
 
  300     std::vector< std::vector<Parameter::ParamAttr> > cattrib;
 
  301     std::vector< std::vector<bool> > cretval;
 
  309       for(
int j=0; j<sigi.
Size(); j++) {
 
  311         std::string ftype=sigi.
At(j).
Type();
 
  315         if(fcret) retcount++;
 
  327         if(retcount>1) 
break;
 
  329         size_t pos=ctype.find(
"faudes::");
 
  330         if(pos!=std::string::npos) 
 
  331           ctype=ctype.substr(std::string(
"faudes::").length());
 
  333         cparams.at(i).push_back(ctype);
 
  334         cattrib.at(i).push_back(fattr);
 
  335         cretval.at(i).push_back(fcret);
 
  338       if((
int) cparams.at(i).size()!=sigi.
Size()) {
 
  339         std::cout << 
"rti2code: function registration: " << fname << 
": cannot interpret signature "  
  340       << sigi.
Name() << std::endl;
 
  346     std::cout << 
"rti2code: generating rti wrapper for \"" << fdef->
Name() << 
"\"" << 
 
  347       " #" << cparams.size() << 
" variants" << std::endl;
 
  348     std::string rtiname = std::string(
"Rti") + 
ToStringInteger(fcnt) + ctype;
 
  351       rticode << 
"  FunctionRegistry::G()->Insert<" << rtiname << 
">(\"" << fname <<
"\");" << std::endl;
 
  355       rtiheader << 
"/* Function class for C++ function " << ctype << 
"*/" << std::endl;
 
  356       rtiheader << 
"class " << rtiname << 
" : public Function { " << std::endl;
 
  357       rtiheader << 
"public:" << std::endl;
 
  358       rtiheader << 
"  using Function::operator=;" << std::endl;
 
  359       rtiheader << rtiname << 
"(const FunctionDefinition* fdef) : Function(fdef) {};" << std::endl;
 
  360       rtiheader << 
"virtual Function* New(void) const { return new " << rtiname << 
"(pFuncDef); };" << std::endl;
 
  361       rtiheader << 
"protected:" << std::endl;
 
  365       for(
unsigned int i=0; i<cparams.size(); i++) 
 
  366         for(
unsigned int j=0; j<cparams.at(i).size(); j++) 
 
  367           rtiheader << cparams.at(i).at(j) << 
"* " << 
"mP_" << i << 
"_" << j << 
";" << std::endl;
 
  371       rtiheader << 
"virtual bool DoTypeCheck(int n) {" << std::endl;
 
  372       rtiheader << 
"  bool res=false;" << std::endl;
 
  373       rtiheader << 
"  switch(mVariantIndex) { "<< std::endl;
 
  374       for(
unsigned int i=0; i<cparams.size(); i++) {
 
  375         rtiheader << 
"  case " << i << 
": { // variant " << fdef->
Variant(i).
Name() << std::endl;
 
  376         rtiheader << 
"    switch(n) { "<< std::endl;
 
  377         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  378           rtiheader << 
"    case " << j << 
": ";
 
  379           rtiheader << 
"    res=DoTypeCast<" << cparams.at(i).at(j) << 
">(" << j << 
", mP_" << i <<
"_" << j << 
"); ";
 
  380           rtiheader << 
"break; "<< std::endl;
 
  382         rtiheader << 
"    default: break; " << std::endl;
 
  383         rtiheader << 
"    } "<< std::endl;
 
  384         rtiheader << 
"    break; "<< std::endl;
 
  385         rtiheader << 
"  } "<< std::endl;
 
  387       rtiheader << 
"  default: break; " << std::endl;
 
  388       rtiheader << 
"  } "<< std::endl;
 
  389       rtiheader << 
"  return res;" << std::endl;
 
  390       rtiheader << 
"};" << std::endl;
 
  394       rtiheader << 
"virtual void DoExecute(void) {" << std::endl;
 
  398       rtiheader << 
"  switch(mVariantIndex) { "<< std::endl;
 
  399       for(
unsigned int i=0; i<cparams.size(); i++) {
 
  400         rtiheader << 
"  case " << i << 
": { // variant " << fdef->
Variant(i).
Name() << std::endl;
 
  403         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  404           if(!cretval.at(i).at(j)) 
continue;
 
  406           if(cparams.at(i).at(j) == 
"Integer") {
 
  407             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference()) = ";
 
  410       if(cparams.at(i).at(j) == 
"Boolean") {
 
  411             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference()) = ";
 
  414           if(cparams.at(i).at(j) == 
"String") {
 
  415             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference()) = ";
 
  418       rtiheader << 
"*mP_" << i << 
"_" << j  << 
" = ";
 
  421         rtiheader << ctype <<
"(";
 
  424         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  425           if(cretval.at(i).at(j)) 
continue;
 
  426           if((parpos++)!=0) rtiheader << 
" ,";
 
  428           if(cparams.at(i).at(j) == 
"Integer") {
 
  429             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference())";
 
  432             if(cparams.at(i).at(j) == 
"Boolean") {
 
  433             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference())";
 
  436           if(cparams.at(i).at(j) == 
"String") {
 
  437             rtiheader << 
"*(mP_" << i << 
"_" << j << 
"->CReference())";
 
  440             rtiheader << 
"*mP_" << i << 
"_" << j;
 
  442         rtiheader << 
"); break; };" << std::endl;
 
  445       rtiheader << 
"  default: break; " << std::endl;
 
  446       rtiheader << 
"  }; "<< std::endl;
 
  448       rtiheader << 
"}; "<< std::endl;
 
  450       rtiheader << 
"};"  << std::endl;
 
  455       swigheader << 
"/* faudes-function \"" << fname << 
"\" */" << std::endl;
 
  460         std::string plugin=fdef->
PlugIn();
 
  461         swigheader << 
"#if " << 
"( SwigModule == \"Swig" << plugin << 
"\")";
 
  463         swigheader << std::endl;
 
  469         swigheader << 
"%rename(" << fname << 
") " << ctype << 
";" << std::endl;
 
  474       std::vector< std::string > lfdefs;
 
  475       std::vector< std::string > lrtypes;
 
  476       std::vector< std::string > lhelp;
 
  478       for(
unsigned int i=0; i<cparams.size(); i++) {
 
  480         std::string lrtype=
"void";
 
  481         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  482           if(!cretval.at(i).at(j)) 
continue;
 
  484           if(cparams.at(i).at(j) == 
"Integer") {
 
  488       if(cparams.at(i).at(j) == 
"Boolean") {
 
  492           if(cparams.at(i).at(j) == 
"String") {
 
  493             lrtype=
"std::string";
 
  496     lrtype = cparams.at(i).at(j);
 
  500         lrtypes.push_back(lrtype);
 
  502         std::string lfdef = ctype + 
"(";
 
  505         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  506           if(cretval.at(i).at(j)) 
continue;
 
  507           if((parpos++)!=0) lfdef += 
", ";
 
  512           if(cparams.at(i).at(j) == 
"Integer") {
 
  513             lfdef += 
"long int&";
 
  516     if(cparams.at(i).at(j) == 
"Boolean") {
 
  520           if(cparams.at(i).at(j) == 
"String") {
 
  521             lfdef += 
"std::string&";
 
  524         lfdef += cparams.at(i).at(j) + 
"&";
 
  526           if(cparams.at(i).at(j) == 
"Boolean" || cparams.at(i).at(j) == 
"String"  
  527              || cparams.at(i).at(j) == 
"Integer")
 
  533         lfdefs.push_back(lfdef);
 
  535         std::string luasig = 
" " + fname + 
"(";
 
  536         bool leftcomma = 
false;
 
  537         bool rightcomma = 
false;
 
  538         for(
unsigned int j=0; j<cparams.at(i).size(); j++) {
 
  540           if(cparams.at(i).at(j) == 
"Boolean" || cparams.at(i).at(j) == 
"String"  
  541              || cparams.at(i).at(j) == 
"Integer")
 
  543             if(leftcomma) luasig = 
"," + luasig;
 
  545       luasig=cparams.at(i).at(j) + luasig;
 
  550           if(rightcomma) luasig += 
", ";
 
  552     luasig += sigi.
At(j).
Str();
 
  558           std::string topic= fdef->
PlugIn();
 
  560           if(topic==
"CoreFaudes") {
 
  564           if(topic.length()>0) topic.at(0)=toupper(topic.at(0));
 
  565           if(key1.length()>0) key1.at(0)=toupper(key1.at(0));
 
  566           lhelp.push_back(
"SwigHelpEntry(\"" + topic + 
"\", \"" + key1 + 
"\", \"" +
 
  573       for(
unsigned int i=1; i<lfdefs.size();i++) {
 
  576       if(lfdefs.at(i)==lfdefs.at(j)) 
break;
 
  579         if(lrtypes.at(j)==
"void") 
 
  580           {lfdefs[j]=
""; 
continue;}  
 
  581         if(lrtypes.at(i)==
"void") 
 
  582           {lfdefs[i]=
""; 
continue;}  
 
  587       for(
unsigned int i=0; i<lfdefs.size(); i++) {
 
  588         if(lfdefs.at(i)==
"") 
continue;
 
  589         swigheader << lrtypes.at(i) << 
" " << lfdefs.at(i) << 
";" << std::endl;
 
  591         if(lhelp.at(i)==
"") 
continue; 
 
  592         swigheader << lhelp.at(i) << 
";" << std::endl;
 
  594       std::cout << 
"rti2code: generating swig interface for function \"" << fdef->
Name() << 
"\"" << 
 
  595       " #" << lcount << 
" variants" << std::endl;
 
  599         swigheader << 
"#endif " << std::endl;
 
  601       swigheader << std::endl;
 
  609     rtiheader << 
"} // namespace" << std::endl;
 
  614     rticode << 
"}" << std::endl;
 
  615     rticode << 
"} // namespace" << std::endl;
 
const std::string & Name(void) const
 
std::string KeywordAt(int pos) const
 
const std::string & PlugIn(void) const
 
const std::string & TextDoc(void) const
 
const std::string & CType(void) const
 
const Signature & Variant(const std::string &rName) const
 
int VariantsSize(void) const
 
static FunctionRegistry * G()
 
std::map< std::string, FunctionDefinition * >::const_iterator Iterator
 
void MergeDocumentation(TokenReader &rTr)
 
Iterator Begin(void) const
 
std::string Str(void) const
 
const std::string & Type(void) const
 
const ParamAttr & Attribute(void) const
 
const std::string & Name(void) const
 
const Parameter & At(int n) const
 
void MergeDocumentation(TokenReader &rTr)
 
const TypeDefinition & Definition(const std::string &rTypeName) const
 
static TypeRegistry * G()
 
bool Exists(const std::string &rName) const
 
std::map< std::string, TypeDefinition * >::const_iterator Iterator
 
void SaveRegistry(const std::string &rPath)
 
void LoadRegistry(const std::string &rPath)
 
std::string VersionString()
 
std::string PluginsString()
 
std::string ToStringInteger(Int number)
 
int main(int argc, char *argv[])
 
void usage(const std::string &rMessage="")