00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #ifndef LLVM_SUPPORT_COMMANDLINE_H
00021 #define LLVM_SUPPORT_COMMANDLINE_H
00022
00023 #include "llvm/Support/type_traits.h"
00024 #include "llvm/Support/Compiler.h"
00025 #include "llvm/ADT/SmallVector.h"
00026 #include "llvm/ADT/Twine.h"
00027 #include <cassert>
00028 #include <climits>
00029 #include <cstdarg>
00030 #include <utility>
00031 #include <vector>
00032
00033 namespace llvm {
00034
00038 namespace cl {
00039
00040
00041
00042
00043 void ParseCommandLineOptions(int argc, char **argv,
00044 const char *Overview = 0);
00045
00046
00047
00048
00049
00050 void ParseEnvironmentOptions(const char *progName, const char *envvar,
00051 const char *Overview = 0);
00052
00058 void SetVersionPrinter(void (*func)());
00059
00067 void AddExtraVersionPrinter(void (*func)());
00068
00069
00070
00071
00072
00073
00074 void PrintOptionValues();
00075
00076
00077 void MarkOptionsChanged();
00078
00079
00080
00081
00082
00083 enum NumOccurrencesFlag {
00084 Optional = 0x01,
00085 ZeroOrMore = 0x02,
00086 Required = 0x03,
00087 OneOrMore = 0x04,
00088
00089
00090
00091
00092
00093
00094
00095
00096 ConsumeAfter = 0x05,
00097
00098 OccurrencesMask = 0x07
00099 };
00100
00101 enum ValueExpected {
00102 ValueOptional = 0x08,
00103 ValueRequired = 0x10,
00104 ValueDisallowed = 0x18,
00105 ValueMask = 0x18
00106 };
00107
00108 enum OptionHidden {
00109 NotHidden = 0x20,
00110 Hidden = 0x40,
00111 ReallyHidden = 0x60,
00112 HiddenMask = 0x60
00113 };
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130 enum FormattingFlags {
00131 NormalFormatting = 0x000,
00132 Positional = 0x080,
00133 Prefix = 0x100,
00134 Grouping = 0x180,
00135 FormattingMask = 0x180
00136 };
00137
00138 enum MiscFlags {
00139 CommaSeparated = 0x200,
00140 PositionalEatsArgs = 0x400,
00141 Sink = 0x800,
00142 MiscMask = 0xE00
00143 };
00144
00145
00146
00147
00148
00149
00150 class alias;
00151 class Option {
00152 friend class alias;
00153
00154
00155
00156
00157
00158 virtual bool handleOccurrence(unsigned pos, StringRef ArgName,
00159 StringRef Arg) = 0;
00160
00161 virtual enum ValueExpected getValueExpectedFlagDefault() const {
00162 return ValueOptional;
00163 }
00164
00165
00166 virtual void anchor();
00167
00168 int NumOccurrences;
00169 int Flags;
00170 unsigned Position;
00171 unsigned AdditionalVals;
00172 Option *NextRegistered;
00173 public:
00174 const char *ArgStr;
00175 const char *HelpStr;
00176 const char *ValueStr;
00177
00178 inline enum NumOccurrencesFlag getNumOccurrencesFlag() const {
00179 return static_cast<enum NumOccurrencesFlag>(Flags & OccurrencesMask);
00180 }
00181 inline enum ValueExpected getValueExpectedFlag() const {
00182 int VE = Flags & ValueMask;
00183 return VE ? static_cast<enum ValueExpected>(VE)
00184 : getValueExpectedFlagDefault();
00185 }
00186 inline enum OptionHidden getOptionHiddenFlag() const {
00187 return static_cast<enum OptionHidden>(Flags & HiddenMask);
00188 }
00189 inline enum FormattingFlags getFormattingFlag() const {
00190 return static_cast<enum FormattingFlags>(Flags & FormattingMask);
00191 }
00192 inline unsigned getMiscFlags() const {
00193 return Flags & MiscMask;
00194 }
00195 inline unsigned getPosition() const { return Position; }
00196 inline unsigned getNumAdditionalVals() const { return AdditionalVals; }
00197
00198
00199 bool hasArgStr() const { return ArgStr[0] != 0; }
00200
00201
00202
00203
00204 void setArgStr(const char *S) { ArgStr = S; }
00205 void setDescription(const char *S) { HelpStr = S; }
00206 void setValueStr(const char *S) { ValueStr = S; }
00207
00208 void setFlag(unsigned Flag, unsigned FlagMask) {
00209 Flags &= ~FlagMask;
00210 Flags |= Flag;
00211 }
00212
00213 void setNumOccurrencesFlag(enum NumOccurrencesFlag Val) {
00214 setFlag(Val, OccurrencesMask);
00215 }
00216 void setValueExpectedFlag(enum ValueExpected Val) { setFlag(Val, ValueMask); }
00217 void setHiddenFlag(enum OptionHidden Val) { setFlag(Val, HiddenMask); }
00218 void setFormattingFlag(enum FormattingFlags V) { setFlag(V, FormattingMask); }
00219 void setMiscFlag(enum MiscFlags M) { setFlag(M, M); }
00220 void setPosition(unsigned pos) { Position = pos; }
00221 protected:
00222 explicit Option(unsigned DefaultFlags)
00223 : NumOccurrences(0), Flags(DefaultFlags | NormalFormatting), Position(0),
00224 AdditionalVals(0), NextRegistered(0),
00225 ArgStr(""), HelpStr(""), ValueStr("") {
00226 assert(getNumOccurrencesFlag() != 0 &&
00227 getOptionHiddenFlag() != 0 && "Not all default flags specified!");
00228 }
00229
00230 inline void setNumAdditionalVals(unsigned n) { AdditionalVals = n; }
00231 public:
00232
00233
00234 void addArgument();
00235
00236 Option *getNextRegisteredOption() const { return NextRegistered; }
00237
00238
00239 virtual size_t getOptionWidth() const = 0;
00240
00241
00242
00243
00244 virtual void printOptionInfo(size_t GlobalWidth) const = 0;
00245
00246 virtual void printOptionValue(size_t GlobalWidth, bool Force) const = 0;
00247
00248 virtual void getExtraOptionNames(SmallVectorImpl<const char*> &) {}
00249
00250
00251
00252 bool addOccurrence(unsigned pos, StringRef ArgName,
00253 StringRef Value, bool MultiArg = false);
00254
00255
00256 bool error(const Twine &Message, StringRef ArgName = StringRef());
00257
00258 public:
00259 inline int getNumOccurrences() const { return NumOccurrences; }
00260 virtual ~Option() {}
00261 };
00262
00263
00264
00265
00266
00267
00268
00269
00270 struct desc {
00271 const char *Desc;
00272 desc(const char *Str) : Desc(Str) {}
00273 void apply(Option &O) const { O.setDescription(Desc); }
00274 };
00275
00276
00277
00278 struct value_desc {
00279 const char *Desc;
00280 value_desc(const char *Str) : Desc(Str) {}
00281 void apply(Option &O) const { O.setValueStr(Desc); }
00282 };
00283
00284
00285
00286
00287
00288 template<class Ty>
00289 struct initializer {
00290 const Ty &Init;
00291 initializer(const Ty &Val) : Init(Val) {}
00292
00293 template<class Opt>
00294 void apply(Opt &O) const { O.setInitialValue(Init); }
00295 };
00296
00297 template<class Ty>
00298 initializer<Ty> init(const Ty &Val) {
00299 return initializer<Ty>(Val);
00300 }
00301
00302
00303
00304
00305
00306
00307 template<class Ty>
00308 struct LocationClass {
00309 Ty &Loc;
00310 LocationClass(Ty &L) : Loc(L) {}
00311
00312 template<class Opt>
00313 void apply(Opt &O) const { O.setLocation(O, Loc); }
00314 };
00315
00316 template<class Ty>
00317 LocationClass<Ty> location(Ty &L) { return LocationClass<Ty>(L); }
00318
00319
00320
00321
00322
00323
00324 struct GenericOptionValue {
00325 virtual ~GenericOptionValue() {}
00326 virtual bool compare(const GenericOptionValue &V) const = 0;
00327 };
00328
00329 template<class DataType> struct OptionValue;
00330
00331
00332
00333 template<class DataType, bool isClass>
00334 struct OptionValueBase : public GenericOptionValue {
00335
00336 typedef OptionValue<DataType> WrapperType;
00337
00338 bool hasValue() const { return false; }
00339
00340 const DataType &getValue() const { assert(false && "no default value"); }
00341
00342
00343 template<class DT>
00344 void setValue(const DT& ) {}
00345
00346 bool compare(const DataType &) const { return false; }
00347
00348 virtual bool compare(const GenericOptionValue& ) const { return false; }
00349 };
00350
00351
00352 template<class DataType>
00353 class OptionValueCopy : public GenericOptionValue {
00354 DataType Value;
00355 bool Valid;
00356 public:
00357 OptionValueCopy() : Valid(false) {}
00358
00359 bool hasValue() const { return Valid; }
00360
00361 const DataType &getValue() const {
00362 assert(Valid && "invalid option value");
00363 return Value;
00364 }
00365
00366 void setValue(const DataType &V) { Valid = true; Value = V; }
00367
00368 bool compare(const DataType &V) const {
00369 return Valid && (Value != V);
00370 }
00371
00372 virtual bool compare(const GenericOptionValue &V) const {
00373 const OptionValueCopy<DataType> &VC =
00374 static_cast< const OptionValueCopy<DataType>& >(V);
00375 if (!VC.hasValue()) return false;
00376 return compare(VC.getValue());
00377 }
00378 };
00379
00380
00381 template<class DataType>
00382 struct OptionValueBase<DataType, false> : OptionValueCopy<DataType> {
00383 typedef DataType WrapperType;
00384 };
00385
00386
00387 template<class DataType>
00388 struct OptionValue : OptionValueBase<DataType, is_class<DataType>::value> {
00389 OptionValue() {}
00390
00391 OptionValue(const DataType& V) {
00392 this->setValue(V);
00393 }
00394
00395 template<class DT>
00396 OptionValue<DataType> &operator=(const DT& V) {
00397 this->setValue(V);
00398 return *this;
00399 }
00400 };
00401
00402
00403 enum boolOrDefault { BOU_UNSET, BOU_TRUE, BOU_FALSE };
00404 template<>
00405 struct OptionValue<cl::boolOrDefault> : OptionValueCopy<cl::boolOrDefault> {
00406 typedef cl::boolOrDefault WrapperType;
00407
00408 OptionValue() {}
00409
00410 OptionValue(const cl::boolOrDefault& V) {
00411 this->setValue(V);
00412 }
00413 OptionValue<cl::boolOrDefault> &operator=(const cl::boolOrDefault& V) {
00414 setValue(V);
00415 return *this;
00416 }
00417 };
00418
00419 template<>
00420 struct OptionValue<std::string> : OptionValueCopy<std::string> {
00421 typedef StringRef WrapperType;
00422
00423 OptionValue() {}
00424
00425 OptionValue(const std::string& V) {
00426 this->setValue(V);
00427 }
00428 OptionValue<std::string> &operator=(const std::string& V) {
00429 setValue(V);
00430 return *this;
00431 }
00432 };
00433
00434
00435
00436
00437 #define clEnumVal(ENUMVAL, DESC) #ENUMVAL, int(ENUMVAL), DESC
00438 #define clEnumValN(ENUMVAL, FLAGNAME, DESC) FLAGNAME, int(ENUMVAL), DESC
00439 #define clEnumValEnd (reinterpret_cast<void*>(0))
00440
00441
00442
00443
00444
00445
00446 template<class DataType>
00447 class ValuesClass {
00448
00449
00450
00451 SmallVector<std::pair<const char *, std::pair<int, const char *> >,4> Values;
00452 void processValues(va_list Vals);
00453 public:
00454 ValuesClass(const char *EnumName, DataType Val, const char *Desc,
00455 va_list ValueArgs) {
00456
00457 Values.push_back(std::make_pair(EnumName, std::make_pair(Val, Desc)));
00458
00459
00460 while (const char *enumName = va_arg(ValueArgs, const char *)) {
00461 DataType EnumVal = static_cast<DataType>(va_arg(ValueArgs, int));
00462 const char *EnumDesc = va_arg(ValueArgs, const char *);
00463 Values.push_back(std::make_pair(enumName,
00464 std::make_pair(EnumVal, EnumDesc)));
00465 }
00466 }
00467
00468 template<class Opt>
00469 void apply(Opt &O) const {
00470 for (unsigned i = 0, e = static_cast<unsigned>(Values.size());
00471 i != e; ++i)
00472 O.getParser().addLiteralOption(Values[i].first, Values[i].second.first,
00473 Values[i].second.second);
00474 }
00475 };
00476
00477 template<class DataType>
00478 ValuesClass<DataType> END_WITH_NULL values(const char *Arg, DataType Val,
00479 const char *Desc, ...) {
00480 va_list ValueArgs;
00481 va_start(ValueArgs, Desc);
00482 ValuesClass<DataType> Vals(Arg, Val, Desc, ValueArgs);
00483 va_end(ValueArgs);
00484 return Vals;
00485 }
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499 class generic_parser_base {
00500 protected:
00501 class GenericOptionInfo {
00502 public:
00503 GenericOptionInfo(const char *name, const char *helpStr) :
00504 Name(name), HelpStr(helpStr) {}
00505 const char *Name;
00506 const char *HelpStr;
00507 };
00508 public:
00509 virtual ~generic_parser_base() {}
00510
00511
00512
00513
00514 virtual unsigned getNumOptions() const = 0;
00515
00516
00517 virtual const char *getOption(unsigned N) const = 0;
00518
00519
00520 virtual const char *getDescription(unsigned N) const = 0;
00521
00522
00523 virtual size_t getOptionWidth(const Option &O) const;
00524
00525 virtual const GenericOptionValue &getOptionValue(unsigned N) const = 0;
00526
00527
00528
00529
00530 virtual void printOptionInfo(const Option &O, size_t GlobalWidth) const;
00531
00532 void printGenericOptionDiff(const Option &O, const GenericOptionValue &V,
00533 const GenericOptionValue &Default,
00534 size_t GlobalWidth) const;
00535
00536
00537
00538
00539
00540 template<class AnyOptionValue>
00541 void printOptionDiff(const Option &O, const AnyOptionValue &V,
00542 const AnyOptionValue &Default,
00543 size_t GlobalWidth) const {
00544 printGenericOptionDiff(O, V, Default, GlobalWidth);
00545 }
00546
00547 void initialize(Option &O) {
00548
00549
00550
00551 hasArgStr = O.hasArgStr();
00552 }
00553
00554 void getExtraOptionNames(SmallVectorImpl<const char*> &OptionNames) {
00555
00556
00557
00558 if (!hasArgStr)
00559 for (unsigned i = 0, e = getNumOptions(); i != e; ++i)
00560 OptionNames.push_back(getOption(i));
00561 }
00562
00563
00564 enum ValueExpected getValueExpectedFlagDefault() const {
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576 if (hasArgStr)
00577 return ValueRequired;
00578 else
00579 return ValueDisallowed;
00580 }
00581
00582
00583
00584
00585 unsigned findOption(const char *Name);
00586
00587 protected:
00588 bool hasArgStr;
00589 };
00590
00591
00592
00593
00594
00595
00596
00597 template <class DataType>
00598 class parser : public generic_parser_base {
00599 protected:
00600 class OptionInfo : public GenericOptionInfo {
00601 public:
00602 OptionInfo(const char *name, DataType v, const char *helpStr) :
00603 GenericOptionInfo(name, helpStr), V(v) {}
00604 OptionValue<DataType> V;
00605 };
00606 SmallVector<OptionInfo, 8> Values;
00607 public:
00608 typedef DataType parser_data_type;
00609
00610
00611 unsigned getNumOptions() const { return unsigned(Values.size()); }
00612 const char *getOption(unsigned N) const { return Values[N].Name; }
00613 const char *getDescription(unsigned N) const {
00614 return Values[N].HelpStr;
00615 }
00616
00617
00618 virtual const GenericOptionValue &getOptionValue(unsigned N) const {
00619 return Values[N].V;
00620 }
00621
00622
00623 bool parse(Option &O, StringRef ArgName, StringRef Arg, DataType &V) {
00624 StringRef ArgVal;
00625 if (hasArgStr)
00626 ArgVal = Arg;
00627 else
00628 ArgVal = ArgName;
00629
00630 for (unsigned i = 0, e = static_cast<unsigned>(Values.size());
00631 i != e; ++i)
00632 if (Values[i].Name == ArgVal) {
00633 V = Values[i].V.getValue();
00634 return false;
00635 }
00636
00637 return O.error("Cannot find option named '" + ArgVal + "'!");
00638 }
00639
00642 template <class DT>
00643 void addLiteralOption(const char *Name, const DT &V, const char *HelpStr) {
00644 assert(findOption(Name) == Values.size() && "Option already exists!");
00645 OptionInfo X(Name, static_cast<DataType>(V), HelpStr);
00646 Values.push_back(X);
00647 MarkOptionsChanged();
00648 }
00649
00652 void removeLiteralOption(const char *Name) {
00653 unsigned N = findOption(Name);
00654 assert(N != Values.size() && "Option not found!");
00655 Values.erase(Values.begin()+N);
00656 }
00657 };
00658
00659
00660
00661
00662 class basic_parser_impl {
00663 public:
00664 virtual ~basic_parser_impl() {}
00665
00666 enum ValueExpected getValueExpectedFlagDefault() const {
00667 return ValueRequired;
00668 }
00669
00670 void getExtraOptionNames(SmallVectorImpl<const char*> &) {}
00671
00672 void initialize(Option &) {}
00673
00674
00675 size_t getOptionWidth(const Option &O) const;
00676
00677
00678
00679
00680 void printOptionInfo(const Option &O, size_t GlobalWidth) const;
00681
00682
00683
00684 void printOptionNoValue(const Option &O, size_t GlobalWidth) const;
00685
00686
00687 virtual const char *getValueName() const { return "value"; }
00688
00689
00690 virtual void anchor();
00691
00692 protected:
00693
00694 void printOptionName(const Option &O, size_t GlobalWidth) const;
00695 };
00696
00697
00698
00699
00700 template<class DataType>
00701 class basic_parser : public basic_parser_impl {
00702 public:
00703 typedef DataType parser_data_type;
00704 typedef OptionValue<DataType> OptVal;
00705 };
00706
00707
00708
00709
00710 template<>
00711 class parser<bool> : public basic_parser<bool> {
00712 const char *ArgStr;
00713 public:
00714
00715
00716 bool parse(Option &O, StringRef ArgName, StringRef Arg, bool &Val);
00717
00718 template <class Opt>
00719 void initialize(Opt &O) {
00720 ArgStr = O.ArgStr;
00721 }
00722
00723 enum ValueExpected getValueExpectedFlagDefault() const {
00724 return ValueOptional;
00725 }
00726
00727
00728 virtual const char *getValueName() const { return 0; }
00729
00730 void printOptionDiff(const Option &O, bool V, OptVal Default,
00731 size_t GlobalWidth) const;
00732
00733
00734 virtual void anchor();
00735 };
00736
00737 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<bool>);
00738
00739
00740
00741 template<>
00742 class parser<boolOrDefault> : public basic_parser<boolOrDefault> {
00743 public:
00744
00745 bool parse(Option &O, StringRef ArgName, StringRef Arg, boolOrDefault &Val);
00746
00747 enum ValueExpected getValueExpectedFlagDefault() const {
00748 return ValueOptional;
00749 }
00750
00751
00752 virtual const char *getValueName() const { return 0; }
00753
00754 void printOptionDiff(const Option &O, boolOrDefault V, OptVal Default,
00755 size_t GlobalWidth) const;
00756
00757
00758 virtual void anchor();
00759 };
00760
00761 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<boolOrDefault>);
00762
00763
00764
00765
00766 template<>
00767 class parser<int> : public basic_parser<int> {
00768 public:
00769
00770 bool parse(Option &O, StringRef ArgName, StringRef Arg, int &Val);
00771
00772
00773 virtual const char *getValueName() const { return "int"; }
00774
00775 void printOptionDiff(const Option &O, int V, OptVal Default,
00776 size_t GlobalWidth) const;
00777
00778
00779 virtual void anchor();
00780 };
00781
00782 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<int>);
00783
00784
00785
00786
00787
00788 template<>
00789 class parser<unsigned> : public basic_parser<unsigned> {
00790 public:
00791
00792 bool parse(Option &O, StringRef ArgName, StringRef Arg, unsigned &Val);
00793
00794
00795 virtual const char *getValueName() const { return "uint"; }
00796
00797 void printOptionDiff(const Option &O, unsigned V, OptVal Default,
00798 size_t GlobalWidth) const;
00799
00800
00801 virtual void anchor();
00802 };
00803
00804 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<unsigned>);
00805
00806
00807
00808
00809 template<>
00810 class parser<unsigned long long> : public basic_parser<unsigned long long> {
00811 public:
00812
00813 bool parse(Option &O, StringRef ArgName, StringRef Arg,
00814 unsigned long long &Val);
00815
00816
00817 virtual const char *getValueName() const { return "uint"; }
00818
00819 void printOptionDiff(const Option &O, unsigned long long V, OptVal Default,
00820 size_t GlobalWidth) const;
00821
00822
00823 virtual void anchor();
00824 };
00825
00826 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<unsigned long long>);
00827
00828
00829
00830
00831 template<>
00832 class parser<double> : public basic_parser<double> {
00833 public:
00834
00835 bool parse(Option &O, StringRef ArgName, StringRef Arg, double &Val);
00836
00837
00838 virtual const char *getValueName() const { return "number"; }
00839
00840 void printOptionDiff(const Option &O, double V, OptVal Default,
00841 size_t GlobalWidth) const;
00842
00843
00844 virtual void anchor();
00845 };
00846
00847 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<double>);
00848
00849
00850
00851
00852 template<>
00853 class parser<float> : public basic_parser<float> {
00854 public:
00855
00856 bool parse(Option &O, StringRef ArgName, StringRef Arg, float &Val);
00857
00858
00859 virtual const char *getValueName() const { return "number"; }
00860
00861 void printOptionDiff(const Option &O, float V, OptVal Default,
00862 size_t GlobalWidth) const;
00863
00864
00865 virtual void anchor();
00866 };
00867
00868 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<float>);
00869
00870
00871
00872
00873 template<>
00874 class parser<std::string> : public basic_parser<std::string> {
00875 public:
00876
00877 bool parse(Option &, StringRef, StringRef Arg, std::string &Value) {
00878 Value = Arg.str();
00879 return false;
00880 }
00881
00882
00883 virtual const char *getValueName() const { return "string"; }
00884
00885 void printOptionDiff(const Option &O, StringRef V, OptVal Default,
00886 size_t GlobalWidth) const;
00887
00888
00889 virtual void anchor();
00890 };
00891
00892 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<std::string>);
00893
00894
00895
00896
00897 template<>
00898 class parser<char> : public basic_parser<char> {
00899 public:
00900
00901 bool parse(Option &, StringRef, StringRef Arg, char &Value) {
00902 Value = Arg[0];
00903 return false;
00904 }
00905
00906
00907 virtual const char *getValueName() const { return "char"; }
00908
00909 void printOptionDiff(const Option &O, char V, OptVal Default,
00910 size_t GlobalWidth) const;
00911
00912
00913 virtual void anchor();
00914 };
00915
00916 EXTERN_TEMPLATE_INSTANTIATION(class basic_parser<char>);
00917
00918
00919
00920
00921
00922
00923
00924
00925 template<class ParserClass, class DT>
00926 void printOptionDiff(const Option &O, const generic_parser_base &P, const DT &V,
00927 const OptionValue<DT> &Default, size_t GlobalWidth) {
00928 OptionValue<DT> OV = V;
00929 P.printOptionDiff(O, OV, Default, GlobalWidth);
00930 }
00931
00932
00933
00934 template<class ParserDT, class ValDT>
00935 struct OptionDiffPrinter {
00936 void print(const Option &O, const parser<ParserDT> P, const ValDT &,
00937 const OptionValue<ValDT> &, size_t GlobalWidth) {
00938 P.printOptionNoValue(O, GlobalWidth);
00939 }
00940 };
00941
00942
00943
00944 template<class DT>
00945 struct OptionDiffPrinter<DT, DT> {
00946 void print(const Option &O, const parser<DT> P, const DT &V,
00947 const OptionValue<DT> &Default, size_t GlobalWidth) {
00948 P.printOptionDiff(O, V, Default, GlobalWidth);
00949 }
00950 };
00951
00952
00953
00954 template<class ParserClass, class ValDT>
00955 void printOptionDiff(
00956 const Option &O,
00957 const basic_parser<typename ParserClass::parser_data_type> &P,
00958 const ValDT &V, const OptionValue<ValDT> &Default,
00959 size_t GlobalWidth) {
00960
00961 OptionDiffPrinter<typename ParserClass::parser_data_type, ValDT> printer;
00962 printer.print(O, static_cast<const ParserClass&>(P), V, Default,
00963 GlobalWidth);
00964 }
00965
00966
00967
00968
00969
00970
00971
00972 template<class Mod> struct applicator {
00973 template<class Opt>
00974 static void opt(const Mod &M, Opt &O) { M.apply(O); }
00975 };
00976
00977
00978 template<unsigned n> struct applicator<char[n]> {
00979 template<class Opt>
00980 static void opt(const char *Str, Opt &O) { O.setArgStr(Str); }
00981 };
00982 template<unsigned n> struct applicator<const char[n]> {
00983 template<class Opt>
00984 static void opt(const char *Str, Opt &O) { O.setArgStr(Str); }
00985 };
00986 template<> struct applicator<const char*> {
00987 template<class Opt>
00988 static void opt(const char *Str, Opt &O) { O.setArgStr(Str); }
00989 };
00990
00991 template<> struct applicator<NumOccurrencesFlag> {
00992 static void opt(NumOccurrencesFlag NO, Option &O) {
00993 O.setNumOccurrencesFlag(NO);
00994 }
00995 };
00996 template<> struct applicator<ValueExpected> {
00997 static void opt(ValueExpected VE, Option &O) { O.setValueExpectedFlag(VE); }
00998 };
00999 template<> struct applicator<OptionHidden> {
01000 static void opt(OptionHidden OH, Option &O) { O.setHiddenFlag(OH); }
01001 };
01002 template<> struct applicator<FormattingFlags> {
01003 static void opt(FormattingFlags FF, Option &O) { O.setFormattingFlag(FF); }
01004 };
01005 template<> struct applicator<MiscFlags> {
01006 static void opt(MiscFlags MF, Option &O) { O.setMiscFlag(MF); }
01007 };
01008
01009
01010 template<class Mod, class Opt>
01011 void apply(const Mod &M, Opt *O) {
01012 applicator<Mod>::opt(M, *O);
01013 }
01014
01015
01016
01017
01018
01019
01020
01021
01022 template<class DataType, bool ExternalStorage, bool isClass>
01023 class opt_storage {
01024 DataType *Location;
01025 OptionValue<DataType> Default;
01026
01027 void check() const {
01028 assert(Location != 0 && "cl::location(...) not specified for a command "
01029 "line option with external storage, "
01030 "or cl::init specified before cl::location()!!");
01031 }
01032 public:
01033 opt_storage() : Location(0) {}
01034
01035 bool setLocation(Option &O, DataType &L) {
01036 if (Location)
01037 return O.error("cl::location(x) specified more than once!");
01038 Location = &L;
01039 Default = L;
01040 return false;
01041 }
01042
01043 template<class T>
01044 void setValue(const T &V, bool initial = false) {
01045 check();
01046 *Location = V;
01047 if (initial)
01048 Default = V;
01049 }
01050
01051 DataType &getValue() { check(); return *Location; }
01052 const DataType &getValue() const { check(); return *Location; }
01053
01054 operator DataType() const { return this->getValue(); }
01055
01056 const OptionValue<DataType> &getDefault() const { return Default; }
01057 };
01058
01059
01060
01061
01062
01063 template<class DataType>
01064 class opt_storage<DataType,false,true> : public DataType {
01065 public:
01066 OptionValue<DataType> Default;
01067
01068 template<class T>
01069 void setValue(const T &V, bool initial = false) {
01070 DataType::operator=(V);
01071 if (initial)
01072 Default = V;
01073 }
01074
01075 DataType &getValue() { return *this; }
01076 const DataType &getValue() const { return *this; }
01077
01078 const OptionValue<DataType> &getDefault() const { return Default; }
01079 };
01080
01081
01082
01083
01084
01085 template<class DataType>
01086 class opt_storage<DataType, false, false> {
01087 public:
01088 DataType Value;
01089 OptionValue<DataType> Default;
01090
01091
01092
01093 opt_storage() : Value(DataType()) {}
01094
01095 template<class T>
01096 void setValue(const T &V, bool initial = false) {
01097 Value = V;
01098 if (initial)
01099 Default = V;
01100 }
01101 DataType &getValue() { return Value; }
01102 DataType getValue() const { return Value; }
01103
01104 const OptionValue<DataType> &getDefault() const { return Default; }
01105
01106 operator DataType() const { return getValue(); }
01107
01108
01109 DataType operator->() const { return Value; }
01110 };
01111
01112
01113
01114
01115
01116 template <class DataType, bool ExternalStorage = false,
01117 class ParserClass = parser<DataType> >
01118 class opt : public Option,
01119 public opt_storage<DataType, ExternalStorage,
01120 is_class<DataType>::value> {
01121 ParserClass Parser;
01122
01123 virtual bool handleOccurrence(unsigned pos, StringRef ArgName,
01124 StringRef Arg) {
01125 typename ParserClass::parser_data_type Val =
01126 typename ParserClass::parser_data_type();
01127 if (Parser.parse(*this, ArgName, Arg, Val))
01128 return true;
01129 this->setValue(Val);
01130 this->setPosition(pos);
01131 return false;
01132 }
01133
01134 virtual enum ValueExpected getValueExpectedFlagDefault() const {
01135 return Parser.getValueExpectedFlagDefault();
01136 }
01137 virtual void getExtraOptionNames(SmallVectorImpl<const char*> &OptionNames) {
01138 return Parser.getExtraOptionNames(OptionNames);
01139 }
01140
01141
01142 virtual size_t getOptionWidth() const {return Parser.getOptionWidth(*this);}
01143 virtual void printOptionInfo(size_t GlobalWidth) const {
01144 Parser.printOptionInfo(*this, GlobalWidth);
01145 }
01146
01147 virtual void printOptionValue(size_t GlobalWidth, bool Force) const {
01148 if (Force || this->getDefault().compare(this->getValue())) {
01149 cl::printOptionDiff<ParserClass>(
01150 *this, Parser, this->getValue(), this->getDefault(), GlobalWidth);
01151 }
01152 }
01153
01154 void done() {
01155 addArgument();
01156 Parser.initialize(*this);
01157 }
01158 public:
01159
01160 void setInitialValue(const DataType &V) { this->setValue(V, true); }
01161
01162 ParserClass &getParser() { return Parser; }
01163
01164 template<class T>
01165 DataType &operator=(const T &Val) {
01166 this->setValue(Val);
01167 return this->getValue();
01168 }
01169
01170
01171 template<class M0t>
01172 explicit opt(const M0t &M0) : Option(Optional | NotHidden) {
01173 apply(M0, this);
01174 done();
01175 }
01176
01177
01178 template<class M0t, class M1t>
01179 opt(const M0t &M0, const M1t &M1) : Option(Optional | NotHidden) {
01180 apply(M0, this); apply(M1, this);
01181 done();
01182 }
01183
01184
01185 template<class M0t, class M1t, class M2t>
01186 opt(const M0t &M0, const M1t &M1,
01187 const M2t &M2) : Option(Optional | NotHidden) {
01188 apply(M0, this); apply(M1, this); apply(M2, this);
01189 done();
01190 }
01191
01192 template<class M0t, class M1t, class M2t, class M3t>
01193 opt(const M0t &M0, const M1t &M1, const M2t &M2,
01194 const M3t &M3) : Option(Optional | NotHidden) {
01195 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01196 done();
01197 }
01198
01199 template<class M0t, class M1t, class M2t, class M3t, class M4t>
01200 opt(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01201 const M4t &M4) : Option(Optional | NotHidden) {
01202 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01203 apply(M4, this);
01204 done();
01205 }
01206
01207 template<class M0t, class M1t, class M2t, class M3t,
01208 class M4t, class M5t>
01209 opt(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01210 const M4t &M4, const M5t &M5) : Option(Optional | NotHidden) {
01211 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01212 apply(M4, this); apply(M5, this);
01213 done();
01214 }
01215
01216 template<class M0t, class M1t, class M2t, class M3t,
01217 class M4t, class M5t, class M6t>
01218 opt(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01219 const M4t &M4, const M5t &M5,
01220 const M6t &M6) : Option(Optional | NotHidden) {
01221 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01222 apply(M4, this); apply(M5, this); apply(M6, this);
01223 done();
01224 }
01225
01226 template<class M0t, class M1t, class M2t, class M3t,
01227 class M4t, class M5t, class M6t, class M7t>
01228 opt(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01229 const M4t &M4, const M5t &M5, const M6t &M6,
01230 const M7t &M7) : Option(Optional | NotHidden) {
01231 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01232 apply(M4, this); apply(M5, this); apply(M6, this); apply(M7, this);
01233 done();
01234 }
01235 };
01236
01237 EXTERN_TEMPLATE_INSTANTIATION(class opt<unsigned>);
01238 EXTERN_TEMPLATE_INSTANTIATION(class opt<int>);
01239 EXTERN_TEMPLATE_INSTANTIATION(class opt<std::string>);
01240 EXTERN_TEMPLATE_INSTANTIATION(class opt<char>);
01241 EXTERN_TEMPLATE_INSTANTIATION(class opt<bool>);
01242
01243
01244
01245
01246
01247
01248
01249
01250 template<class DataType, class StorageClass>
01251 class list_storage {
01252 StorageClass *Location;
01253
01254 public:
01255 list_storage() : Location(0) {}
01256
01257 bool setLocation(Option &O, StorageClass &L) {
01258 if (Location)
01259 return O.error("cl::location(x) specified more than once!");
01260 Location = &L;
01261 return false;
01262 }
01263
01264 template<class T>
01265 void addValue(const T &V) {
01266 assert(Location != 0 && "cl::location(...) not specified for a command "
01267 "line option with external storage!");
01268 Location->push_back(V);
01269 }
01270 };
01271
01272
01273
01274
01275
01276
01277 template<class DataType>
01278 class list_storage<DataType, bool> : public std::vector<DataType> {
01279 public:
01280 template<class T>
01281 void addValue(const T &V) { std::vector<DataType>::push_back(V); }
01282 };
01283
01284
01285
01286
01287
01288 template <class DataType, class Storage = bool,
01289 class ParserClass = parser<DataType> >
01290 class list : public Option, public list_storage<DataType, Storage> {
01291 std::vector<unsigned> Positions;
01292 ParserClass Parser;
01293
01294 virtual enum ValueExpected getValueExpectedFlagDefault() const {
01295 return Parser.getValueExpectedFlagDefault();
01296 }
01297 virtual void getExtraOptionNames(SmallVectorImpl<const char*> &OptionNames) {
01298 return Parser.getExtraOptionNames(OptionNames);
01299 }
01300
01301 virtual bool handleOccurrence(unsigned pos, StringRef ArgName, StringRef Arg){
01302 typename ParserClass::parser_data_type Val =
01303 typename ParserClass::parser_data_type();
01304 if (Parser.parse(*this, ArgName, Arg, Val))
01305 return true;
01306 list_storage<DataType, Storage>::addValue(Val);
01307 setPosition(pos);
01308 Positions.push_back(pos);
01309 return false;
01310 }
01311
01312
01313 virtual size_t getOptionWidth() const {return Parser.getOptionWidth(*this);}
01314 virtual void printOptionInfo(size_t GlobalWidth) const {
01315 Parser.printOptionInfo(*this, GlobalWidth);
01316 }
01317
01318
01319 virtual void printOptionValue(size_t , bool ) const {}
01320
01321 void done() {
01322 addArgument();
01323 Parser.initialize(*this);
01324 }
01325 public:
01326 ParserClass &getParser() { return Parser; }
01327
01328 unsigned getPosition(unsigned optnum) const {
01329 assert(optnum < this->size() && "Invalid option index");
01330 return Positions[optnum];
01331 }
01332
01333 void setNumAdditionalVals(unsigned n) {
01334 Option::setNumAdditionalVals(n);
01335 }
01336
01337
01338 template<class M0t>
01339 explicit list(const M0t &M0) : Option(ZeroOrMore | NotHidden) {
01340 apply(M0, this);
01341 done();
01342 }
01343
01344 template<class M0t, class M1t>
01345 list(const M0t &M0, const M1t &M1) : Option(ZeroOrMore | NotHidden) {
01346 apply(M0, this); apply(M1, this);
01347 done();
01348 }
01349
01350 template<class M0t, class M1t, class M2t>
01351 list(const M0t &M0, const M1t &M1, const M2t &M2)
01352 : Option(ZeroOrMore | NotHidden) {
01353 apply(M0, this); apply(M1, this); apply(M2, this);
01354 done();
01355 }
01356
01357 template<class M0t, class M1t, class M2t, class M3t>
01358 list(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3)
01359 : Option(ZeroOrMore | NotHidden) {
01360 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01361 done();
01362 }
01363
01364 template<class M0t, class M1t, class M2t, class M3t, class M4t>
01365 list(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01366 const M4t &M4) : Option(ZeroOrMore | NotHidden) {
01367 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01368 apply(M4, this);
01369 done();
01370 }
01371
01372 template<class M0t, class M1t, class M2t, class M3t,
01373 class M4t, class M5t>
01374 list(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01375 const M4t &M4, const M5t &M5) : Option(ZeroOrMore | NotHidden) {
01376 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01377 apply(M4, this); apply(M5, this);
01378 done();
01379 }
01380
01381 template<class M0t, class M1t, class M2t, class M3t,
01382 class M4t, class M5t, class M6t>
01383 list(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01384 const M4t &M4, const M5t &M5, const M6t &M6)
01385 : Option(ZeroOrMore | NotHidden) {
01386 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01387 apply(M4, this); apply(M5, this); apply(M6, this);
01388 done();
01389 }
01390
01391 template<class M0t, class M1t, class M2t, class M3t,
01392 class M4t, class M5t, class M6t, class M7t>
01393 list(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01394 const M4t &M4, const M5t &M5, const M6t &M6,
01395 const M7t &M7) : Option(ZeroOrMore | NotHidden) {
01396 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01397 apply(M4, this); apply(M5, this); apply(M6, this); apply(M7, this);
01398 done();
01399 }
01400 };
01401
01402
01403 struct multi_val {
01404 unsigned AdditionalVals;
01405 explicit multi_val(unsigned N) : AdditionalVals(N) {}
01406
01407 template <typename D, typename S, typename P>
01408 void apply(list<D, S, P> &L) const { L.setNumAdditionalVals(AdditionalVals); }
01409 };
01410
01411
01412
01413
01414
01415
01416
01417
01418
01419 template<class DataType, class StorageClass>
01420 class bits_storage {
01421 unsigned *Location;
01422
01423 template<class T>
01424 static unsigned Bit(const T &V) {
01425 unsigned BitPos = reinterpret_cast<unsigned>(V);
01426 assert(BitPos < sizeof(unsigned) * CHAR_BIT &&
01427 "enum exceeds width of bit vector!");
01428 return 1 << BitPos;
01429 }
01430
01431 public:
01432 bits_storage() : Location(0) {}
01433
01434 bool setLocation(Option &O, unsigned &L) {
01435 if (Location)
01436 return O.error("cl::location(x) specified more than once!");
01437 Location = &L;
01438 return false;
01439 }
01440
01441 template<class T>
01442 void addValue(const T &V) {
01443 assert(Location != 0 && "cl::location(...) not specified for a command "
01444 "line option with external storage!");
01445 *Location |= Bit(V);
01446 }
01447
01448 unsigned getBits() { return *Location; }
01449
01450 template<class T>
01451 bool isSet(const T &V) {
01452 return (*Location & Bit(V)) != 0;
01453 }
01454 };
01455
01456
01457
01458
01459
01460 template<class DataType>
01461 class bits_storage<DataType, bool> {
01462 unsigned Bits;
01463
01464 template<class T>
01465 static unsigned Bit(const T &V) {
01466 unsigned BitPos = (unsigned)V;
01467 assert(BitPos < sizeof(unsigned) * CHAR_BIT &&
01468 "enum exceeds width of bit vector!");
01469 return 1 << BitPos;
01470 }
01471
01472 public:
01473 template<class T>
01474 void addValue(const T &V) {
01475 Bits |= Bit(V);
01476 }
01477
01478 unsigned getBits() { return Bits; }
01479
01480 template<class T>
01481 bool isSet(const T &V) {
01482 return (Bits & Bit(V)) != 0;
01483 }
01484 };
01485
01486
01487
01488
01489
01490 template <class DataType, class Storage = bool,
01491 class ParserClass = parser<DataType> >
01492 class bits : public Option, public bits_storage<DataType, Storage> {
01493 std::vector<unsigned> Positions;
01494 ParserClass Parser;
01495
01496 virtual enum ValueExpected getValueExpectedFlagDefault() const {
01497 return Parser.getValueExpectedFlagDefault();
01498 }
01499 virtual void getExtraOptionNames(SmallVectorImpl<const char*> &OptionNames) {
01500 return Parser.getExtraOptionNames(OptionNames);
01501 }
01502
01503 virtual bool handleOccurrence(unsigned pos, StringRef ArgName, StringRef Arg){
01504 typename ParserClass::parser_data_type Val =
01505 typename ParserClass::parser_data_type();
01506 if (Parser.parse(*this, ArgName, Arg, Val))
01507 return true;
01508 addValue(Val);
01509 setPosition(pos);
01510 Positions.push_back(pos);
01511 return false;
01512 }
01513
01514
01515 virtual size_t getOptionWidth() const {return Parser.getOptionWidth(*this);}
01516 virtual void printOptionInfo(size_t GlobalWidth) const {
01517 Parser.printOptionInfo(*this, GlobalWidth);
01518 }
01519
01520
01521 virtual void printOptionValue(size_t , bool ) const {}
01522
01523 void done() {
01524 addArgument();
01525 Parser.initialize(*this);
01526 }
01527 public:
01528 ParserClass &getParser() { return Parser; }
01529
01530 unsigned getPosition(unsigned optnum) const {
01531 assert(optnum < this->size() && "Invalid option index");
01532 return Positions[optnum];
01533 }
01534
01535
01536 template<class M0t>
01537 explicit bits(const M0t &M0) : Option(ZeroOrMore | NotHidden) {
01538 apply(M0, this);
01539 done();
01540 }
01541
01542 template<class M0t, class M1t>
01543 bits(const M0t &M0, const M1t &M1) : Option(ZeroOrMore | NotHidden) {
01544 apply(M0, this); apply(M1, this);
01545 done();
01546 }
01547
01548 template<class M0t, class M1t, class M2t>
01549 bits(const M0t &M0, const M1t &M1, const M2t &M2)
01550 : Option(ZeroOrMore | NotHidden) {
01551 apply(M0, this); apply(M1, this); apply(M2, this);
01552 done();
01553 }
01554
01555 template<class M0t, class M1t, class M2t, class M3t>
01556 bits(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3)
01557 : Option(ZeroOrMore | NotHidden) {
01558 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01559 done();
01560 }
01561
01562 template<class M0t, class M1t, class M2t, class M3t, class M4t>
01563 bits(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01564 const M4t &M4) : Option(ZeroOrMore | NotHidden) {
01565 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01566 apply(M4, this);
01567 done();
01568 }
01569
01570 template<class M0t, class M1t, class M2t, class M3t,
01571 class M4t, class M5t>
01572 bits(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01573 const M4t &M4, const M5t &M5) : Option(ZeroOrMore | NotHidden) {
01574 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01575 apply(M4, this); apply(M5, this);
01576 done();
01577 }
01578
01579 template<class M0t, class M1t, class M2t, class M3t,
01580 class M4t, class M5t, class M6t>
01581 bits(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01582 const M4t &M4, const M5t &M5, const M6t &M6)
01583 : Option(ZeroOrMore | NotHidden) {
01584 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01585 apply(M4, this); apply(M5, this); apply(M6, this);
01586 done();
01587 }
01588
01589 template<class M0t, class M1t, class M2t, class M3t,
01590 class M4t, class M5t, class M6t, class M7t>
01591 bits(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3,
01592 const M4t &M4, const M5t &M5, const M6t &M6,
01593 const M7t &M7) : Option(ZeroOrMore | NotHidden) {
01594 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01595 apply(M4, this); apply(M5, this); apply(M6, this); apply(M7, this);
01596 done();
01597 }
01598 };
01599
01600
01601
01602
01603
01604 class alias : public Option {
01605 Option *AliasFor;
01606 virtual bool handleOccurrence(unsigned pos, StringRef ,
01607 StringRef Arg) {
01608 return AliasFor->handleOccurrence(pos, AliasFor->ArgStr, Arg);
01609 }
01610
01611 virtual size_t getOptionWidth() const;
01612 virtual void printOptionInfo(size_t GlobalWidth) const;
01613
01614
01615 virtual void printOptionValue(size_t , bool ) const {}
01616
01617 void done() {
01618 if (!hasArgStr())
01619 error("cl::alias must have argument name specified!");
01620 if (AliasFor == 0)
01621 error("cl::alias must have an cl::aliasopt(option) specified!");
01622 addArgument();
01623 }
01624 public:
01625 void setAliasFor(Option &O) {
01626 if (AliasFor)
01627 error("cl::alias must only have one cl::aliasopt(...) specified!");
01628 AliasFor = &O;
01629 }
01630
01631
01632 template<class M0t>
01633 explicit alias(const M0t &M0) : Option(Optional | Hidden), AliasFor(0) {
01634 apply(M0, this);
01635 done();
01636 }
01637
01638 template<class M0t, class M1t>
01639 alias(const M0t &M0, const M1t &M1) : Option(Optional | Hidden), AliasFor(0) {
01640 apply(M0, this); apply(M1, this);
01641 done();
01642 }
01643
01644 template<class M0t, class M1t, class M2t>
01645 alias(const M0t &M0, const M1t &M1, const M2t &M2)
01646 : Option(Optional | Hidden), AliasFor(0) {
01647 apply(M0, this); apply(M1, this); apply(M2, this);
01648 done();
01649 }
01650
01651 template<class M0t, class M1t, class M2t, class M3t>
01652 alias(const M0t &M0, const M1t &M1, const M2t &M2, const M3t &M3)
01653 : Option(Optional | Hidden), AliasFor(0) {
01654 apply(M0, this); apply(M1, this); apply(M2, this); apply(M3, this);
01655 done();
01656 }
01657 };
01658
01659
01660 struct aliasopt {
01661 Option &Opt;
01662 explicit aliasopt(Option &O) : Opt(O) {}
01663 void apply(alias &A) const { A.setAliasFor(Opt); }
01664 };
01665
01666
01667
01668
01669
01670 struct extrahelp {
01671 const char * morehelp;
01672 explicit extrahelp(const char* help);
01673 };
01674
01675 void PrintVersionMessage();
01676
01677
01678
01679 void PrintHelpMessage();
01680
01681 }
01682
01683 }
01684
01685 #endif