ArgList.h 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459
  1. //===--- ArgList.h - Argument List Management -------------------*- C++ -*-===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. #ifndef LLVM_OPTION_ARGLIST_H
  10. #define LLVM_OPTION_ARGLIST_H
  11. #include "llvm/ADT/SmallVector.h"
  12. #include "llvm/ADT/SmallString.h"
  13. #include "llvm/ADT/StringRef.h"
  14. #include "llvm/ADT/Twine.h"
  15. #include "llvm/Option/Arg.h"
  16. #include "llvm/Option/OptSpecifier.h"
  17. #include "llvm/Option/Option.h"
  18. #include <list>
  19. #include <memory>
  20. #include <string>
  21. #include <vector>
  22. namespace llvm {
  23. namespace opt {
  24. class ArgList;
  25. class Option;
  26. /// arg_iterator - Iterates through arguments stored inside an ArgList.
  27. class arg_iterator {
  28. /// The current argument.
  29. SmallVectorImpl<Arg*>::const_iterator Current;
  30. /// The argument list we are iterating over.
  31. const ArgList &Args;
  32. /// Optional filters on the arguments which will be match. Most clients
  33. /// should never want to iterate over arguments without filters, so we won't
  34. /// bother to factor this into two separate iterator implementations.
  35. //
  36. // FIXME: Make efficient; the idea is to provide efficient iteration over
  37. // all arguments which match a particular id and then just provide an
  38. // iterator combinator which takes multiple iterators which can be
  39. // efficiently compared and returns them in order.
  40. OptSpecifier Id0, Id1, Id2;
  41. void SkipToNextArg();
  42. public:
  43. typedef Arg * const * value_type;
  44. typedef Arg * const & reference;
  45. typedef Arg * const * pointer;
  46. typedef std::forward_iterator_tag iterator_category;
  47. typedef std::ptrdiff_t difference_type;
  48. arg_iterator(SmallVectorImpl<Arg *>::const_iterator it, const ArgList &Args,
  49. OptSpecifier Id0 = 0U, OptSpecifier Id1 = 0U,
  50. OptSpecifier Id2 = 0U)
  51. : Current(it), Args(Args), Id0(Id0), Id1(Id1), Id2(Id2) {
  52. SkipToNextArg();
  53. }
  54. operator const Arg*() { return *Current; }
  55. reference operator*() const { return *Current; }
  56. pointer operator->() const { return Current; }
  57. arg_iterator &operator++() {
  58. ++Current;
  59. SkipToNextArg();
  60. return *this;
  61. }
  62. arg_iterator operator++(int) {
  63. arg_iterator tmp(*this);
  64. ++(*this);
  65. return tmp;
  66. }
  67. friend bool operator==(arg_iterator LHS, arg_iterator RHS) {
  68. return LHS.Current == RHS.Current;
  69. }
  70. friend bool operator!=(arg_iterator LHS, arg_iterator RHS) {
  71. return !(LHS == RHS);
  72. }
  73. };
  74. /// ArgList - Ordered collection of driver arguments.
  75. ///
  76. /// The ArgList class manages a list of Arg instances as well as
  77. /// auxiliary data and convenience methods to allow Tools to quickly
  78. /// check for the presence of Arg instances for a particular Option
  79. /// and to iterate over groups of arguments.
  80. class ArgList {
  81. public:
  82. typedef SmallVector<Arg*, 16> arglist_type;
  83. typedef arglist_type::iterator iterator;
  84. typedef arglist_type::const_iterator const_iterator;
  85. typedef arglist_type::reverse_iterator reverse_iterator;
  86. typedef arglist_type::const_reverse_iterator const_reverse_iterator;
  87. private:
  88. /// The internal list of arguments.
  89. arglist_type Args;
  90. protected:
  91. // Make the default special members protected so they won't be used to slice
  92. // derived objects, but can still be used by derived objects to implement
  93. // their own special members.
  94. ArgList() = default;
  95. // Explicit move operations to ensure the container is cleared post-move
  96. // otherwise it could lead to a double-delete in the case of moving of an
  97. // InputArgList which deletes the contents of the container. If we could fix
  98. // up the ownership here (delegate storage/ownership to the derived class so
  99. // it can be a container of unique_ptr) this would be simpler.
  100. ArgList(ArgList &&RHS) : Args(std::move(RHS.Args)) { RHS.Args.clear(); }
  101. ArgList &operator=(ArgList &&RHS) {
  102. Args = std::move(RHS.Args);
  103. RHS.Args.clear();
  104. return *this;
  105. }
  106. // Protect the dtor to ensure this type is never destroyed polymorphically.
  107. ~ArgList() = default;
  108. public:
  109. /// @name Arg Access
  110. /// @{
  111. /// append - Append \p A to the arg list.
  112. void append(Arg *A);
  113. arglist_type &getArgs() { return Args; }
  114. const arglist_type &getArgs() const { return Args; }
  115. unsigned size() const { return Args.size(); }
  116. /// @}
  117. /// @name Arg Iteration
  118. /// @{
  119. iterator begin() { return Args.begin(); }
  120. iterator end() { return Args.end(); }
  121. reverse_iterator rbegin() { return Args.rbegin(); }
  122. reverse_iterator rend() { return Args.rend(); }
  123. const_iterator begin() const { return Args.begin(); }
  124. const_iterator end() const { return Args.end(); }
  125. const_reverse_iterator rbegin() const { return Args.rbegin(); }
  126. const_reverse_iterator rend() const { return Args.rend(); }
  127. arg_iterator filtered_begin(OptSpecifier Id0 = 0U, OptSpecifier Id1 = 0U,
  128. OptSpecifier Id2 = 0U) const {
  129. return arg_iterator(Args.begin(), *this, Id0, Id1, Id2);
  130. }
  131. arg_iterator filtered_end() const {
  132. return arg_iterator(Args.end(), *this);
  133. }
  134. iterator_range<arg_iterator> filtered(OptSpecifier Id0 = 0U,
  135. OptSpecifier Id1 = 0U,
  136. OptSpecifier Id2 = 0U) const {
  137. return make_range(filtered_begin(Id0, Id1, Id2), filtered_end());
  138. }
  139. /// @}
  140. /// @name Arg Removal
  141. /// @{
  142. /// eraseArg - Remove any option matching \p Id.
  143. void eraseArg(OptSpecifier Id);
  144. /// @}
  145. /// @name Arg Access
  146. /// @{
  147. /// hasArg - Does the arg list contain any option matching \p Id.
  148. ///
  149. /// \p Claim Whether the argument should be claimed, if it exists.
  150. bool hasArgNoClaim(OptSpecifier Id) const {
  151. return getLastArgNoClaim(Id) != nullptr;
  152. }
  153. bool hasArg(OptSpecifier Id) const {
  154. return getLastArg(Id) != nullptr;
  155. }
  156. bool hasArg(OptSpecifier Id0, OptSpecifier Id1) const {
  157. return getLastArg(Id0, Id1) != nullptr;
  158. }
  159. bool hasArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2) const {
  160. return getLastArg(Id0, Id1, Id2) != nullptr;
  161. }
  162. /// getLastArg - Return the last argument matching \p Id, or null.
  163. ///
  164. /// \p Claim Whether the argument should be claimed, if it exists.
  165. Arg *getLastArgNoClaim(OptSpecifier Id) const;
  166. Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1) const;
  167. Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1,
  168. OptSpecifier Id2) const;
  169. Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  170. OptSpecifier Id3) const;
  171. Arg *getLastArg(OptSpecifier Id) const;
  172. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1) const;
  173. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2) const;
  174. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  175. OptSpecifier Id3) const;
  176. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  177. OptSpecifier Id3, OptSpecifier Id4) const;
  178. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  179. OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5) const;
  180. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  181. OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5,
  182. OptSpecifier Id6) const;
  183. Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
  184. OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5,
  185. OptSpecifier Id6, OptSpecifier Id7) const;
  186. /// getArgString - Return the input argument string at \p Index.
  187. virtual const char *getArgString(unsigned Index) const = 0;
  188. /// getNumInputArgStrings - Return the number of original argument strings,
  189. /// which are guaranteed to be the first strings in the argument string
  190. /// list.
  191. virtual unsigned getNumInputArgStrings() const = 0;
  192. /// @}
  193. /// @name Argument Lookup Utilities
  194. /// @{
  195. /// getLastArgValue - Return the value of the last argument, or a default.
  196. StringRef getLastArgValue(OptSpecifier Id,
  197. StringRef Default = "") const;
  198. /// getAllArgValues - Get the values of all instances of the given argument
  199. /// as strings.
  200. std::vector<std::string> getAllArgValues(OptSpecifier Id) const;
  201. /// @}
  202. /// @name Translation Utilities
  203. /// @{
  204. /// hasFlag - Given an option \p Pos and its negative form \p Neg, return
  205. /// true if the option is present, false if the negation is present, and
  206. /// \p Default if neither option is given. If both the option and its
  207. /// negation are present, the last one wins.
  208. bool hasFlag(OptSpecifier Pos, OptSpecifier Neg, bool Default=true) const;
  209. /// hasFlag - Given an option \p Pos, an alias \p PosAlias and its negative
  210. /// form \p Neg, return true if the option or its alias is present, false if
  211. /// the negation is present, and \p Default if none of the options are
  212. /// given. If multiple options are present, the last one wins.
  213. bool hasFlag(OptSpecifier Pos, OptSpecifier PosAlias, OptSpecifier Neg,
  214. bool Default = true) const;
  215. /// AddLastArg - Render only the last argument match \p Id0, if present.
  216. void AddLastArg(ArgStringList &Output, OptSpecifier Id0) const;
  217. void AddLastArg(ArgStringList &Output, OptSpecifier Id0,
  218. OptSpecifier Id1) const;
  219. /// AddAllArgs - Render all arguments matching the given ids.
  220. void AddAllArgs(ArgStringList &Output, OptSpecifier Id0,
  221. OptSpecifier Id1 = 0U, OptSpecifier Id2 = 0U) const;
  222. /// AddAllArgValues - Render the argument values of all arguments
  223. /// matching the given ids.
  224. void AddAllArgValues(ArgStringList &Output, OptSpecifier Id0,
  225. OptSpecifier Id1 = 0U, OptSpecifier Id2 = 0U) const;
  226. /// AddAllArgsTranslated - Render all the arguments matching the
  227. /// given ids, but forced to separate args and using the provided
  228. /// name instead of the first option value.
  229. ///
  230. /// \param Joined - If true, render the argument as joined with
  231. /// the option specifier.
  232. void AddAllArgsTranslated(ArgStringList &Output, OptSpecifier Id0,
  233. const char *Translation,
  234. bool Joined = false) const;
  235. /// ClaimAllArgs - Claim all arguments which match the given
  236. /// option id.
  237. void ClaimAllArgs(OptSpecifier Id0) const;
  238. /// ClaimAllArgs - Claim all arguments.
  239. ///
  240. void ClaimAllArgs() const;
  241. /// @}
  242. /// @name Arg Synthesis
  243. /// @{
  244. /// Construct a constant string pointer whose
  245. /// lifetime will match that of the ArgList.
  246. virtual const char *MakeArgStringRef(StringRef Str) const = 0;
  247. const char *MakeArgString(const Twine &Str) const {
  248. SmallString<256> Buf;
  249. return MakeArgStringRef(Str.toStringRef(Buf));
  250. }
  251. /// \brief Create an arg string for (\p LHS + \p RHS), reusing the
  252. /// string at \p Index if possible.
  253. const char *GetOrMakeJoinedArgString(unsigned Index, StringRef LHS,
  254. StringRef RHS) const;
  255. /// @}
  256. };
  257. class InputArgList final : public ArgList {
  258. private:
  259. /// List of argument strings used by the contained Args.
  260. ///
  261. /// This is mutable since we treat the ArgList as being the list
  262. /// of Args, and allow routines to add new strings (to have a
  263. /// convenient place to store the memory) via MakeIndex.
  264. mutable ArgStringList ArgStrings;
  265. /// Strings for synthesized arguments.
  266. ///
  267. /// This is mutable since we treat the ArgList as being the list
  268. /// of Args, and allow routines to add new strings (to have a
  269. /// convenient place to store the memory) via MakeIndex.
  270. mutable std::list<std::string> SynthesizedStrings;
  271. /// The number of original input argument strings.
  272. unsigned NumInputArgStrings;
  273. /// Release allocated arguments.
  274. void releaseMemory();
  275. public:
  276. InputArgList(const char* const *ArgBegin, const char* const *ArgEnd);
  277. InputArgList(InputArgList &&RHS)
  278. : ArgList(std::move(RHS)), ArgStrings(std::move(RHS.ArgStrings)),
  279. SynthesizedStrings(std::move(RHS.SynthesizedStrings)),
  280. NumInputArgStrings(RHS.NumInputArgStrings) {}
  281. InputArgList &operator=(InputArgList &&RHS) {
  282. releaseMemory();
  283. ArgList::operator=(std::move(RHS));
  284. ArgStrings = std::move(RHS.ArgStrings);
  285. SynthesizedStrings = std::move(RHS.SynthesizedStrings);
  286. NumInputArgStrings = RHS.NumInputArgStrings;
  287. return *this;
  288. }
  289. ~InputArgList() { releaseMemory(); }
  290. const char *getArgString(unsigned Index) const override {
  291. return ArgStrings[Index];
  292. }
  293. unsigned getNumInputArgStrings() const override {
  294. return NumInputArgStrings;
  295. }
  296. /// @name Arg Synthesis
  297. /// @{
  298. public:
  299. /// MakeIndex - Get an index for the given string(s).
  300. unsigned MakeIndex(StringRef String0) const;
  301. unsigned MakeIndex(StringRef String0, StringRef String1) const;
  302. using ArgList::MakeArgString;
  303. const char *MakeArgStringRef(StringRef Str) const override;
  304. /// @}
  305. };
  306. /// DerivedArgList - An ordered collection of driver arguments,
  307. /// whose storage may be in another argument list.
  308. class DerivedArgList final : public ArgList {
  309. const InputArgList &BaseArgs;
  310. /// The list of arguments we synthesized.
  311. mutable SmallVector<std::unique_ptr<Arg>, 16> SynthesizedArgs;
  312. public:
  313. /// Construct a new derived arg list from \p BaseArgs.
  314. DerivedArgList(const InputArgList &BaseArgs);
  315. const char *getArgString(unsigned Index) const override {
  316. return BaseArgs.getArgString(Index);
  317. }
  318. unsigned getNumInputArgStrings() const override {
  319. return BaseArgs.getNumInputArgStrings();
  320. }
  321. const InputArgList &getBaseArgs() const {
  322. return BaseArgs;
  323. }
  324. /// @name Arg Synthesis
  325. /// @{
  326. /// AddSynthesizedArg - Add a argument to the list of synthesized arguments
  327. /// (to be freed).
  328. void AddSynthesizedArg(Arg *A);
  329. using ArgList::MakeArgString;
  330. const char *MakeArgStringRef(StringRef Str) const override;
  331. /// AddFlagArg - Construct a new FlagArg for the given option \p Id and
  332. /// append it to the argument list.
  333. void AddFlagArg(const Arg *BaseArg, const Option Opt) {
  334. append(MakeFlagArg(BaseArg, Opt));
  335. }
  336. /// AddPositionalArg - Construct a new Positional arg for the given option
  337. /// \p Id, with the provided \p Value and append it to the argument
  338. /// list.
  339. void AddPositionalArg(const Arg *BaseArg, const Option Opt,
  340. StringRef Value) {
  341. append(MakePositionalArg(BaseArg, Opt, Value));
  342. }
  343. /// AddSeparateArg - Construct a new Positional arg for the given option
  344. /// \p Id, with the provided \p Value and append it to the argument
  345. /// list.
  346. void AddSeparateArg(const Arg *BaseArg, const Option Opt,
  347. StringRef Value) {
  348. append(MakeSeparateArg(BaseArg, Opt, Value));
  349. }
  350. /// AddJoinedArg - Construct a new Positional arg for the given option
  351. /// \p Id, with the provided \p Value and append it to the argument list.
  352. void AddJoinedArg(const Arg *BaseArg, const Option Opt,
  353. StringRef Value) {
  354. append(MakeJoinedArg(BaseArg, Opt, Value));
  355. }
  356. /// MakeFlagArg - Construct a new FlagArg for the given option \p Id.
  357. Arg *MakeFlagArg(const Arg *BaseArg, const Option Opt) const;
  358. /// MakePositionalArg - Construct a new Positional arg for the
  359. /// given option \p Id, with the provided \p Value.
  360. Arg *MakePositionalArg(const Arg *BaseArg, const Option Opt,
  361. StringRef Value) const;
  362. /// MakeSeparateArg - Construct a new Positional arg for the
  363. /// given option \p Id, with the provided \p Value.
  364. Arg *MakeSeparateArg(const Arg *BaseArg, const Option Opt,
  365. StringRef Value) const;
  366. /// MakeJoinedArg - Construct a new Positional arg for the
  367. /// given option \p Id, with the provided \p Value.
  368. Arg *MakeJoinedArg(const Arg *BaseArg, const Option Opt,
  369. StringRef Value) const;
  370. /// @}
  371. };
  372. } // end namespace opt
  373. } // end namespace llvm
  374. #endif