aboutsummaryrefslogtreecommitdiff
path: root/libbuild2/b-options.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'libbuild2/b-options.cxx')
-rw-r--r--libbuild2/b-options.cxx494
1 files changed, 0 insertions, 494 deletions
diff --git a/libbuild2/b-options.cxx b/libbuild2/b-options.cxx
index 86f5bfe..0164a0a 100644
--- a/libbuild2/b-options.cxx
+++ b/libbuild2/b-options.cxx
@@ -19,8 +19,6 @@
#include <utility>
#include <ostream>
#include <sstream>
-#include <cstring>
-#include <fstream>
namespace build2
{
@@ -28,498 +26,6 @@ namespace build2
{
namespace cli
{
- // unknown_option
- //
- unknown_option::
- ~unknown_option () throw ()
- {
- }
-
- void unknown_option::
- print (::std::ostream& os) const
- {
- os << "unknown option '" << option ().c_str () << "'";
- }
-
- const char* unknown_option::
- what () const throw ()
- {
- return "unknown option";
- }
-
- // unknown_argument
- //
- unknown_argument::
- ~unknown_argument () throw ()
- {
- }
-
- void unknown_argument::
- print (::std::ostream& os) const
- {
- os << "unknown argument '" << argument ().c_str () << "'";
- }
-
- const char* unknown_argument::
- what () const throw ()
- {
- return "unknown argument";
- }
-
- // missing_value
- //
- missing_value::
- ~missing_value () throw ()
- {
- }
-
- void missing_value::
- print (::std::ostream& os) const
- {
- os << "missing value for option '" << option ().c_str () << "'";
- }
-
- const char* missing_value::
- what () const throw ()
- {
- return "missing option value";
- }
-
- // invalid_value
- //
- invalid_value::
- ~invalid_value () throw ()
- {
- }
-
- void invalid_value::
- print (::std::ostream& os) const
- {
- os << "invalid value '" << value ().c_str () << "' for option '"
- << option ().c_str () << "'";
-
- if (!message ().empty ())
- os << ": " << message ().c_str ();
- }
-
- const char* invalid_value::
- what () const throw ()
- {
- return "invalid option value";
- }
-
- // eos_reached
- //
- void eos_reached::
- print (::std::ostream& os) const
- {
- os << what ();
- }
-
- const char* eos_reached::
- what () const throw ()
- {
- return "end of argument stream reached";
- }
-
- // file_io_failure
- //
- file_io_failure::
- ~file_io_failure () throw ()
- {
- }
-
- void file_io_failure::
- print (::std::ostream& os) const
- {
- os << "unable to open file '" << file ().c_str () << "' or read failure";
- }
-
- const char* file_io_failure::
- what () const throw ()
- {
- return "unable to open file or read failure";
- }
-
- // unmatched_quote
- //
- unmatched_quote::
- ~unmatched_quote () throw ()
- {
- }
-
- void unmatched_quote::
- print (::std::ostream& os) const
- {
- os << "unmatched quote in argument '" << argument ().c_str () << "'";
- }
-
- const char* unmatched_quote::
- what () const throw ()
- {
- return "unmatched quote";
- }
-
- // scanner
- //
- scanner::
- ~scanner ()
- {
- }
-
- // argv_scanner
- //
- bool argv_scanner::
- more ()
- {
- return i_ < argc_;
- }
-
- const char* argv_scanner::
- peek ()
- {
- if (i_ < argc_)
- return argv_[i_];
- else
- throw eos_reached ();
- }
-
- const char* argv_scanner::
- next ()
- {
- if (i_ < argc_)
- {
- const char* r (argv_[i_]);
-
- if (erase_)
- {
- for (int i (i_ + 1); i < argc_; ++i)
- argv_[i - 1] = argv_[i];
-
- --argc_;
- argv_[argc_] = 0;
- }
- else
- ++i_;
-
- ++start_position_;
- return r;
- }
- else
- throw eos_reached ();
- }
-
- void argv_scanner::
- skip ()
- {
- if (i_ < argc_)
- {
- ++i_;
- ++start_position_;
- }
- else
- throw eos_reached ();
- }
-
- std::size_t argv_scanner::
- position ()
- {
- return start_position_;
- }
-
- // argv_file_scanner
- //
- int argv_file_scanner::zero_argc_ = 0;
- std::string argv_file_scanner::empty_string_;
-
- bool argv_file_scanner::
- more ()
- {
- if (!args_.empty ())
- return true;
-
- while (base::more ())
- {
- // See if the next argument is the file option.
- //
- const char* a (base::peek ());
- const option_info* oi = 0;
- const char* ov = 0;
-
- if (!skip_)
- {
- if ((oi = find (a)) != 0)
- {
- base::next ();
-
- if (!base::more ())
- throw missing_value (a);
-
- ov = base::next ();
- }
- else if (std::strncmp (a, "-", 1) == 0)
- {
- if ((ov = std::strchr (a, '=')) != 0)
- {
- std::string o (a, 0, ov - a);
- if ((oi = find (o.c_str ())) != 0)
- {
- base::next ();
- ++ov;
- }
- }
- }
- }
-
- if (oi != 0)
- {
- if (oi->search_func != 0)
- {
- std::string f (oi->search_func (ov, oi->arg));
-
- if (!f.empty ())
- load (f);
- }
- else
- load (ov);
-
- if (!args_.empty ())
- return true;
- }
- else
- {
- if (!skip_)
- skip_ = (std::strcmp (a, "--") == 0);
-
- return true;
- }
- }
-
- return false;
- }
-
- const char* argv_file_scanner::
- peek ()
- {
- if (!more ())
- throw eos_reached ();
-
- return args_.empty () ? base::peek () : args_.front ().value.c_str ();
- }
-
- const std::string& argv_file_scanner::
- peek_file ()
- {
- if (!more ())
- throw eos_reached ();
-
- return args_.empty () ? empty_string_ : *args_.front ().file;
- }
-
- std::size_t argv_file_scanner::
- peek_line ()
- {
- if (!more ())
- throw eos_reached ();
-
- return args_.empty () ? 0 : args_.front ().line;
- }
-
- const char* argv_file_scanner::
- next ()
- {
- if (!more ())
- throw eos_reached ();
-
- if (args_.empty ())
- return base::next ();
- else
- {
- hold_[i_ == 0 ? ++i_ : --i_].swap (args_.front ().value);
- args_.pop_front ();
- ++start_position_;
- return hold_[i_].c_str ();
- }
- }
-
- void argv_file_scanner::
- skip ()
- {
- if (!more ())
- throw eos_reached ();
-
- if (args_.empty ())
- return base::skip ();
- else
- {
- args_.pop_front ();
- ++start_position_;
- }
- }
-
- const argv_file_scanner::option_info* argv_file_scanner::
- find (const char* a) const
- {
- for (std::size_t i (0); i < options_count_; ++i)
- if (std::strcmp (a, options_[i].option) == 0)
- return &options_[i];
-
- return 0;
- }
-
- std::size_t argv_file_scanner::
- position ()
- {
- return start_position_;
- }
-
- void argv_file_scanner::
- load (const std::string& file)
- {
- using namespace std;
-
- ifstream is (file.c_str ());
-
- if (!is.is_open ())
- throw file_io_failure (file);
-
- files_.push_back (file);
-
- arg a;
- a.file = &*files_.rbegin ();
-
- for (a.line = 1; !is.eof (); ++a.line)
- {
- string line;
- getline (is, line);
-
- if (is.fail () && !is.eof ())
- throw file_io_failure (file);
-
- string::size_type n (line.size ());
-
- // Trim the line from leading and trailing whitespaces.
- //
- if (n != 0)
- {
- const char* f (line.c_str ());
- const char* l (f + n);
-
- const char* of (f);
- while (f < l && (*f == ' ' || *f == '\t' || *f == '\r'))
- ++f;
-
- --l;
-
- const char* ol (l);
- while (l > f && (*l == ' ' || *l == '\t' || *l == '\r'))
- --l;
-
- if (f != of || l != ol)
- line = f <= l ? string (f, l - f + 1) : string ();
- }
-
- // Ignore empty lines, those that start with #.
- //
- if (line.empty () || line[0] == '#')
- continue;
-
- string::size_type p (string::npos);
- if (line.compare (0, 1, "-") == 0)
- {
- p = line.find (' ');
-
- string::size_type q (line.find ('='));
- if (q != string::npos && q < p)
- p = q;
- }
-
- string s1;
- if (p != string::npos)
- {
- s1.assign (line, 0, p);
-
- // Skip leading whitespaces in the argument.
- //
- if (line[p] == '=')
- ++p;
- else
- {
- n = line.size ();
- for (++p; p < n; ++p)
- {
- char c (line[p]);
- if (c != ' ' && c != '\t' && c != '\r')
- break;
- }
- }
- }
- else if (!skip_)
- skip_ = (line == "--");
-
- string s2 (line, p != string::npos ? p : 0);
-
- // If the string (which is an option value or argument) is
- // wrapped in quotes, remove them.
- //
- n = s2.size ();
- char cf (s2[0]), cl (s2[n - 1]);
-
- if (cf == '"' || cf == '\'' || cl == '"' || cl == '\'')
- {
- if (n == 1 || cf != cl)
- throw unmatched_quote (s2);
-
- s2 = string (s2, 1, n - 2);
- }
-
- if (!s1.empty ())
- {
- // See if this is another file option.
- //
- const option_info* oi;
- if (!skip_ && (oi = find (s1.c_str ())))
- {
- if (s2.empty ())
- throw missing_value (oi->option);
-
- if (oi->search_func != 0)
- {
- string f (oi->search_func (s2.c_str (), oi->arg));
- if (!f.empty ())
- load (f);
- }
- else
- {
- // If the path of the file being parsed is not simple and the
- // path of the file that needs to be loaded is relative, then
- // complete the latter using the former as a base.
- //
-#ifndef _WIN32
- string::size_type p (file.find_last_of ('/'));
- bool c (p != string::npos && s2[0] != '/');
-#else
- string::size_type p (file.find_last_of ("/\\"));
- bool c (p != string::npos && s2[1] != ':');
-#endif
- if (c)
- s2.insert (0, file, 0, p + 1);
-
- load (s2);
- }
-
- continue;
- }
-
- a.value = s1;
- args_.push_back (a);
- }
-
- a.value = s2;
- args_.push_back (a);
- }
- }
-
template <typename X>
struct parser
{