1 karl 1.27 //%2006////////////////////////////////////////////////////////////////////////
|
2 mike 1.12 //
|
3 karl 1.24 // Copyright (c) 2000, 2001, 2002 BMC Software; Hewlett-Packard Development
4 // Company, L.P.; IBM Corp.; The Open Group; Tivoli Systems.
5 // Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company, L.P.;
|
6 karl 1.23 // IBM Corp.; EMC Corporation, The Open Group.
|
7 karl 1.24 // Copyright (c) 2004 BMC Software; Hewlett-Packard Development Company, L.P.;
8 // IBM Corp.; EMC Corporation; VERITAS Software Corporation; The Open Group.
|
9 karl 1.25 // Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.;
10 // EMC Corporation; VERITAS Software Corporation; The Open Group.
|
11 karl 1.27 // Copyright (c) 2006 Hewlett-Packard Development Company, L.P.; IBM Corp.;
12 // EMC Corporation; Symantec Corporation; The Open Group.
|
13 mike 1.12 //
14 // Permission is hereby granted, free of charge, to any person obtaining a copy
|
15 kumpf 1.17 // of this software and associated documentation files (the "Software"), to
16 // deal in the Software without restriction, including without limitation the
17 // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
18 mike 1.12 // sell copies of the Software, and to permit persons to whom the Software is
19 // furnished to do so, subject to the following conditions:
|
20 karl 1.27 //
|
21 kumpf 1.17 // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
|
22 mike 1.12 // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
23 // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
|
24 kumpf 1.17 // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
25 // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
26 // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
|
27 mike 1.12 // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 //
30 //==============================================================================
31 //
32 // Author: Bob Blair (bblair@bmc.com)
33 //
|
34 david.dillard 1.26 // Modified By: Carol Ann Krug Graves, Hewlett-Packard Company
35 // (carolann_graves@hp.com)
36 // David Dillard, VERITAS Software Corp.
37 // (david.dillard@veritas.com)
|
38 mike 1.12 //
39 //%/////////////////////////////////////////////////////////////////////////////
40
41
42 //
43 // Yet another attempt to create a general-purpose, object-oriented,
44 // portable C++ command line parser.
45 //
46 // There are two classes involved:
47 // getoopt which encapsulates three functions:
48 // 1. Registration of program-defined flags and their characteristics
49 // 2. Parsing of the command line IAW the flag definitions
50 // 3. Orderly retrieval of the command line components
51 //
52 // Optarg which abstracts the idea of a command line argument.
53 //
54 // The details of these classes are discussed in the comments above each
55 // class.
|
56 david.dillard 1.26 //
|
57 mike 1.12
58 #ifndef _GETOOPT_H_
59 #define _GETOOPT_H_
60
|
61 mike 1.13 #include <stdio.h>
|
62 mike 1.12 #include <iostream>
|
63 kumpf 1.20 #include <Pegasus/Common/ArrayInternal.h>
|
64 mike 1.12 #include <Pegasus/Common/String.h>
65 #include <Pegasus/Common/Config.h>
|
66 mike 1.13 #include <Pegasus/Common/Exception.h>
|
67 kumpf 1.18 #include <Pegasus/getoopt/Linkage.h>
|
68 mike 1.12
69 PEGASUS_USING_STD;
70 PEGASUS_USING_PEGASUS;
71
72 //
73 // This structure describes a program-defined command line option.
74 // The syntax of these options are the same as those understood by
|
75 david.dillard 1.26 // the standard C language routines getopt() and getopt_long()
|
76 mike 1.12 //
77 // Command line options are named, and the name is prefaced by
78 // either a hyphen or by two hyphens. Names prefixed by one
79 // hyphen are restricted to a length of one character. There is
80 // no limit to the size of names prefixed by two hyphens. The
81 // two-hyphen-named options are called "long" options.
82 //
83 // The argtype indicates whether the name should be bound to a value.
84 // If it never has a value, the type is 0. If it always has a value,
85 // the type is 1. If it can optionally have a value, the type is 2.
86 // Type 2 is valid only with long-named options
87 //
88 // The islong flag tells whether the option is long-named.
|
89 david.dillard 1.26 //
|
90 mike 1.12 // The isactive flag tells whether the option should be considered
91 // during parsing. It is on unless explicitly turned off by the program.
92 struct flagspec {
93 String name;
94 int argtype;
95 Boolean islong;
96 Boolean active;
97 };
98
99 //
100 // Class Optarg encapsulates a command line argument as it was parsed.
101 // If it has a name, it means that it is bound to that command line option.
102 // For example, if the command line were
103 // myprog --database=xyz mytable
104 // then the name "database" would be associated with the first argument.
105 // There would be no name associated with the second argument ("mytable").
106 //
107 // In the example above, the value property of the arguments would
108 // be "xyz" bound to the name "database" and "mytable" bound to a
109 // blank name.
110 //
111 mike 1.12 // The option type further describes the binding:
112 // A FLAG means that the value is bound to a short-named option name (flag)
113 // A LONGFLAG means that the value is bound to a long-named option name
114 // REGULAR means that the argument value is not preceded by a flag
115 //
116 class PEGASUS_GETOOPT_LINKAGE Optarg {
117 public:
118 enum opttype {FLAG, LONGFLAG, REGULAR};
119 private:
120 String _name;
121 opttype _opttype;
122 String _value;
123 public:
124 // Constructors and Destructor. Default copying is OK for this class.
125 Optarg();
126 Optarg(const String &name, opttype type, const String &value);
127 ~Optarg();
128 // Methods to set or reset the properties
129 void setName(const String &name);
130 void setType(opttype type);
131 void setValue(const String &value);
132 mike 1.12 // Methods to get information about the object
133 const String &getName() const;
134 const String &getopt() const;
135 opttype getType() const;
136 Boolean isFlag() const; // Is the opttype == "FLAG" or "LONGFLAG"?
137 Boolean isLongFlag() const; // IS the Opttype == LONGFLAG?
138 const String &Value() const; // return the value as a String
139 const String &optarg() const; // ditto, in getopt() terminology
140 void Value(String &v) const ; // Fill in a String with the Value
|
141 david.dillard 1.26 // @exception TypeMismatchException
142 void Value(int &v) const; // Fill in an int with
143 // the value
144 // @exception TypeMismatchException
145 void Value(unsigned int &v) const; // ditto an
146 // unsigned int
|
147 mike 1.12 void Value(long &v) const ; // ditto a long
148 void Value(unsigned long &v) const; // ditto an unsigned long
149 void Value(double &d) const; // ditto a double
150 ostream &print(ostream &os) const; // print the members (for debug)
151 };
|
152 mike 1.13
153
|
154 mike 1.12 //
155 // class getoopt (a portamentau of "getopt" and "oo") is a container
156 // for Optarg objects parsed from the command line, and it provides
157 // methods for specifying command line options and initiating the
158 // parse.
159 //
160 // The idea is to be able to do getopt()-like things with it:
161 // getoopt cmdline(optstring);
162 // for (getoopt::const_iterator it = cmdline.begin();
163 // it != cmdline.end();
164 // it++) {
165 // . . . (process an Optarg represented by *it.
166 //
167 // There are three steps in using this class:
168 // 1. Initialization -- specifying the command line options
169 // You can pass a String identical in format the an optstring
170 // to the object either in the constructor or by an explicit method.
171 // If you have long-named options to describe, use as manu
172 // addLongFilespec() calls as you need.
173 // 2. Parse the command line.
174 // This will almost always be cmdline.parse(argc, argv);
175 mike 1.12 // You can check for errors (violations of the command line
176 // options specified) by calling hasErrors(). If you need
177 // a description of the errors, they are stored in a
178 // Array<String> which can be retrieved with getErrorStrings();
179 // You can also print the error strings with printErrors();
180 // 3. Analyze the parsed data. You can either iterate through the
181 // the command line, or use indexes like this:
182 // for (unsigned int i = cmdline.first(); i < cmdline.last(); i++)
183 // . . . (process an Optarg represented by cmdline[i])
184 //
185 // You can also look at the parsed data for named arguments
186 // in an adhoc fashion by calling
187 // isSet(flagName);
188 // and
189 // value(flagName);
|
190 david.dillard 1.26 //
|
191 mike 1.12 class PEGASUS_GETOOPT_LINKAGE getoopt {
192 public:
193 typedef Array<flagspec> Flagspec_List;
194 typedef Array<String> Error_List;
195 typedef Array<Optarg> Arg_List;
|
196 mike 1.13
197 /**
198 In the valid option definition string, following an option,
199 indicates that the preceding option takes a required argument.
200 */
201 static const char GETOPT_ARGUMENT_DESIGNATOR;
202
|
203 mike 1.12 private:
204 Flagspec_List _flagspecs;
205 Error_List _errorStrings;
206 Arg_List _args;
207 flagspec *getFlagspecForUpdate(char c);
208 flagspec *getFlagspecForUpdate(const String &s);
209 String emptystring;
210 Optarg _emptyopt;
211 public:
|
212 kumpf 1.14 enum argtype {NOARG, MUSTHAVEARG, OPTIONALARG};
|
213 mike 1.12 // Constructor and destructor. You can initialize an instance with
214 // an optstring to specify command line flags.
215 getoopt(const char *optstring = 0);
216 ~getoopt();
|
217 david.dillard 1.26
|
218 mike 1.12 // Routines for specifying the command line options
219 // add short-named flags, either en masse as an optstring
220 Boolean addFlagspec(const String &opt);
221 // or individually
222 Boolean addFlagspec(char opt, Boolean hasarg = false);
223 // (You can also remove a short flag specification if you need to)
224 Boolean removeFlagspec(char opt);
225 // You can add long-named flags only individually
226 Boolean addLongFlagspec(const String &name, argtype type);
227 // and remove them in the same way.
228 Boolean removeLongFlagspec(const String &name);
229 // You can also get a pointer to the flagspec structure for
230 // a particular flag, specifying a char for short or String for long name
231 const flagspec *getFlagspec(char c);
232 const flagspec *getFlagspec(const String &s);
233
234 // Routines for initiating the parse and checking its success.
235 Boolean parse(int argc, char **argv);
236 Boolean hasErrors() const;
237 const Error_List &getErrorStrings() const;
238 ostream &printErrors(ostream &os) const;
239 mike 1.12 void printErrors(String &s) const;
240
241 // Routines for processing the parsed command line
242 // Using indexes
243 unsigned int size() const; // The number of arguments found
244 const Optarg &operator[](unsigned int n); // The nth element
245 unsigned int first() const; // always 0 (duh)
246 unsigned int last() const; // always == size();
247 // Ad Hoc
248 // isSet returns the number of times a particular option appeared
249 // in the argument set.
250 unsigned int isSet(char opt) const;
251 unsigned int isSet(const String &opt) const;
252 // value returns the String value bount to the nth instance of
253 // the flag on the command line
254 const String &value(char opt, unsigned int idx = 0) const;
255 const String &value(const String &opt, unsigned int idx = 0) const;
256 // Still not flexible enough? Here's an array of the results for
257 // your perusal.
258 const Arg_List &getArgs() const;
259
260 mike 1.12 // Miscellanous methods
261 // You can add your own error to the error list if you want
262 void addError(const String &errstr);
263 // This method gives the number of named arguments (flags)
264 // size() - flagent() == number of nonflag arguments.
265 unsigned int flagcnt() const;
266 };
267
268 inline int operator==(const Optarg& x, const Optarg& y)
269 {
270 return 0;
271 }
272
273 inline int operator==(const flagspec& x, const flagspec& y)
274 {
275 return 0;
276 }
277
278 #endif
|