1 // Copyright Vladimir Prus 2002-2004.
2 // Distributed under the Boost Software License, Version 1.0.
3 // (See accompanying file LICENSE_1_0.txt
4 // or copy at http://www.boost.org/LICENSE_1_0.txt)
5 
6 
7 #ifndef BOOST_PARSERS_VP_2003_05_19
8 #define BOOST_PARSERS_VP_2003_05_19
9 
10 #include <boost/program_options/config.hpp>
11 #include <boost/program_options/option.hpp>
12 #include <boost/program_options/detail/cmdline.hpp>
13 
14 #include <boost/function/function1.hpp>
15 
16 #include <iosfwd>
17 #include <vector>
18 #include <utility>
19 
20 #if defined(BOOST_MSVC)
21 #   pragma warning (push)
22 #   pragma warning (disable:4251) // class 'std::vector<_Ty>' needs to have dll-interface to be used by clients of class 'boost::program_options::basic_parsed_options<wchar_t>'
23 #endif
24 
25 namespace boost { namespace program_options {
26 
27     class options_description;
28     class positional_options_description;
29 
30 
31     /** Results of parsing an input source.
32         The primary use of this class is passing information from parsers
33         component to value storage component. This class does not makes
34         much sense itself.
35     */
36     template<class charT>
37     class basic_parsed_options {
38     public:
basic_parsed_options(const options_description * xdescription,int options_prefix=0)39         explicit basic_parsed_options(const options_description* xdescription, int options_prefix = 0)
40         : description(xdescription), m_options_prefix(options_prefix) {}
41         /** Options found in the source. */
42         std::vector< basic_option<charT> > options;
43         /** Options description that was used for parsing.
44             Parsers should return pointer to the instance of
45             option_description passed to them, and issues of lifetime are
46             up to the caller. Can be NULL.
47          */
48         const options_description* description;
49 
50         /** Mainly used for the diagnostic messages in exceptions.
51          *  The canonical option prefix  for the parser which generated these results,
52          *  depending on the settings for basic_command_line_parser::style() or
53          *  cmdline::style(). In order of precedence of command_line_style enums:
54          *      allow_long
55          *      allow_long_disguise
56          *      allow_dash_for_short
57          *      allow_slash_for_short
58         */
59         int m_options_prefix;
60     };
61 
62     /** Specialization of basic_parsed_options which:
63         - provides convenient conversion from basic_parsed_options<char>
64         - stores the passed char-based options for later use.
65     */
66     template<>
67     class BOOST_PROGRAM_OPTIONS_DECL basic_parsed_options<wchar_t> {
68     public:
69         /** Constructs wrapped options from options in UTF8 encoding. */
70         explicit basic_parsed_options(const basic_parsed_options<char>& po);
71 
72         std::vector< basic_option<wchar_t> > options;
73         const options_description* description;
74 
75         /** Stores UTF8 encoded options that were passed to constructor,
76             to avoid reverse conversion in some cases. */
77         basic_parsed_options<char> utf8_encoded_options;
78 
79         /** Mainly used for the diagnostic messages in exceptions.
80          *  The canonical option prefix  for the parser which generated these results,
81          *  depending on the settings for basic_command_line_parser::style() or
82          *  cmdline::style(). In order of precedence of command_line_style enums:
83          *      allow_long
84          *      allow_long_disguise
85          *      allow_dash_for_short
86          *      allow_slash_for_short
87         */
88         int m_options_prefix;
89     };
90 
91     typedef basic_parsed_options<char> parsed_options;
92     typedef basic_parsed_options<wchar_t> wparsed_options;
93 
94     /** Augments basic_parsed_options<wchar_t> with conversion from
95         'parsed_options' */
96 
97 
98     typedef function1<std::pair<std::string, std::string>, const std::string&> ext_parser;
99 
100     /** Command line parser.
101 
102         The class allows one to specify all the information needed for parsing
103         and to parse the command line. It is primarily needed to
104         emulate named function parameters \-- a regular function with 5
105         parameters will be hard to use and creating overloads with a smaller
106         number of parameters will be confusing.
107 
108         For the most common case, the function parse_command_line is a better
109         alternative.
110 
111         There are two typedefs \-- command_line_parser and wcommand_line_parser,
112         for charT == char and charT == wchar_t cases.
113     */
114     template<class charT>
115     class basic_command_line_parser : private detail::cmdline {
116     public:
117         /** Creates a command line parser for the specified arguments
118             list. The 'args' parameter should not include program name.
119         */
120         basic_command_line_parser(const std::vector<
121                                   std::basic_string<charT> >& args);
122         /** Creates a command line parser for the specified arguments
123             list. The parameters should be the same as passed to 'main'.
124         */
125         basic_command_line_parser(int argc, const charT* const argv[]);
126 
127         /** Sets options descriptions to use. */
128         basic_command_line_parser& options(const options_description& desc);
129         /** Sets positional options description to use. */
130         basic_command_line_parser& positional(
131             const positional_options_description& desc);
132 
133         /** Sets the command line style. */
134         basic_command_line_parser& style(int);
135         /** Sets the extra parsers. */
136         basic_command_line_parser& extra_parser(ext_parser);
137 
138         /** Parses the options and returns the result of parsing.
139             Throws on error.
140         */
141         basic_parsed_options<charT> run();
142 
143         /** Specifies that unregistered options are allowed and should
144             be passed though. For each command like token that looks
145             like an option but does not contain a recognized name, an
146             instance of basic_option<charT> will be added to result,
147             with 'unrecognized' field set to 'true'. It's possible to
148             collect all unrecognized options with the 'collect_unrecognized'
149             funciton.
150         */
151         basic_command_line_parser& allow_unregistered();
152 
153         using detail::cmdline::style_parser;
154 
155         basic_command_line_parser& extra_style_parser(style_parser s);
156 
157     private:
158         const options_description* m_desc;
159     };
160 
161     typedef basic_command_line_parser<char> command_line_parser;
162     typedef basic_command_line_parser<wchar_t> wcommand_line_parser;
163 
164     /** Creates instance of 'command_line_parser', passes parameters to it,
165         and returns the result of calling the 'run' method.
166      */
167     template<class charT>
168     basic_parsed_options<charT>
169     parse_command_line(int argc, const charT* const argv[],
170                        const options_description&,
171                        int style = 0,
172                        function1<std::pair<std::string, std::string>,
173                                  const std::string&> ext
174                        = ext_parser());
175 
176     /** Parse a config file.
177 
178         Read from given stream.
179     */
180     template<class charT>
181 #if ! BOOST_WORKAROUND(__ICL, BOOST_TESTED_AT(700))
182     BOOST_PROGRAM_OPTIONS_DECL
183 #endif
184     basic_parsed_options<charT>
185     parse_config_file(std::basic_istream<charT>&, const options_description&,
186                       bool allow_unregistered = false);
187 
188     /** Parse a config file.
189 
190         Read from file with the given name. The character type is
191         passed to the file stream.
192     */
193 #ifdef BOOST_NO_CXX11_FUNCTION_TEMPLATE_DEFAULT_ARGS
194     template<class charT>
195 #else
196     template<class charT = char>
197 #endif
198 #if ! BOOST_WORKAROUND(__ICL, BOOST_TESTED_AT(700))
199     BOOST_PROGRAM_OPTIONS_DECL
200 #endif
201     basic_parsed_options<charT>
202     parse_config_file(const char* filename, const options_description&,
203                       bool allow_unregistered = false);
204 
205     /** Controls if the 'collect_unregistered' function should
206         include positional options, or not. */
207     enum collect_unrecognized_mode
208     { include_positional, exclude_positional };
209 
210     /** Collects the original tokens for all named options with
211         'unregistered' flag set. If 'mode' is 'include_positional'
212         also collects all positional options.
213         Returns the vector of origianl tokens for all collected
214         options.
215     */
216     template<class charT>
217     std::vector< std::basic_string<charT> >
218     collect_unrecognized(const std::vector< basic_option<charT> >& options,
219                          enum collect_unrecognized_mode mode);
220 
221     /** Parse environment.
222 
223         For each environment variable, the 'name_mapper' function is called to
224         obtain the option name. If it returns empty string, the variable is
225         ignored.
226 
227         This is done since naming of environment variables is typically
228         different from the naming of command line options.
229     */
230     BOOST_PROGRAM_OPTIONS_DECL parsed_options
231     parse_environment(const options_description&,
232                       const function1<std::string, std::string>& name_mapper);
233 
234     /** Parse environment.
235 
236         Takes all environment variables which start with 'prefix'. The option
237         name is obtained from variable name by removing the prefix and
238         converting the remaining string into lower case.
239     */
240     BOOST_PROGRAM_OPTIONS_DECL parsed_options
241     parse_environment(const options_description&, const std::string& prefix);
242 
243     /** @overload
244         This function exists to resolve ambiguity between the two above
245         functions when second argument is of 'char*' type. There's implicit
246         conversion to both function1 and string.
247     */
248     BOOST_PROGRAM_OPTIONS_DECL parsed_options
249     parse_environment(const options_description&, const char* prefix);
250 
251     /** Splits a given string to a collection of single strings which
252         can be passed to command_line_parser. The second parameter is
253         used to specify a collection of possible seperator chars used
254         for splitting. The seperator is defaulted to space " ".
255         Splitting is done in a unix style way, with respect to quotes '"'
256         and escape characters '\'
257     */
258     BOOST_PROGRAM_OPTIONS_DECL std::vector<std::string>
259     split_unix(const std::string& cmdline, const std::string& seperator = " \t",
260          const std::string& quote = "'\"", const std::string& escape = "\\");
261 
262 #ifndef BOOST_NO_STD_WSTRING
263     /** @overload */
264     BOOST_PROGRAM_OPTIONS_DECL std::vector<std::wstring>
265     split_unix(const std::wstring& cmdline, const std::wstring& seperator = L" \t",
266          const std::wstring& quote = L"'\"", const std::wstring& escape = L"\\");
267 #endif
268 
269     #ifdef _WIN32
270     /** Parses the char* string which is passed to WinMain function on
271         windows. This function is provided for convenience, and because it's
272         not clear how to portably access split command line string from
273         runtime library and if it always exists.
274         This function is available only on Windows.
275     */
276     BOOST_PROGRAM_OPTIONS_DECL std::vector<std::string>
277     split_winmain(const std::string& cmdline);
278 
279 #ifndef BOOST_NO_STD_WSTRING
280     /** @overload */
281     BOOST_PROGRAM_OPTIONS_DECL std::vector<std::wstring>
282     split_winmain(const std::wstring& cmdline);
283     #endif
284 #endif
285 
286 
287 }}
288 
289 #if defined(BOOST_MSVC)
290 #   pragma warning (pop)
291 #endif
292 
293 #undef DECL
294 
295 #include "boost/program_options/detail/parsers.hpp"
296 
297 #endif
298