Page MenuHomec4science

main.cc
No OneTemporary

File Metadata

Created
Sun, Sep 1, 02:23
/**
* @file main.cc
*
* @author Guillaume Anciaux <guillaume.anciaux@epfl.ch>
*
* @date Fri Oct 10 16:40:09 2014
*
* @brief Manual parser
*
* @section LICENSE
*
* Copyright (©) 2010-2011 EPFL (Ecole Polytechnique Fédérale de Lausanne)
* Laboratory (LSMS - Laboratoire de Simulation en Mécanique des Solides)
*
* LibMultiScale is free software: you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* LibMultiScale is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with LibMultiScale. If not, see <http://www.gnu.org/licenses/>.
*
*/
/* -------------------------------------------------------------------------- */
#include "generate_latex.hh"
#include "libmultiscale_doc_parser.hh"
#include <fstream>
/* -------------------------------------------------------------------------- */
#include <boost/filesystem.hpp>
#include <iostream>
#include <limits>
using namespace std;
using namespace boost::filesystem;
/* -------------------------------------------------------------------------- */
typedef unsigned int UInt;
/* -------------------------------------------------------------------------- */
bool searchDeclareParamInFile(const std::string &filename) {
std::ifstream file(filename.c_str());
std::string str((std::istreambuf_iterator<char>(file)),
std::istreambuf_iterator<char>());
const boost::regex my_filter(".*(declareParams\\(\\)\\s*\\{).*");
boost::smatch what;
bool res = boost::regex_match(str, what, my_filter);
if (res) {
const boost::regex filter_header_files(".*\\.hh");
boost::smatch what;
bool res = boost::regex_match(filename, what, filter_header_files);
if (res)
std::cerr
<< filename
<< ":0:Warning: please move declaration of parameters to .cc file"
<< std::endl;
}
// std::cout << "test file " << filename << " : " << res<< std::endl;
return res;
}
/* -------------------------------------------------------------------------- */
std::vector<path> recursiveSearchForSourceFiles(path p) {
const boost::regex my_filter(".*\\.(cc|hh)");
std::vector<path> list_source_files;
boost::filesystem::recursive_directory_iterator end;
boost::filesystem::recursive_directory_iterator dir(p);
while (dir != end) {
path f = dir->path();
if (is_regular_file(f)) {
boost::smatch what;
if (boost::regex_match(f.leaf().native(), what, my_filter))
if (searchDeclareParamInFile(f.native()))
list_source_files.push_back(f);
}
++dir;
}
return list_source_files;
}
/* -------------------------------------------------------------------------- */
std::vector<path> readListOfSourceFiles(path p) {
std::string fname = p.native();
std::ifstream f(fname.c_str());
std::vector<path> list_files;
if (!f.is_open()) {
std::cerr << "could not open config file " << fname << std::endl;
exit(EXIT_FAILURE);
}
while (f.good()) {
std::string line;
getline(f, line);
if (line == "")
continue;
if (!searchDeclareParamInFile(line))
continue;
path source_file = line;
// std::cout << "I will parse file " << source_file << std::endl;
list_files.push_back(source_file);
}
return list_files;
}
/* -------------------------------------------------------------------------- */
void addDoc(LMDataNode &root, LMDocData &doc, path file) {
path::iterator end = file.end();
path::iterator begin = file.begin();
--end;
for (; end != begin; --end) {
if (end->native() == "src") {
++end;
break;
}
}
if (end == file.end()) {
std::cerr << "problem in the file structure" << std::endl;
exit(EXIT_FAILURE);
}
begin = end;
end = file.end();
LMDataNode *it = &root;
for (; begin != end; ++begin) {
std::string sublevel = begin->native();
it = &(it->children[sublevel]);
it->name = sublevel;
}
it->data.push_back(doc);
}
/* -------------------------------------------------------------------------- */
void addDocByName(std::map<std::string, LMDocData> &sorted_by_name,
LMDocData &doc, path file) {
std::string short_name = file.stem().native();
// std::cerr << "record heritance " << short_name << std::endl;
sorted_by_name[protectString(short_name)] = doc;
}
/* -------------------------------------------------------------------------- */
void protectUnderscoreInDoc(LMDocData &doc) {
doc.name = protectString(doc.name);
doc.type = protectString(doc.type);
doc.var_name = protectString(doc.var_name);
doc.defaults = protectString(doc.defaults);
doc.c_type = protectString(doc.c_type);
doc.example = protectString(doc.example);
for (UInt i = 0; i < doc.heritance.size(); ++i) {
doc.heritance[i] = protectString(doc.heritance[i]);
}
for (UInt i = 0; i < doc.children.size(); ++i)
protectUnderscoreInDoc(doc.children[i]);
}
/* -------------------------------------------------------------------------- */
void checkKeywordExistance(
const std::string key,
std::map<std::string, std::vector<std::string>> &key_list,
std::set<std::string> &internal_key_list) {
if (key_list.count(key) == 0 && internal_key_list.count(key) == 0) {
std::cerr << "Error: Undeclared keyword " << key << std::endl;
std::map<std::string, std::vector<std::string>>::iterator it =
key_list.begin();
std::map<std::string, std::vector<std::string>>::iterator end =
key_list.end();
std::cerr << "declared keywords are ";
while (it != end) {
std::cerr << it->first << " ";
++it;
}
std::cerr << std::endl;
exit(EXIT_FAILURE);
} else if (key_list.count(key)) {
// std::cerr << "treating key " << key << " " << key_list[key].size();
key_list[key].pop_back();
// std::cerr << " " << key_list[key].size() << std::endl;
if (key_list[key].size() == 0) {
key_list.erase(key);
// std::cerr << "removing key";
}
// std::cerr << std::endl;
}
}
/* -------------------------------------------------------------------------- */
int main(int argc, char **argv) {
path p = argv[1];
// std::vector<path> files = recursiveSearchForSourceFiles(p);
std::vector<path> files = readListOfSourceFiles(p);
std::map<std::string, std::vector<std::string>> key_list =
generatorKeyWordList();
std::set<std::string> internal_key_list = generatorInternalKeyWordList();
LibMultiScaleParser parser;
LMDataNode root;
std::map<std::string, LMDocData> sorted_by_name;
for (UInt i = 0; i < files.size(); ++i) {
LMDocData res;
res.filename = files[i].native();
// std::cout << "parsing " << res.filename << std::endl;
bool r = parser.parse(res, internal_key_list);
if (r) {
checkKeywordExistance(res.name, key_list, internal_key_list);
protectUnderscoreInDoc(res);
for (UInt k = 0; k < res.children.size(); ++k) {
res.children[k].filename = res.filename;
}
protectUnderscoreInDoc(res);
addDoc(root, res, files[i]);
addDocByName(sorted_by_name, res, files[i]);
} else
std::cout << "parsing of " << res.filename << " failed" << std::endl;
}
std::map<std::string, std::vector<std::string>>::iterator it =
key_list.begin();
std::map<std::string, std::vector<std::string>>::iterator end =
key_list.end();
if (it != end) {
std::cerr << "Error: keyword " << it->first << " was not documented "
<< std::endl;
exit(EXIT_FAILURE);
}
std::string fname = "manual-generated.tex";
std::ofstream fout(fname.c_str());
GenerateLatex ltx;
ltx.generateLatex(fout, root, sorted_by_name);
}

Event Timeline