The Battle for Wesnoth  1.13.4+dev
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
schema_generator.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2011 - 2016 by Sytyi Nick <[email protected]>
3  Part of the Battle for Wesnoth Project http://www.wesnoth.org/
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY.
11 
12  See the COPYING file for more details.
13 */
14 
15 /**
16  * @file
17  * This file parses the input parameters, prepares a list of files to be parsed
18  * and calls parser for each of them.
19  *
20  */
21 
23 
24 #include "filesystem.hpp"
25 
26 #include <iostream>
27 #include <fstream>
28 #include <string>
29 
30 #include <string.h>
31 
32 
33 std::string version = "0.6.0";
34 
35 using namespace schema_validation;
36 /**
37  * Parses the command line.
38  * @retval 0 Everything's OK!
39  * @retval 1 Errors found. User decided to exit.
40  * @retval 2 No input files found. Please, check your input directory.
41  * @retval 3 Output file for schema cannot be created.
42  * @retval 4 Output file for regex list cannot be created.
43  */
44 int main(int argc, char *argv[]){
45  std::string input_dir = "";
46  std::string output_file = "./data/gui/schema.cfg";
47  std::string regex_file = "./utils/regex_list.txt";
48  bool expand = false;
49  for (int arg = 1; arg != argc; ++arg) {
50  const std::string val(argv[arg]);
51  if (val.empty()) {
52  continue;
53  }
54  else if ((val == "--src-dir" || val == "-s") && arg+1 != argc) {
55  input_dir = argv[++arg];
56  }
57  else if ((val == "--output" || val == "-o") && arg+1 != argc) {
58  output_file = argv[++arg];
59  }
60  else if ((val == "--regex" || val == "-r") ) {
61  if (arg+1 != argc){
62  regex_file = argv[++arg];
63  }
64  std::fstream f;
65  f.open(regex_file.c_str(),std::ios::out|std::ios::trunc);
66  if (f.fail()){
67  return 4;
68  }
69  test_regex(f);
70  f.close();
71  return 0;
72  }
73  else if (val == "--help" || val == "-h") {
74  std::cout << "usage: " << argv[0]
75  << " [-erhV] [-s <input_dir>] [-o <output_file>]\n"
76  << " -r, --regex <regex_file>\t"
77  << "List of used regexes.\n"
78  << " -e, --expand \t"
79  << "Expands all tags due to their super-tags."
80  << "Useful to debug schema markup.\n"
81  << " -h, --help\t\t\t"
82  << "Shows this usage message.\n"
83  << " -s, --src-dir <input_dir>\t"
84  <<"Select the input directory.\n"
85  << " -o, --output <output_file>\t"
86  <<"Select the output file.\n"
87  << " -V, --version\t\t\t"
88  << "Version of tool\n";
89  return 0;
90  } else if (val == "--version" || val == "-V") {
91  std::cout << "Battle for Wesnoth schema generator tool, version "
92  << version << "\n";
93  return 0;
94  } else if (val == "--expand" || val == "-e") {
95  expand = true;
96  }
97  }
98  if(input_dir.empty()){
99  std::cout << "No input was selected. Processing \"./src\"\n";
100  input_dir = "./src";
101  }
102 
103  if (! filesystem::file_exists(input_dir)){
104  return 2;
105  }
106 
107  std::vector<std::string> files;
108  std::vector<std::string> dirs;
109 
110  if (filesystem::is_directory(input_dir)){
112 
113  if (files.empty() && dirs.empty()){
114  std::cout << "Some problem with input directory "
115  << input_dir << "\n"
116  << "No files found\n";
117  return 2;
118  }
119  /** Getting full list of files recursively.*/
120  while (!dirs.empty()){
121  std::string temp_dir = dirs.back();
122  dirs.pop_back();
124  }
125  }else{
126  files.push_back(input_dir);
127  }
128  class_source_parser parser;
129  parser.set_output(output_file);
130  std::vector<std::string>::iterator i = files.begin();
131  unsigned int counter = 0;
132 
133  for (;i != files.end(); ++i){
134  bool ok = false;
135  if (filesystem::base_name((*i)).find(".cpp")!=std::string::npos){
136  ok = true;
137  } else
138  if (filesystem::base_name((*i)).find(".hpp")!=std::string::npos){
139  ok = true;
140  } else
141  if (filesystem::base_name((*i)).find(".schema")!=std::string::npos){
142  ok = true;
143  }
144  if (ok){
145  ++counter;
146  parser.set_input((*i));
147  parser.parse_source();
148  }
149  }
150  std::cout << "Processed " << counter << " files in " << input_dir << "\n";
151  // check errors
152 
153  if (! parser.see_errors().is_empty()) {
154  /**
155  * Let the user decide whether error are great or just misprints.
156  * If any error found, waits for a Yy or Nn to continue or not.
157  */
158  std::cout << "There are some errors\n";
159  parser.see_errors().print_errors(std::cout);
160  // Take user response
161  char c;
162  std::cout << "Continue with errors? Y/N ";
163  while (true) {
164  std::cin.get(c);
165  const char *r = strchr("yYnN",c);
166  if (r == nullptr){
167  std::cout << "Please, choose your answer " << std::endl;
168  continue;
169  }
170  if (c == 'n' || c=='N'){
171  std::cout << "I'll take that as a NO" << std::endl;
172  return 1;
173  }
174  if (c == 'y' || c=='Y'){
175  std::cout << "I'll take that as a Yes" << std::endl;
176  break;
177  }
178  }
179  }
180  if (expand) {
181  parser.expand();
182  }
183  // save schema information
184  if ( ! parser.save_schema()){
185  return 4;
186  }
187  std::cout << "Schema written to "<< output_file << "\n";
188  return 0;
189 }
void test_regex(std::ostream &f)
Writes to the file regex templates list.
bool parse_source()
Parses file line-by-line, checking every line to open WIKI block Please, notice that main input work ...
GLuint counter
Definition: glew.h:2584
int main(int argc, char *argv[])
Parses the command line.
This file contains sourceparser object, collecting annotations and building a tag tree...
GLuint const GLfloat * val
Definition: glew.h:2614
bool save_schema()
Saves tag tree to schema file.
void set_input(const std::string &s)
std::string base_name(const std::string &file)
Returns the base filename of a file, with directory name stripped.
const class_error_container & see_errors() const
Grants access to error container.
bool is_directory(const std::string &fname)
Returns true if the given file is a directory.
void get_files_in_dir(const std::string &dir, std::vector< std::string > *files, std::vector< std::string > *dirs=nullptr, file_name_option mode=FILE_NAME_ONLY, file_filter_option filter=NO_FILTER, file_reorder_option reorder=DONT_REORDER, file_tree_checksum *checksum=nullptr)
Populates 'files' with all the files and 'dirs' with all the directories in dir.
bool is_empty() const
Checks, if container is empty.
size_t i
Definition: function.cpp:1057
Declarations for File-IO.
void set_output(const std::string &s)
GLdouble GLdouble GLdouble r
Definition: glew.h:1374
void print_errors(std::ostream &s) const
Prints errors to output stream.
#define c
Definition: glew.h:12743
std::string version
std::string::const_iterator iterator
Definition: tokenizer.hpp:21
bool file_exists(const std::string &name)
Returns true if a file or directory with such name already exists.
GLsizei const GLcharARB ** string
Definition: glew.h:4503
GLclampf f
Definition: glew.h:3024