| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337 | /* Distributed under the OSI-approved BSD 3-Clause License.  See accompanying   file Copyright.txt or https://cmake.org/licensing for details.  */#include "cmDependsJavaParserHelper.h"#include "cmDependsJavaLexer.h"#include "cmSystemTools.h"#include "cmsys/FStream.hxx"#include <iostream>#include <stdio.h>#include <stdlib.h>#include <string.h>#include <utility>int cmDependsJava_yyparse(yyscan_t yyscanner);cmDependsJavaParserHelper::cmDependsJavaParserHelper(){  this->CurrentDepth = 0;  this->UnionsAvailable = 0;  this->LastClassId = 0;  CurrentClass tl;  tl.Name = "*";  this->ClassStack.push_back(std::move(tl));}cmDependsJavaParserHelper::~cmDependsJavaParserHelper(){  this->CleanupParser();}void cmDependsJavaParserHelper::CurrentClass::AddFileNamesForPrinting(  std::vector<std::string>* files, const char* prefix, const char* sep) const{  std::string rname;  if (prefix) {    rname += prefix;    rname += sep;  }  rname += this->Name;  files->push_back(rname);  for (CurrentClass const& nc : this->NestedClasses) {    nc.AddFileNamesForPrinting(files, rname.c_str(), sep);  }}void cmDependsJavaParserHelper::DeallocateParserType(char** pt){  if (!pt) {    return;  }  if (!*pt) {    return;  }  *pt = nullptr;  this->UnionsAvailable--;}void cmDependsJavaParserHelper::AddClassFound(const char* sclass){  if (!sclass) {    return;  }  for (std::string const& cf : this->ClassesFound) {    if (cf == sclass) {      return;    }  }  this->ClassesFound.emplace_back(sclass);}void cmDependsJavaParserHelper::AddPackagesImport(const char* sclass){  for (std::string const& pi : this->PackagesImport) {    if (pi == sclass) {      return;    }  }  this->PackagesImport.emplace_back(sclass);}void cmDependsJavaParserHelper::SafePrintMissing(const char* str, int line,                                                 int cnt){  if (str) {    std::cout << line << " String " << cnt << " exists: ";    unsigned int cc;    for (cc = 0; cc < strlen(str); cc++) {      unsigned char ch = str[cc];      if (ch >= 32 && ch <= 126) {        std::cout << static_cast<char>(ch);      } else {        std::cout << "<" << static_cast<int>(ch) << ">";        break;      }    }    std::cout << "- " << strlen(str) << std::endl;  }}void cmDependsJavaParserHelper::Print(const char* place, const char* str){  if (this->Verbose) {    std::cout << "[" << place << "=" << str << "]" << std::endl;  }}void cmDependsJavaParserHelper::CombineUnions(char** out, const char* in1,                                              char** in2, const char* sep){  size_t len = 1;  if (in1) {    len += strlen(in1);  }  if (*in2) {    len += strlen(*in2);  }  if (sep) {    len += strlen(sep);  }  *out = new char[len];  *out[0] = 0;  if (in1) {    strcat(*out, in1);  }  if (sep) {    strcat(*out, sep);  }  if (*in2) {    strcat(*out, *in2);  }  if (*in2) {    this->DeallocateParserType(in2);  }  this->UnionsAvailable++;}void cmDependsJavaParserHelper::CheckEmpty(  int line, int cnt, cmDependsJavaParserHelper::ParserType* pt){  int cc;  int kk = -cnt + 1;  for (cc = 1; cc <= cnt; cc++) {    cmDependsJavaParserHelper::ParserType* cpt = pt + kk;    this->SafePrintMissing(cpt->str, line, cc);    kk++;  }}void cmDependsJavaParserHelper::PrepareElement(  cmDependsJavaParserHelper::ParserType* me){  // Inititalize self  me->str = nullptr;}void cmDependsJavaParserHelper::AllocateParserType(  cmDependsJavaParserHelper::ParserType* pt, const char* str, int len){  pt->str = nullptr;  if (len == 0) {    len = static_cast<int>(strlen(str));  }  if (len == 0) {    return;  }  this->UnionsAvailable++;  pt->str = new char[len + 1];  strncpy(pt->str, str, len);  pt->str[len] = 0;  this->Allocates.push_back(pt->str);}void cmDependsJavaParserHelper::StartClass(const char* cls){  CurrentClass cl;  cl.Name = cls;  this->ClassStack.push_back(std::move(cl));  this->CurrentDepth++;}void cmDependsJavaParserHelper::EndClass(){  if (this->ClassStack.empty()) {    std::cerr << "Error when parsing. Current class is null" << std::endl;    abort();  }  if (this->ClassStack.size() <= 1) {    std::cerr << "Error when parsing. Parent class is null" << std::endl;    abort();  }  CurrentClass& current = this->ClassStack.back();  CurrentClass& parent = this->ClassStack[this->ClassStack.size() - 2];  this->CurrentDepth--;  parent.NestedClasses.push_back(current);  this->ClassStack.pop_back();}void cmDependsJavaParserHelper::PrintClasses(){  if (this->ClassStack.empty()) {    std::cerr << "Error when parsing. No classes on class stack" << std::endl;    abort();  }  for (std::string const& f : this->GetFilesProduced()) {    std::cout << "  " << f << ".class" << std::endl;  }}std::vector<std::string> cmDependsJavaParserHelper::GetFilesProduced(){  std::vector<std::string> files;  CurrentClass const& toplevel = this->ClassStack.front();  for (CurrentClass const& nc : toplevel.NestedClasses) {    nc.AddFileNamesForPrinting(&files, nullptr, "$");  }  return files;}int cmDependsJavaParserHelper::ParseString(const char* str, int verb){  if (!str) {    return 0;  }  this->Verbose = verb;  this->InputBuffer = str;  this->InputBufferPos = 0;  this->CurrentLine = 0;  yyscan_t yyscanner;  cmDependsJava_yylex_init(&yyscanner);  cmDependsJava_yyset_extra(this, yyscanner);  int res = cmDependsJava_yyparse(yyscanner);  cmDependsJava_yylex_destroy(yyscanner);  if (res != 0) {    std::cout << "JP_Parse returned: " << res << std::endl;    return 0;  }  if (verb) {    if (!this->CurrentPackage.empty()) {      std::cout << "Current package is: " << this->CurrentPackage << std::endl;    }    std::cout << "Imports packages:";    if (!this->PackagesImport.empty()) {      std::vector<std::string>::iterator it;      for (it = this->PackagesImport.begin(); it != this->PackagesImport.end();           ++it) {        std::cout << " " << *it;      }    }    std::cout << std::endl;    std::cout << "Depends on:";    if (!this->ClassesFound.empty()) {      for (std::string const& cf : this->ClassesFound) {        std::cout << " " << cf;      }    }    std::cout << std::endl;    std::cout << "Generated files:" << std::endl;    this->PrintClasses();    if (this->UnionsAvailable != 0) {      std::cout << "There are still " << this->UnionsAvailable                << " unions available" << std::endl;    }  }  this->CleanupParser();  return 1;}void cmDependsJavaParserHelper::CleanupParser(){  for (char* allocate : this->Allocates) {    delete[] allocate;  }  this->Allocates.erase(this->Allocates.begin(), this->Allocates.end());}int cmDependsJavaParserHelper::LexInput(char* buf, int maxlen){  if (maxlen < 1) {    return 0;  }  if (this->InputBufferPos < this->InputBuffer.size()) {    buf[0] = this->InputBuffer[this->InputBufferPos++];    if (buf[0] == '\n') {      this->CurrentLine++;    }    return 1;  }  buf[0] = '\n';  return 0;}void cmDependsJavaParserHelper::Error(const char* str){  unsigned long pos = static_cast<unsigned long>(this->InputBufferPos);  fprintf(stderr, "JPError: %s (%lu / Line: %d)\n", str, pos,          this->CurrentLine);  int cc;  std::cerr << "String: [";  for (cc = 0;       cc < 30 && *(this->InputBuffer.c_str() + this->InputBufferPos + cc);       cc++) {    std::cerr << *(this->InputBuffer.c_str() + this->InputBufferPos + cc);  }  std::cerr << "]" << std::endl;}void cmDependsJavaParserHelper::UpdateCombine(const char* str1,                                              const char* str2){  if (this->CurrentCombine.empty() && str1 != nullptr) {    this->CurrentCombine = str1;  }  this->CurrentCombine += ".";  this->CurrentCombine += str2;}int cmDependsJavaParserHelper::ParseFile(const char* file){  if (!cmSystemTools::FileExists(file)) {    return 0;  }  cmsys::ifstream ifs(file);  if (!ifs) {    return 0;  }  std::string fullfile;  std::string line;  while (cmSystemTools::GetLineFromStream(ifs, line)) {    fullfile += line + "\n";  }  return this->ParseString(fullfile.c_str(), 0);}
 |