From c5db2b9db6c8c707c745c5920a4179e6e6b2772c Mon Sep 17 00:00:00 2001 From: Boris Kolpackov Date: Fri, 12 Feb 2016 13:40:27 +0200 Subject: Add support for generating vector scanner (--generate-vector-scanner) --- cli/options.cli | 6 ++++++ cli/options.cxx | 10 ++++++++++ cli/options.hxx | 4 ++++ cli/options.ixx | 6 ++++++ cli/runtime-header.cxx | 31 +++++++++++++++++++++++++++++++ cli/runtime-inline.cxx | 21 +++++++++++++++++++++ cli/runtime-source.cxx | 41 +++++++++++++++++++++++++++++++++++++++++ 7 files changed, 119 insertions(+) (limited to 'cli') diff --git a/cli/options.cli b/cli/options.cli index 501cc82..aa353e1 100644 --- a/cli/options.cli +++ b/cli/options.cli @@ -68,6 +68,12 @@ class options well as files specified with command line options." }; + bool --generate-vector-scanner + { + "Generate the \c{vector_scanner} implementation. This scanner is capable + of reading command line arguments from \cb{vector}." + }; + bool --suppress-inline { "Generate all functions non-inline. By default simple functions are diff --git a/cli/options.cxx b/cli/options.cxx index 6008a4b..26f6eba 100644 --- a/cli/options.cxx +++ b/cli/options.cxx @@ -576,6 +576,7 @@ options () generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -707,6 +708,7 @@ options (int& argc, generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -841,6 +843,7 @@ options (int start, generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -975,6 +978,7 @@ options (int& argc, generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -1111,6 +1115,7 @@ options (int start, generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -1243,6 +1248,7 @@ options (::cli::scanner& s, generate_parse_ (), generate_description_ (), generate_file_scanner_ (), + generate_vector_scanner_ (), suppress_inline_ (), cli_namespace_ ("::cli"), cli_namespace_specified_ (false), @@ -1391,6 +1397,8 @@ print_usage (::std::ostream& os, ::cli::usage_para p) os << "--generate-file-scanner Generate the argv_file_scanner implementation." << ::std::endl; + os << "--generate-vector-scanner Generate the vector_scanner implementation." << ::std::endl; + os << "--suppress-inline Generate all functions non-inline." << ::std::endl; os << "--cli-namespace Generate the CLI support types in the " << ::std::endl @@ -1621,6 +1629,8 @@ struct _cli_options_map_init &::cli::thunk< options, bool, &options::generate_description_ >; _cli_options_map_["--generate-file-scanner"] = &::cli::thunk< options, bool, &options::generate_file_scanner_ >; + _cli_options_map_["--generate-vector-scanner"] = + &::cli::thunk< options, bool, &options::generate_vector_scanner_ >; _cli_options_map_["--suppress-inline"] = &::cli::thunk< options, bool, &options::suppress_inline_ >; _cli_options_map_["--cli-namespace"] = diff --git a/cli/options.hxx b/cli/options.hxx index 74dfb1e..5e6ae8c 100644 --- a/cli/options.hxx +++ b/cli/options.hxx @@ -433,6 +433,9 @@ class options generate_file_scanner () const; const bool& + generate_vector_scanner () const; + + const bool& suppress_inline () const; const std::string& @@ -791,6 +794,7 @@ class options bool generate_parse_; bool generate_description_; bool generate_file_scanner_; + bool generate_vector_scanner_; bool suppress_inline_; std::string cli_namespace_; bool cli_namespace_specified_; diff --git a/cli/options.ixx b/cli/options.ixx index 6e7520b..f8ceadf 100644 --- a/cli/options.ixx +++ b/cli/options.ixx @@ -290,6 +290,12 @@ generate_file_scanner () const } inline const bool& options:: +generate_vector_scanner () const +{ + return this->generate_vector_scanner_; +} + +inline const bool& options:: suppress_inline () const { return this->suppress_inline_; diff --git a/cli/runtime-header.cxx b/cli/runtime-header.cxx index 98a2e5d..50281fa 100644 --- a/cli/runtime-header.cxx +++ b/cli/runtime-header.cxx @@ -292,6 +292,37 @@ generate_runtime_header (context& ctx) << "bool erase_;" << "};"; + // vector_scanner + // + if (ctx.options.generate_vector_scanner ()) + { + os << "class vector_scanner: public scanner" + << "{" + << "public:" << endl + << "vector_scanner (const std::vector&, " << + "std::size_t start = 0);" + << endl + << "std::size_t" << endl + << "end () const;" + << endl + << "virtual bool" << endl + << "more ();" + << endl + << "virtual const char*" << endl + << "peek ();" + << endl + << "virtual const char*" << endl + << "next ();" + << endl + << "virtual void" << endl + << "skip ();" + << endl + << "private:" << endl + << "const std::vector& v_;" + << "std::size_t i_;" + << "};"; + } + // argv_file_scanner // if (ctx.options.generate_file_scanner ()) diff --git a/cli/runtime-inline.cxx b/cli/runtime-inline.cxx index ce53575..2774ee7 100644 --- a/cli/runtime-inline.cxx +++ b/cli/runtime-inline.cxx @@ -187,6 +187,27 @@ generate_runtime_inline (context& ctx) << "return i_;" << "}"; + // vector_scanner + // + if (ctx.options.generate_vector_scanner ()) + { + os << "// vector_scanner" << endl + << "//" << endl; + + os << inl << "vector_scanner::" << endl + << "vector_scanner (const std::vector& v, " << + "std::size_t i)" << endl + << ": v_ (v), i_ (i)" + << "{" + << "}"; + + os << inl << "std::size_t vector_scanner::" << endl + << "end () const" + << "{" + << "return i_;" + << "}"; + } + // argv_file_scanner // if (ctx.options.generate_file_scanner ()) diff --git a/cli/runtime-source.cxx b/cli/runtime-source.cxx index 144eace..30f08b0 100644 --- a/cli/runtime-source.cxx +++ b/cli/runtime-source.cxx @@ -242,6 +242,47 @@ generate_runtime_source (context& ctx, bool complete) << "throw eos_reached ();" << "}"; + // vector_scanner + // + if (ctx.options.generate_vector_scanner ()) + { + os << "// vector_scanner" << endl + << "//" << endl + + << "bool vector_scanner::" << endl + << "more ()" + << "{" + << "return i_ < v_.size ();" + << "}" + + << "const char* vector_scanner::" << endl + << "peek ()" + << "{" + << "if (i_ < v_.size ())" << endl + << "return v_[i_].c_str ();" + << "else" << endl + << "throw eos_reached ();" + << "}" + + << "const char* vector_scanner::" << endl + << "next ()" + << "{" + << "if (i_ < v_.size ())" << endl + << "return v_[i_++].c_str ();" + << "else" << endl + << "throw eos_reached ();" + << "}" + + << "void vector_scanner::" << endl + << "skip ()" + << "{" + << "if (i_ < v_.size ())" << endl + << "++i_;" + << "else" << endl + << "throw eos_reached ();" + << "}"; + } + // argv_file_scanner // if (ctx.options.generate_file_scanner ()) -- cgit v1.1