LCOV - code coverage report
Current view: top level - oksdalgen/apps - utils.cpp (source / functions) Coverage Total Hit
Test: code.result Lines: 0.0 % 292 0
Test Date: 2025-12-21 13:07:08 Functions: 0.0 % 26 0

            Line data    Source code
       1              : 
       2              : #include "class_info.hpp"
       3              : 
       4              : #include "oks/kernel.hpp"
       5              : #include "oks/method.hpp"
       6              : 
       7              : #include <ctype.h>
       8              : 
       9              : #include <algorithm>
      10              : #include <ctime>
      11              : #include <initializer_list>
      12              : #include <iomanip>
      13              : #include <iostream>
      14              : 
      15              : 
      16              : using namespace dunedaq::oks;
      17              : using namespace dunedaq::oksdalgen;
      18              : 
      19              :   /**
      20              :    *  The functions cvt_symbol() and alnum_name() are used
      21              :    *  to replace all symbols allowed in names of classes, attributes
      22              :    *  and relationships, but misinterpreted by c++.
      23              :    */
      24              : 
      25              : char
      26            0 : cvt_symbol(char c)
      27              : {
      28            0 :   return (isalnum(c) ? c : '_');
      29              : }
      30              : 
      31              : std::string
      32            0 : alnum_name(const std::string& in)
      33              : {
      34            0 :   std::string s(in);
      35            0 :   std::transform(s.begin(), s.end(), s.begin(), cvt_symbol);
      36            0 :   return s;
      37            0 : }
      38              : 
      39              : std::string
      40            0 : capitalize_name(const std::string& in)
      41              : {
      42            0 :   std::string s(in);
      43            0 :   if (!in.empty())
      44              :     {
      45            0 :       if (isalpha(in[0]))
      46              :         {
      47            0 :           if (islower(in[0]))
      48            0 :             s[0] = toupper(in[0]);
      49              :         }
      50              :       else
      51              :         {
      52            0 :           s.insert(s.begin(), '_');
      53              :         }
      54              :     }
      55            0 :   return s;
      56            0 : }
      57              : 
      58              : 
      59              :   /**
      60              :    *  The function print_description() is used for printing of the
      61              :    *  multi-line text with right alignment.
      62              :    */
      63              : 
      64              : void
      65            0 : print_description(std::ostream& s, const std::string& text, const char * dx)
      66              : {
      67            0 :   if (!text.empty())
      68              :     {
      69            0 :       s << dx << " /**\n";
      70              : 
      71            0 :       Oks::Tokenizer t(text, "\n");
      72            0 :       std::string token;
      73              : 
      74            0 :       while (!(token = t.next()).empty())
      75              :         {
      76            0 :           s << dx << "  *  " << token << std::endl;
      77              :         }
      78              : 
      79            0 :       s << dx << "  */\n\n";
      80            0 :     }
      81            0 : }
      82              : 
      83              : void
      84            0 : print_indented(std::ostream& s, const std::string& text, const char * dx)
      85              : {
      86            0 :   if (!text.empty())
      87              :     {
      88            0 :       Oks::Tokenizer t(text, "\n");
      89            0 :       std::string token;
      90              : 
      91            0 :       while (!(token = t.next()).empty())
      92              :         {
      93            0 :           s << dx << token << std::endl;
      94              :         }
      95            0 :     }
      96            0 : }
      97              : 
      98              : std::string
      99            0 : get_type(OksData::Type oks_type, bool is_cpp)
     100              : {
     101            0 :   switch (oks_type)
     102              :     {
     103            0 :       case OksData::unknown_type:
     104            0 :         return "UNKNOWN";
     105            0 :       case OksData::s8_int_type:
     106            0 :         return (is_cpp ? "int8_t" : "char");
     107            0 :       case OksData::u8_int_type:
     108            0 :         return (is_cpp ? "uint8_t" : "byte");
     109            0 :       case OksData::s16_int_type:
     110            0 :         return (is_cpp ? "int16_t" : "short");
     111            0 :       case OksData::u16_int_type:
     112            0 :         return (is_cpp ? "uint16_t" : "short");
     113            0 :       case OksData::s32_int_type:
     114            0 :         return (is_cpp ? "int32_t" : "int");
     115            0 :       case OksData::u32_int_type:
     116            0 :         return (is_cpp ? "uint32_t" : "int");
     117            0 :       case OksData::s64_int_type:
     118            0 :         return (is_cpp ? "int64_t" : "long");
     119            0 :       case OksData::u64_int_type:
     120            0 :         return (is_cpp ? "uint64_t" : "long");
     121            0 :       case OksData::float_type:
     122            0 :         return "float";
     123            0 :       case OksData::double_type:
     124            0 :         return "double";
     125            0 :       case OksData::bool_type:
     126            0 :         return (is_cpp ? "bool" : "boolean");
     127              : 
     128            0 :       case OksData::string_type:
     129            0 :       case OksData::enum_type:
     130            0 :       case OksData::date_type:
     131            0 :       case OksData::time_type:
     132            0 :       case OksData::class_type:
     133            0 :         return (is_cpp ? "std::string" : "String");
     134              : 
     135            0 :       case OksData::object_type:
     136            0 :       case OksData::list_type:
     137            0 :       case OksData::uid_type:
     138            0 :       case OksData::uid2_type:
     139            0 :         return "funnytype";
     140              :     }
     141              : 
     142            0 :   return "invalid";
     143              : }
     144              : 
     145              : // std::string
     146              : // get_java_impl_name(const std::string& s)
     147              : // {
     148              : //   std::string str(s);
     149              : //   str += "_Impl";
     150              : //   return str;
     151              : // }
     152              : 
     153              : // std::string
     154              : // get_java_helper_name(const std::string& s)
     155              : // {
     156              : //   std::string str(s);
     157              : //   str += "_Helper";
     158              : //   return str;
     159              : // }
     160              : 
     161              : void
     162            0 : gen_dump_application(std::ostream& s,
     163              :                      std::list<std::string>& class_names,
     164              :                      const std::string& cpp_ns_name,
     165              :                      const std::string& cpp_hdr_dir,
     166              :                      const char * conf_header,
     167              :                      const char * conf_name,
     168              :                      const char * headres_prologue,
     169              :                      const char * main_function_prologue
     170              :                      )
     171              : {
     172            0 :   s <<
     173              :     "  // *** this file is generated by oksdalgen ***\n"
     174              :     "\n"
     175              :     "#include \"conffwk/ConfigObject.hpp\"\n"
     176            0 :     "#include \"" << conf_header << "\"\n\n";
     177              : 
     178              :   // generate list of includes
     179            0 :   for (const auto& i : class_names)
     180              :     {
     181            0 :       std::string hname(cpp_hdr_dir);
     182            0 :       if (!hname.empty())
     183            0 :         hname += '/';
     184            0 :       hname += i;
     185            0 :       s << "#include \"" << hname << ".hpp\"\n";
     186            0 :     }
     187              : 
     188            0 :   if (headres_prologue && *headres_prologue)
     189              :     {
     190            0 :       s << "\n  // db implementation-specific headrers prologue\n\n" << headres_prologue << "\n";
     191              :     }
     192              : 
     193            0 :   s <<
     194              :       "\n"
     195              :       "\n"
     196              :       "static void usage(const char * s)\n"
     197              :       "{\n"
     198              :       "  std::cout << s << \" -d db-name -c class-name [-q query | -i object-id] [-t]\\n\"\n"
     199              :       "    \"\\n\"\n"
     200              :       "    \"Options/Arguments:\\n\"\n"
     201              :       "    \"  -d | --data db-name            mandatory name of the database\\n\"\n"
     202              :       "    \"  -c | --class-name class-name   mandatory name of class\\n\"\n"
     203              :       "    \"  -q | --query query             optional query to select class objects\\n\"\n"
     204              :       "    \"  -i | --object-id object-id     optional identity to select one object\\n\"\n"
     205              :       "    \"  -t | --init-children           all referenced objects are initialized (is used\\n\"\n"
     206              :       "    \"                                 for debug purposes and performance measurements)\\n\"\n"
     207              :       "    \"  -h | --help                    print this message\\n\"\n"
     208              :       "    \"\\n\"\n"
     209              :       "    \"Description:\\n\"\n"
     210              :       "    \"  The program prints out object(s) of given class.\\n\"\n"
     211              :       "    \"  If no query or object id is provided, all objects of the class are printed.\\n\"\n"
     212              :       "    \"  It is automatically generated by oksdalgen utility.\\n\"\n"
     213              :       "    \"\\n\";\n"
     214              :       "}\n"
     215              :       "\n"
     216              :       "static void no_param(const char * s)\n"
     217              :       "{\n"
     218              :       "  std::cerr << \"ERROR: the required argument for option \\\'\" << s << \"\\\' is missing\\n\\n\";\n"
     219              :       "  exit (EXIT_FAILURE);\n"
     220              :       "}\n"
     221              :       "\n"
     222              :       "int main(int argc, char *argv[])\n"
     223            0 :       "{\n";
     224              : 
     225            0 :   if (main_function_prologue && *main_function_prologue)
     226              :     {
     227            0 :       s << "    // db implementation-specific main function prologue\n\n  " << main_function_prologue << "\n\n";
     228              :     }
     229              : 
     230            0 :   s <<
     231              :       "    // parse parameters\n"
     232              :       "\n"
     233              :       "  const char * db_name = nullptr;\n"
     234              :       "  const char * object_id = nullptr;\n"
     235              :       "  const char * query = \"\";\n"
     236              :       "  std::string class_name;\n"
     237              :       "  bool init_children = false;\n"
     238              :       "\n"
     239              :       "  for(int i = 1; i < argc; i++) {\n"
     240              :       "    const char * cp = argv[i];\n"
     241              :       "    if(!strcmp(cp, \"-h\") || !strcmp(cp, \"--help\")) {\n"
     242              :       "      usage(argv[0]);\n"
     243              :       "      return 0;\n"
     244              :       "    }\n"
     245              :       "    if(!strcmp(cp, \"-t\") || !strcmp(cp, \"--init-children\")) {\n"
     246              :       "      init_children = true;\n"
     247              :       "    }\n"
     248              :       "    else if(!strcmp(cp, \"-d\") || !strcmp(cp, \"--data\")) {\n"
     249              :       "      if(++i == argc || argv[i][0] == '-') { no_param(cp); } else { db_name = argv[i]; }\n"
     250              :       "    }\n"
     251              :       "    else if(!strcmp(cp, \"-c\") || !strcmp(cp, \"--class-name\")) {\n"
     252              :       "      if(++i == argc || argv[i][0] == '-') { no_param(cp); } else { class_name = argv[i]; }\n"
     253              :       "    }\n"
     254              :       "    else if(!strcmp(cp, \"-i\") || !strcmp(cp, \"--object-id\")) {\n"
     255              :       "      if(++i == argc || argv[i][0] == '-') { no_param(cp); } else { object_id = argv[i]; }\n"
     256              :       "    }\n"
     257              :       "    else if(!strcmp(cp, \"-q\") || !strcmp(cp, \"--query\")) {\n"
     258              :       "      if(++i == argc || argv[i][0] == '-') { no_param(cp); } else { query = argv[i]; }\n"
     259              :       "    }\n"
     260              :       "    else {\n"
     261              :       "      std::cerr << \"ERROR: bad parameter \" << cp << std::endl;\n"
     262              :       "      usage(argv[0]);\n"
     263              :       "      return (EXIT_FAILURE);\n"
     264              :       "    }\n"
     265              :       "  }\n"
     266              :       "\n"
     267              :       "  if(db_name == nullptr) {\n"
     268              :       "    std::cerr << \"ERROR: no database name provided\\n\";\n"
     269              :       "    return (EXIT_FAILURE);\n"
     270              :       "  }\n"
     271              :       "\n"
     272              :       "  if(class_name.empty()) {\n"
     273              :       "    std::cerr << \"ERROR: no class name provided\\n\";\n"
     274              :       "    return (EXIT_FAILURE);\n"
     275              :       "  }\n"
     276              :       "\n"
     277              :       "  if(*query != 0 && object_id != nullptr) {\n"
     278              :       "    std::cerr << \"ERROR: only one parameter -i or -q can be provided\\n\";\n"
     279              :       "    return (EXIT_FAILURE);\n"
     280              :       "  }\n"
     281              :       "\n"
     282              :       "\n"
     283              :       "std::cout << std::boolalpha;\n"
     284            0 :       "\n";
     285              : 
     286            0 :   if (conf_name)
     287              :     {
     288            0 :       s <<
     289              :           "  " << conf_name << " impl_conf;\n"
     290              :           "\n"
     291              :           "  {\n"
     292            0 :           "    dunedaq::conffwk::Configuration conf(db_name, &impl_conf);\n";
     293              :     }
     294              :   else
     295              :     {
     296            0 :       s <<
     297              :           "  try {\n"
     298            0 :           "    dunedaq::conffwk::Configuration conf(db_name);\n";
     299              :     }
     300              : 
     301            0 :   s <<
     302              :       "\n"
     303              :       "    if(!conf.loaded()) {\n"
     304              :       "      std::cerr << \"Can not load database: \" << db_name << std::endl;\n"
     305              :       "      return (EXIT_FAILURE);\n"
     306              :       "    }\n"
     307              :       "    \n"
     308              :       "    std::vector< dunedaq::conffwk::ConfigObject > objects;\n"
     309              :       "    \n"
     310              :       "    if(object_id) {\n"
     311              :       "      dunedaq::conffwk::ConfigObject obj;\n"
     312              :       "      try {\n"
     313              :       "        conf.get(class_name, object_id, obj, 1);\n"
     314              :       "      }\n"
     315              :       "      catch (dunedaq::conffwk::NotFound & ex) {\n"
     316              :       "        std::cerr << \"Can not get object \\'\" << object_id << \"\\' of class \\'\" << class_name << \"\\':\\n\" << ex << std::endl;\n"
     317              :       "        return (EXIT_FAILURE);\n"
     318              :       "      }\n"
     319              :       "      objects.push_back(obj);\n"
     320              :       "    }\n"
     321              :       "    else {\n"
     322              :       "      try {\n"
     323              :       "        conf.get(class_name, objects, query, 1);\n"
     324              :       "      }\n"
     325              :       "      catch (dunedaq::conffwk::NotFound & ex) {\n"
     326              :       "        std::cerr << \"Can not get objects of class \\'\" << class_name << \"\\':\\n\" << ex << std::endl;\n"
     327              :       "        return (EXIT_FAILURE);\n"
     328              :       "      }\n"
     329              :       "    }\n"
     330              :       "    \n"
     331              :       "    struct SortByUId {\n"
     332              :       "      bool operator() (const dunedaq::conffwk::ConfigObject * o1, const dunedaq::conffwk::ConfigObject * o2) const {\n"
     333              :       "        return (o1->UID() < o2->UID());\n"
     334              :       "      };\n"
     335              :       "    };\n"
     336              :       "    \n"
     337              :       "    std::set< dunedaq::conffwk::ConfigObject *, SortByUId > sorted_objects;\n"
     338              :       "    \n"
     339              :       "    for(auto& i : objects)\n"
     340              :       "      sorted_objects.insert(&i);\n"
     341              :       "    \n"
     342            0 :       "    for(auto& i : sorted_objects) {\n";
     343              : 
     344            0 :   for (std::list<std::string>::iterator i = class_names.begin(); i != class_names.end(); ++i)
     345              :     {
     346            0 :       const char * op = (i == class_names.begin() ? "if" : "else if");
     347            0 :       std::string cname(cpp_ns_name);
     348              : 
     349            0 :       if (!cname.empty())
     350            0 :         cname += "::";
     351              : 
     352            0 :       cname += *i;
     353              : 
     354            0 :       s <<
     355              :           "      " << op << "(class_name == \"" << *i << "\") {\n"
     356              :           "        std::cout << *conf.get<" << cname << ">(*i, init_children) << std::endl;\n"
     357            0 :           "      }\n";
     358            0 :     }
     359              : 
     360            0 :   s <<
     361              :       "      else {\n"
     362              :       "        std::cerr << \"ERROR: do not know how to dump object of \" << class_name << \" class\\n\";\n"
     363              :       "        return (EXIT_FAILURE);\n"
     364              :       "      }\n"
     365              :       "    }\n"
     366              :       "  }\n"
     367              :       "  catch (dunedaq::conffwk::Exception & ex) {\n"
     368              :       "    std::cerr << \"Caught \" << ex << std::endl;\n"
     369              :       "    return (EXIT_FAILURE);\n"
     370              :       "  }\n"
     371              :       "\n"
     372              :       "  return 0;\n"
     373            0 :       "}\n";
     374            0 : }
     375              : 
     376              : 
     377              : void
     378            0 : write_info_file(std::ostream& s,
     379              :                 const std::string& cpp_namespace,
     380              :                 const std::string& cpp_header_dir,
     381              :                 // const std::string& java_pname,
     382              :                 const std::set<const OksClass *, std::less<const OksClass *> >& classes)
     383              : {
     384            0 :   std::time_t now = std::time(nullptr);
     385              : 
     386            0 :   s << "// the file is generated " << std::put_time(std::localtime(&now), "%F %T %Z") << " by oksdalgen utility\n"
     387              :       "// *** do not modify the file ***\n"
     388              :       "c++-namespace=" << cpp_namespace << "\n"
     389              :       "c++-header-dir-prefix=" << cpp_header_dir << "\n"
     390              :       // "java-package-name=" << java_pname << "\n"
     391            0 :       "classes:\n";
     392              : 
     393            0 :   for (const auto& i : classes)
     394            0 :     s << "  " << i->get_name() << std::endl;
     395            0 : }
     396              : 
     397              : 
     398              :   /**
     399              :    *  The function get_full_cpp_class_name() returns name of class
     400              :    *  with it's namespace (e.g. "NAMESPACE_A::CLASS_X")
     401              :    */
     402              : 
     403              : std::string
     404            0 : get_full_cpp_class_name(const OksClass * c, const ClassInfo::Map& cl_info, const std::string & cpp_ns_name)
     405              : {
     406            0 :   std::string s;
     407            0 :   ClassInfo::Map::const_iterator idx = cl_info.find(c);
     408              : 
     409            0 :   if (idx != cl_info.end())
     410            0 :     s = (*idx).second.get_namespace();
     411              :   else
     412            0 :     s = cpp_ns_name;
     413              : 
     414            0 :   if (!s.empty())
     415            0 :     s += "::";
     416              : 
     417            0 :   s += alnum_name(c->get_name());
     418              : 
     419            0 :   return s;
     420            0 : }
     421              : 
     422              : 
     423              : std::string
     424            0 : get_include_dir(const OksClass * c, const ClassInfo::Map& cl_info, const std::string& cpp_hdr_dir)
     425              : {
     426            0 :   std::string s;
     427              : 
     428            0 :   ClassInfo::Map::const_iterator idx = cl_info.find(c);
     429              : 
     430            0 :   if (idx != cl_info.end())
     431              :     {
     432            0 :       const std::string include_prefix = (*idx).second.get_include_prefix();
     433            0 :       if (!include_prefix.empty())
     434              :         {
     435            0 :           s = include_prefix;
     436            0 :           s += '/';
     437              :         }
     438            0 :     }
     439            0 :   else if (!cpp_hdr_dir.empty())
     440              :     {
     441            0 :       s = cpp_hdr_dir;
     442            0 :       s += '/';
     443              :     }
     444              : 
     445            0 :   s += alnum_name(c->get_name());
     446              : 
     447            0 :   return s;
     448            0 : }
     449              : 
     450              : 
     451              : // const std::string&
     452              : // get_package_name(const OksClass * c, const ClassInfo::Map& cl_info, const std::string& java_p_name)
     453              : // {
     454              : //   std::string s;
     455              : 
     456              : //   ClassInfo::Map::const_iterator idx = cl_info.find(c);
     457              : 
     458              : //   if (idx != cl_info.end())
     459              : //     {
     460              : //       return (*idx).second.get_package_name();
     461              : //     }
     462              : //   else
     463              : //     {
     464              : //       return java_p_name;
     465              : //     }
     466              : // }
     467              : 
     468              : bool
     469            0 : process_external_class(
     470              :   ClassInfo::Map& cl_info,
     471              :   const OksClass * c,
     472              :   const std::list<std::string>& include_dirs,
     473              :   const std::list<std::string>& user_classes,
     474              :   bool verbose)
     475              : {
     476            0 :   if (cl_info.find(c) != cl_info.end())
     477              :     return true;
     478              : 
     479              :   // process list of user-defined classes first
     480              : 
     481            0 :   for (const auto &s : user_classes)
     482              :     {
     483            0 :       std::string::size_type idx = s.find("::");
     484            0 :       std::string::size_type idx2 = s.find("@", idx + 2);
     485              : 
     486            0 :       std::string cpp_ns_name;
     487            0 :       std::string class_name;
     488            0 :       std::string cpp_dir_name;
     489              : 
     490            0 :       if (idx == std::string::npos)
     491              :         {
     492            0 :           class_name = s.substr(0, idx2);
     493              :         }
     494              :       else
     495              :         {
     496            0 :           cpp_ns_name = s.substr(0, idx);
     497            0 :           class_name = s.substr(idx + 2, idx2 - idx - 2);
     498              :         }
     499              : 
     500            0 :       if (idx2 != std::string::npos)
     501            0 :         cpp_dir_name = s.substr(idx2 + 1);
     502              : 
     503            0 :       if (class_name == c->get_name())
     504              :         {
     505            0 :           cl_info[c] = ClassInfo(cpp_ns_name, cpp_dir_name);
     506            0 :           if (verbose)
     507              :             {
     508            0 :               std::cout << " * class " << c->get_name() << " is defined by user in ";
     509              : 
     510            0 :               if (cpp_ns_name.empty())
     511            0 :                 std::cout << "global namespace";
     512              :               else
     513            0 :                 std::cout << "namespace \"" << cpp_ns_name << '\"';
     514              : 
     515            0 :               if (!cpp_dir_name.empty())
     516            0 :                 std::cout << " with \"" << cpp_dir_name << "\" include prefix";
     517              : 
     518            0 :               std::cout << std::endl;
     519              :             }
     520              : 
     521            0 :           return true;
     522              :         }
     523            0 :     }
     524              : 
     525              :   // process oksdalgen files
     526              : 
     527            0 :   if (verbose)
     528            0 :     std::cout << "Looking for oksdalgen info files ...\n";
     529              : 
     530            0 :   bool found_class_declaration = false;
     531              : 
     532            0 :   for (const auto& i : include_dirs)
     533              :     {
     534            0 :       std::string file_name(i);
     535            0 :       file_name += "/oksdalgen.info";
     536              : 
     537            0 :       std::ifstream f(file_name.c_str());
     538              : 
     539            0 :       if (f)
     540              :         {
     541            0 :           if (verbose)
     542            0 :             std::cout << " *** found file \"" << file_name << "\" ***\n";
     543              : 
     544            0 :           std::string cpp_ns_name;
     545            0 :           std::string cpp_dir_name;
     546              :           // std::string java_pname;
     547            0 :           bool is_class = false;
     548              : 
     549            0 :           std::string s;
     550            0 :           while (std::getline(f, s))
     551              :             {
     552            0 :               if (s.find("//") != std::string::npos)
     553              :                 {
     554            0 :                   if (verbose)
     555            0 :                     std::cout << " - skip comment \"" << s << "\"\n";
     556              :                 }
     557            0 :               else if (s.find("classes:") != std::string::npos)
     558              :                 {
     559            0 :                   if (verbose)
     560            0 :                     std::cout << " - found classes keyword\n";
     561              :                   is_class = true;
     562              :                 }
     563              :               else
     564              :                 {
     565            0 :                   const char s1[] = "c++-namespace=";
     566            0 :                   std::string::size_type idx = s.find(s1);
     567            0 :                   if (idx != std::string::npos)
     568              :                     {
     569            0 :                       cpp_ns_name = s.substr(sizeof(s1) - 1);
     570            0 :                       if (verbose)
     571            0 :                         std::cout << " - c++ namespace = \"" << cpp_ns_name << "\"\n";
     572              :                     }
     573              :                   else
     574              :                     {
     575            0 :                       const char s2[] = "c++-header-dir-prefix=";
     576            0 :                       std::string::size_type idx = s.find(s2);
     577            0 :                       if (idx != std::string::npos)
     578              :                         {
     579            0 :                           cpp_dir_name = s.substr(sizeof(s2) - 1);
     580            0 :                           if (verbose)
     581            0 :                             std::cout << " - c++ header dir prefix name = \"" << cpp_dir_name << "\"\n";
     582              :                         }
     583              :                       // else
     584              :                         // {
     585              :                         //   const char s3[] = "java-package-name=";
     586              :                         //   std::string::size_type idx = s.find(s3);
     587              :                         //   if (idx != std::string::npos)
     588              :                         //     {
     589              :                         //       java_pname = s.substr(sizeof(s3) - 1);
     590              :                         //       if (verbose)
     591              :                         //         std::cout << " - java package name = \"" << java_pname << "\"\n";
     592              :                         //     }
     593            0 :                           else if (is_class)
     594              :                             {
     595            0 :                               std::string cname = s.substr(2);
     596            0 :                               OksClass * cl = c->get_kernel()->find_class(cname);
     597            0 :                               if (cl && cl_info.find(cl) == cl_info.end())
     598              :                                 {
     599            0 :                                   cl_info[cl] = ClassInfo(cpp_ns_name, cpp_dir_name);
     600            0 :                                   if (verbose)
     601            0 :                                     std::cout << " * class " << cl->get_name() << " is defined by " << file_name << " in namespace \"" << cpp_ns_name << "\" with include prefix \"" << cpp_dir_name << "\"\n";
     602            0 :                                   if (cl == c)
     603            0 :                                     found_class_declaration = true;
     604              :                                 }
     605            0 :                               else if (verbose)
     606              :                                 {
     607            0 :                                   std::cout << " - skip class \"" << cname << "\" declaration\n";
     608              :                                 }
     609            0 :                             }
     610              :                           else
     611              :                             {
     612            0 :                               std::cerr << "Failed to parse line \"" << s << "\"\n";
     613              :                             }
     614              :                         // }
     615              :                     }
     616              :                 }
     617              :             }
     618            0 :         }
     619            0 :       else if (verbose)
     620              :         {
     621            0 :           std::cout << " *** file \"" << file_name << "\" does not exist ***\n";
     622              :         }
     623            0 :     }
     624              : 
     625            0 :   return found_class_declaration;
     626              : }
     627              : 
     628              : std::string
     629            0 : int2dx(int level)
     630              : {
     631            0 :   return std::string(level * 2, ' ');
     632              : }
     633              : 
     634              : int
     635            0 : open_cpp_namespace(std::ostream& s, const std::string& value)
     636              : {
     637            0 :   int level = 0;
     638            0 :   std::string dx;
     639              : 
     640            0 :   if (!value.empty())
     641              :     {
     642            0 :       Oks::Tokenizer t(value, ":");
     643            0 :       std::string token;
     644              : 
     645            0 :       while (!(token = t.next()).empty())
     646              :         {
     647            0 :           s << dx << "namespace " << token << " {\n";
     648            0 :           level++;
     649            0 :           dx += "  ";
     650              :         }
     651            0 :     }
     652              : 
     653            0 :   return level;
     654            0 : }
     655              : 
     656              : void
     657            0 : close_cpp_namespace(std::ostream& s, int level)
     658              : {
     659            0 :   while (level > 0)
     660              :     {
     661            0 :       std::string dx = int2dx(--level);
     662            0 :       s << dx << "}\n";
     663            0 :     }
     664            0 : }
     665              : 
     666              : 
     667              : 
     668              : const std::string begin_header_prologue("BEGIN_HEADER_PROLOGUE");
     669              : const std::string end_header_prologue("END_HEADER_PROLOGUE");
     670              : const std::string begin_header_epilogue("BEGIN_HEADER_EPILOGUE");
     671              : const std::string end_header_epilogue("END_HEADER_EPILOGUE");
     672              : const std::string begin_public_section("BEGIN_PUBLIC_SECTION"); // => java interface
     673              : const std::string end_public_section("END_PUBLIC_SECTION");
     674              : const std::string begin_private_section("BEGIN_PRIVATE_SECTION"); // => c++ and java
     675              : const std::string end_private_section("END_PRIVATE_SECTION");
     676              : const std::string begin_member_initializer_list("BEGIN_MEMBER_INITIALIZER_LIST");
     677              : const std::string end_member_initializer_list("END_MEMBER_INITIALIZER_LIST");
     678              : const std::string has_add_algo_1("ADD_ALGO_1");
     679              : const std::string has_add_algo_n("ADD_ALGO_N");
     680              : 
     681              : static std::string
     682            0 : get_method_header_x_logue(OksMethodImplementation * mi, const std::string& begin, const std::string& end)
     683              : {
     684            0 :   std::string::size_type begix_idx = mi->get_body().find(begin, 0);
     685            0 :   if (begix_idx == std::string::npos)
     686            0 :     return "";
     687            0 :   std::string::size_type end_idx = mi->get_body().find(end, begix_idx + begin.size());
     688            0 :   if (end_idx == std::string::npos)
     689            0 :     return "";
     690            0 :   return mi->get_body().substr(begix_idx + begin.size(), end_idx - begix_idx - begin.size());
     691              : }
     692              : 
     693              : std::string
     694            0 : get_method_header_prologue(OksMethodImplementation * mi)
     695              : {
     696            0 :   return get_method_header_x_logue(mi, begin_header_prologue, end_header_prologue);
     697              : }
     698              : 
     699              : std::string
     700            0 : get_method_header_epilogue(OksMethodImplementation * mi)
     701              : {
     702            0 :   return get_method_header_x_logue(mi, begin_header_epilogue, end_header_epilogue);
     703              : }
     704              : 
     705              : std::string
     706            0 : get_public_section(OksMethodImplementation * mi)
     707              : {
     708            0 :   return get_method_header_x_logue(mi, begin_public_section, end_public_section);
     709              : }
     710              : 
     711              : std::string
     712            0 : get_private_section(OksMethodImplementation * mi)
     713              : {
     714            0 :   return get_method_header_x_logue(mi, begin_private_section, end_private_section);
     715              : }
     716              : 
     717              : std::string
     718            0 : get_member_initializer_list(OksMethodImplementation * mi)
     719              : {
     720            0 :   return get_method_header_x_logue(mi, begin_member_initializer_list, end_member_initializer_list);
     721              : }
     722              : 
     723              : bool
     724            0 : get_add_algo_1(OksMethodImplementation * mi)
     725              : {
     726            0 :   return (mi->get_body().find(has_add_algo_1, 0) != std::string::npos);
     727              : }
     728              : 
     729              : bool
     730            0 : get_add_algo_n(OksMethodImplementation * mi)
     731              : {
     732            0 :   return (mi->get_body().find(has_add_algo_n, 0) != std::string::npos);
     733              : }
     734              : 
     735              : static void
     736            0 : remove_string_section(std::string& s, const std::string& begin, const std::string& end)
     737              : {
     738            0 :   std::string::size_type begix_idx = s.find(begin, 0);
     739            0 :   if (begix_idx == std::string::npos)
     740              :     return;
     741              : 
     742            0 :   std::string::size_type end_idx = (end.empty() ? (begix_idx + begin.size()) : s.find(end, begix_idx + begin.size()));
     743            0 :   if (end_idx == std::string::npos)
     744              :     return;
     745              : 
     746            0 :   end_idx += end.size();
     747            0 :   while (s[end_idx] == '\n')
     748            0 :     end_idx++;
     749              : 
     750            0 :   s.erase(begix_idx, end_idx - begix_idx);
     751              : }
     752              : 
     753              : std::string
     754            0 : get_method_implementation_body(OksMethodImplementation * mi)
     755              : {
     756            0 :   std::string s = mi->get_body();
     757            0 :   remove_string_section(s, begin_header_prologue, end_header_prologue);
     758            0 :   remove_string_section(s, begin_header_epilogue, end_header_epilogue);
     759            0 :   remove_string_section(s, begin_public_section, end_public_section);
     760            0 :   remove_string_section(s, begin_private_section, end_private_section);
     761            0 :   remove_string_section(s, begin_member_initializer_list, end_member_initializer_list);
     762            0 :   remove_string_section(s, has_add_algo_1, "");
     763            0 :   remove_string_section(s, has_add_algo_n, "");
     764              : 
     765            0 :   if(std::all_of(s.begin(),s.end(),isspace))
     766            0 :     return "";
     767              :   else
     768            0 :     return s;
     769            0 : }
     770              : 
     771              : static OksMethodImplementation *
     772            0 : find_method_implementation(const OksMethod * method, std::initializer_list<std::string> names)
     773              : {
     774            0 :   for (const auto& name : names)
     775              :     {
     776            0 :       if (OksMethodImplementation * mi = method->find_implementation(name))
     777            0 :         if (mi->get_prototype().empty() == false)
     778            0 :           return mi;
     779              :     }
     780              : 
     781              :   return nullptr;
     782              : }
     783              : 
     784              : OksMethodImplementation *
     785            0 : find_cpp_method_implementation(const OksMethod * method)
     786              : {
     787            0 :   return find_method_implementation(method, { "c++", "C++" });
     788            0 : }
     789              : 
        

Generated by: LCOV version 2.0-1