[llvm] r300135 - ArgList: cache index ranges containing arguments with each ID

Richard Smith via llvm-commits llvm-commits at lists.llvm.org
Wed Apr 12 16:19:52 PDT 2017


Author: rsmith
Date: Wed Apr 12 18:19:51 2017
New Revision: 300135

URL: http://llvm.org/viewvc/llvm-project?rev=300135&view=rev
Log:
ArgList: cache index ranges containing arguments with each ID

Improve performance of argument list parsing with large numbers of IDs and
large numbers of arguments, by tracking a conservative range of indexes within
the argument list that might contain an argument with each ID. In the worst
case (when the first and last argument with a given ID are at the opposite ends
of the argument list), this still results in a linear-time walk of the list,
but it helps substantially in the common case where each ID occurs only once,
or a few times close together in the list.

This gives a ~10x speedup to clang's `test/Driver/response-file.c`, which
constructs a very large set of command line arguments and feeds them to the
clang driver.

Differential Revision: https://reviews.llvm.org/D30130

Modified:
    llvm/trunk/include/llvm/Option/ArgList.h
    llvm/trunk/lib/Option/ArgList.cpp

Modified: llvm/trunk/include/llvm/Option/ArgList.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Option/ArgList.h?rev=300135&r1=300134&r2=300135&view=diff
==============================================================================
--- llvm/trunk/include/llvm/Option/ArgList.h (original)
+++ llvm/trunk/include/llvm/Option/ArgList.h Wed Apr 12 18:19:51 2017
@@ -10,6 +10,7 @@
 #ifndef LLVM_OPTION_ARGLIST_H
 #define LLVM_OPTION_ARGLIST_H
 
+#include "llvm/ADT/DenseMap.h"
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/ADT/SmallString.h"
 #include "llvm/ADT/StringRef.h"
@@ -28,40 +29,57 @@ class ArgList;
 class Option;
 
 /// arg_iterator - Iterates through arguments stored inside an ArgList.
+template<typename BaseIter, unsigned NumOptSpecifiers = 0>
 class arg_iterator {
-  /// The current argument.
-  SmallVectorImpl<Arg*>::const_iterator Current;
+  /// The current argument and the end of the sequence we're iterating.
+  BaseIter Current, End;
 
-  /// The argument list we are iterating over.
-  const ArgList &Args;
-
-  /// Optional filters on the arguments which will be match. Most clients
-  /// should never want to iterate over arguments without filters, so we won't
-  /// bother to factor this into two separate iterator implementations.
-  //
-  // FIXME: Make efficient; the idea is to provide efficient iteration over
-  // all arguments which match a particular id and then just provide an
-  // iterator combinator which takes multiple iterators which can be
-  // efficiently compared and returns them in order.
-  OptSpecifier Id0, Id1, Id2;
+  /// Optional filters on the arguments which will be match. To avoid a
+  /// zero-sized array, we store one specifier even if we're asked for none.
+  OptSpecifier Ids[NumOptSpecifiers ? NumOptSpecifiers : 1];
+
+  void SkipToNextArg() {
+    for (; Current != End; ++Current) {
+      // Skip erased elements.
+      if (!*Current)
+        continue;
+
+      // Done if there are no filters.
+      if (!NumOptSpecifiers)
+        return;
+
+      // Otherwise require a match.
+      const Option &O = (*Current)->getOption();
+      for (auto Id : Ids) {
+        if (!Id.isValid())
+          break;
+        if (O.matches(Id))
+          return;
+      }
+    }
+  }
 
-  void SkipToNextArg();
+  typedef std::iterator_traits<BaseIter> Traits;
 
 public:
-  typedef Arg * const *                 value_type;
-  typedef Arg * const &                 reference;
-  typedef Arg * const *                 pointer;
-  typedef std::forward_iterator_tag   iterator_category;
-  typedef std::ptrdiff_t              difference_type;
-
-  arg_iterator(SmallVectorImpl<Arg *>::const_iterator it, const ArgList &Args,
-               OptSpecifier Id0 = 0U, OptSpecifier Id1 = 0U,
-               OptSpecifier Id2 = 0U)
-      : Current(it), Args(Args), Id0(Id0), Id1(Id1), Id2(Id2) {
+  typedef typename Traits::value_type  value_type;
+  typedef typename Traits::reference   reference;
+  typedef typename Traits::pointer     pointer;
+  typedef std::forward_iterator_tag    iterator_category;
+  typedef std::ptrdiff_t               difference_type;
+
+  arg_iterator(
+      BaseIter Current, BaseIter End,
+      const OptSpecifier (&Ids)[NumOptSpecifiers ? NumOptSpecifiers : 1] = {})
+      : Current(Current), End(End) {
+    for (unsigned I = 0; I != NumOptSpecifiers; ++I)
+      this->Ids[I] = Ids[I];
     SkipToNextArg();
   }
 
+  // FIXME: This conversion function makes no sense.
   operator const Arg*() { return *Current; }
+
   reference operator*() const { return *Current; }
   pointer operator->() const { return Current; }
 
@@ -94,15 +112,31 @@ public:
 class ArgList {
 public:
   typedef SmallVector<Arg*, 16> arglist_type;
-  typedef arglist_type::iterator iterator;
-  typedef arglist_type::const_iterator const_iterator;
-  typedef arglist_type::reverse_iterator reverse_iterator;
-  typedef arglist_type::const_reverse_iterator const_reverse_iterator;
+  typedef arg_iterator<arglist_type::iterator> iterator;
+  typedef arg_iterator<arglist_type::const_iterator> const_iterator;
+  typedef arg_iterator<arglist_type::reverse_iterator> reverse_iterator;
+  typedef arg_iterator<arglist_type::const_reverse_iterator>
+      const_reverse_iterator;
+
+  template<unsigned N> using filtered_iterator =
+      arg_iterator<arglist_type::const_iterator, N>;
+  template<unsigned N> using filtered_reverse_iterator =
+      arg_iterator<arglist_type::const_reverse_iterator, N>;
 
 private:
   /// The internal list of arguments.
   arglist_type Args;
 
+  typedef std::pair<unsigned, unsigned> OptRange;
+  static OptRange emptyRange() { return {-1u, 0u}; }
+
+  /// The first and last index of each different OptSpecifier ID.
+  DenseMap<unsigned, OptRange> OptRanges;
+
+  /// Get the range of indexes in which options with the specified IDs might
+  /// reside, or (0, 0) if there are no such options.
+  OptRange getRange(std::initializer_list<OptSpecifier> Ids) const;
+
 protected:
   // Make the default special members protected so they won't be used to slice
   // derived objects, but can still be used by derived objects to implement
@@ -113,24 +147,28 @@ protected:
   // InputArgList which deletes the contents of the container. If we could fix
   // up the ownership here (delegate storage/ownership to the derived class so
   // it can be a container of unique_ptr) this would be simpler.
-  ArgList(ArgList &&RHS) : Args(std::move(RHS.Args)) { RHS.Args.clear(); }
+  ArgList(ArgList &&RHS)
+      : Args(std::move(RHS.Args)), OptRanges(std::move(RHS.OptRanges)) {
+    RHS.Args.clear();
+    RHS.OptRanges.clear();
+  }
   ArgList &operator=(ArgList &&RHS) {
     Args = std::move(RHS.Args);
     RHS.Args.clear();
+    OptRanges = std::move(RHS.OptRanges);
+    RHS.OptRanges.clear();
     return *this;
   }
   // Protect the dtor to ensure this type is never destroyed polymorphically.
   ~ArgList() = default;
 
 public:
-
   /// @name Arg Access
   /// @{
 
   /// append - Append \p A to the arg list.
   void append(Arg *A);
 
-  arglist_type &getArgs() { return Args; }
   const arglist_type &getArgs() const { return Args; }
 
   unsigned size() const { return Args.size(); }
@@ -139,30 +177,36 @@ public:
   /// @name Arg Iteration
   /// @{
 
-  iterator begin() { return Args.begin(); }
-  iterator end() { return Args.end(); }
-
-  reverse_iterator rbegin() { return Args.rbegin(); }
-  reverse_iterator rend() { return Args.rend(); }
+  iterator begin() { return {Args.begin(), Args.end()}; }
+  iterator end() { return {Args.end(), Args.end()}; }
 
-  const_iterator begin() const { return Args.begin(); }
-  const_iterator end() const { return Args.end(); }
+  reverse_iterator rbegin() { return {Args.rbegin(), Args.rend()}; }
+  reverse_iterator rend() { return {Args.rend(), Args.rend()}; }
 
-  const_reverse_iterator rbegin() const { return Args.rbegin(); }
-  const_reverse_iterator rend() const { return Args.rend(); }
+  const_iterator begin() const { return {Args.begin(), Args.end()}; }
+  const_iterator end() const { return {Args.end(), Args.end()}; }
 
-  arg_iterator filtered_begin(OptSpecifier Id0 = 0U, OptSpecifier Id1 = 0U,
-                              OptSpecifier Id2 = 0U) const {
-    return arg_iterator(Args.begin(), *this, Id0, Id1, Id2);
-  }
-  arg_iterator filtered_end() const {
-    return arg_iterator(Args.end(), *this);
-  }
-
-  iterator_range<arg_iterator> filtered(OptSpecifier Id0 = 0U,
-                                        OptSpecifier Id1 = 0U,
-                                        OptSpecifier Id2 = 0U) const {
-    return make_range(filtered_begin(Id0, Id1, Id2), filtered_end());
+  const_reverse_iterator rbegin() const { return {Args.rbegin(), Args.rend()}; }
+  const_reverse_iterator rend() const { return {Args.rend(), Args.rend()}; }
+
+  template<typename ...OptSpecifiers>
+  iterator_range<filtered_iterator<sizeof...(OptSpecifiers)>>
+  filtered(OptSpecifiers ...Ids) const {
+    OptRange Range = getRange({Ids...});
+    auto B = Args.begin() + Range.first;
+    auto E = Args.begin() + Range.second;
+    using Iterator = filtered_iterator<sizeof...(OptSpecifiers)>;
+    return make_range(Iterator(B, E, {Ids...}), Iterator(E, E, {Ids...}));
+  }
+
+  template<typename ...OptSpecifiers>
+  iterator_range<filtered_reverse_iterator<sizeof...(OptSpecifiers)>>
+  filtered_reverse(OptSpecifiers ...Ids) const {
+    OptRange Range = getRange({Ids...});
+    auto B = Args.rend() - Range.second;
+    auto E = Args.rend() - Range.first;
+    using Iterator = filtered_reverse_iterator<sizeof...(OptSpecifiers)>;
+    return make_range(Iterator(B, E, {Ids...}), Iterator(E, E, {Ids...}));
   }
 
   /// @}
@@ -179,43 +223,34 @@ public:
   /// hasArg - Does the arg list contain any option matching \p Id.
   ///
   /// \p Claim Whether the argument should be claimed, if it exists.
-  bool hasArgNoClaim(OptSpecifier Id) const {
-    return getLastArgNoClaim(Id) != nullptr;
-  }
-  bool hasArg(OptSpecifier Id) const {
-    return getLastArg(Id) != nullptr;
-  }
-  bool hasArg(OptSpecifier Id0, OptSpecifier Id1) const {
-    return getLastArg(Id0, Id1) != nullptr;
+  template<typename ...OptSpecifiers>
+  bool hasArgNoClaim(OptSpecifiers ...Ids) const {
+    return getLastArgNoClaim(Ids...) != nullptr;
+  }
+  template<typename ...OptSpecifiers>
+  bool hasArg(OptSpecifiers ...Ids) const {
+    return getLastArg(Ids...) != nullptr;
+  }
+
+  /// Return the last argument matching \p Id, or null.
+  template<typename ...OptSpecifiers>
+  Arg *getLastArg(OptSpecifiers ...Ids) const {
+    Arg *Res = nullptr;
+    for (Arg *A : filtered(Ids...)) {
+      Res = A;
+      Res->claim();
+    }
+    return Res;
+  }
+
+  /// Return the last argument matching \p Id, or null. Do not "claim" the
+  /// option (don't mark it as having been used).
+  template<typename ...OptSpecifiers>
+  Arg *getLastArgNoClaim(OptSpecifiers ...Ids) const {
+    for (Arg *A : filtered_reverse(Ids...))
+      return A;
+    return nullptr;
   }
-  bool hasArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2) const {
-    return getLastArg(Id0, Id1, Id2) != nullptr;
-  }
-
-  /// getLastArg - Return the last argument matching \p Id, or null.
-  ///
-  /// \p Claim Whether the argument should be claimed, if it exists.
-  Arg *getLastArgNoClaim(OptSpecifier Id) const;
-  Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1) const;
-  Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2) const;
-  Arg *getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                         OptSpecifier Id3) const;
-  Arg *getLastArg(OptSpecifier Id) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                  OptSpecifier Id3) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                  OptSpecifier Id3, OptSpecifier Id4) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                  OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                  OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5,
-                  OptSpecifier Id6) const;
-  Arg *getLastArg(OptSpecifier Id0, OptSpecifier Id1, OptSpecifier Id2,
-                  OptSpecifier Id3, OptSpecifier Id4, OptSpecifier Id5,
-                  OptSpecifier Id6, OptSpecifier Id7) const;
 
   /// getArgString - Return the input argument string at \p Index.
   virtual const char *getArgString(unsigned Index) const = 0;
@@ -230,8 +265,7 @@ public:
   /// @{
 
   /// getLastArgValue - Return the value of the last argument, or a default.
-  StringRef getLastArgValue(OptSpecifier Id,
-                                  StringRef Default = "") const;
+  StringRef getLastArgValue(OptSpecifier Id, StringRef Default = "") const;
 
   /// getAllArgValues - Get the values of all instances of the given argument
   /// as strings.
@@ -273,7 +307,7 @@ public:
   /// AddAllArgValues - Render the argument values of all arguments
   /// matching the given ids.
   void AddAllArgValues(ArgStringList &Output, OptSpecifier Id0,
-                        OptSpecifier Id1 = 0U, OptSpecifier Id2 = 0U) const;
+                       OptSpecifier Id1 = 0U, OptSpecifier Id2 = 0U) const;
 
   /// AddAllArgsTranslated - Render all the arguments matching the
   /// given ids, but forced to separate args and using the provided

Modified: llvm/trunk/lib/Option/ArgList.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Option/ArgList.cpp?rev=300135&r1=300134&r2=300135&view=diff
==============================================================================
--- llvm/trunk/lib/Option/ArgList.cpp (original)
+++ llvm/trunk/lib/Option/ArgList.cpp Wed Apr 12 18:19:51 2017
@@ -19,203 +19,44 @@
 using namespace llvm;
 using namespace llvm::opt;
 
-void arg_iterator::SkipToNextArg() {
-  for (; Current != Args.end(); ++Current) {
-    // Done if there are no filters.
-    if (!Id0.isValid())
-      break;
-
-    // Otherwise require a match.
-    const Option &O = (*Current)->getOption();
-    if (O.matches(Id0) ||
-        (Id1.isValid() && O.matches(Id1)) ||
-        (Id2.isValid() && O.matches(Id2)))
-      break;
-  }
-}
-
 void ArgList::append(Arg *A) {
   Args.push_back(A);
-}
-
-void ArgList::eraseArg(OptSpecifier Id) {
-  Args.erase(
-      remove_if(*this, [=](Arg *A) { return A->getOption().matches(Id); }),
-      end());
-}
-
-Arg *ArgList::getLastArgNoClaim(OptSpecifier Id) const {
-  // FIXME: Make search efficient?
-  for (const_reverse_iterator it = rbegin(), ie = rend(); it != ie; ++it)
-    if ((*it)->getOption().matches(Id))
-      return *it;
-  return nullptr;
-}
-
-Arg *ArgList::getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1) const {
-  // FIXME: Make search efficient?
-  for (const_reverse_iterator it = rbegin(), ie = rend(); it != ie; ++it)
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1))
-      return *it;
-  return nullptr;
-}
-
-Arg *ArgList::getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1,
-                                OptSpecifier Id2) const {
-  // FIXME: Make search efficient?
-  for (const_reverse_iterator it = rbegin(), ie = rend(); it != ie; ++it)
-    if ((*it)->getOption().matches(Id0) || (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2))
-      return *it;
-  return nullptr;
-}
-
-Arg *ArgList::getLastArgNoClaim(OptSpecifier Id0, OptSpecifier Id1,
-                                OptSpecifier Id2, OptSpecifier Id3) const {
-  // FIXME: Make search efficient?
-  for (const_reverse_iterator it = rbegin(), ie = rend(); it != ie; ++it)
-    if ((*it)->getOption().matches(Id0) || (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) || (*it)->getOption().matches(Id3))
-      return *it;
-  return nullptr;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1)) {
-      Res = *it;
-      Res->claim();
-
-    }
-  }
-
-  return Res;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
-}
 
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2, OptSpecifier Id3) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) ||
-        (*it)->getOption().matches(Id3)) {
-      Res = *it;
-      Res->claim();
-    }
+  // Update ranges for the option and all of its groups.
+  for (Option O = A->getOption().getUnaliasedOption(); O.isValid();
+       O = O.getGroup()) {
+    auto &R =
+        OptRanges.insert(std::make_pair(O.getID(), emptyRange())).first->second;
+    R.first = std::min<unsigned>(R.first, Args.size() - 1);
+    R.second = Args.size();
   }
-
-  return Res;
 }
 
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2, OptSpecifier Id3,
-                         OptSpecifier Id4) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) ||
-        (*it)->getOption().matches(Id3) ||
-        (*it)->getOption().matches(Id4)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2, OptSpecifier Id3,
-                         OptSpecifier Id4, OptSpecifier Id5) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) ||
-        (*it)->getOption().matches(Id3) ||
-        (*it)->getOption().matches(Id4) ||
-        (*it)->getOption().matches(Id5)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2, OptSpecifier Id3,
-                         OptSpecifier Id4, OptSpecifier Id5,
-                         OptSpecifier Id6) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) ||
-        (*it)->getOption().matches(Id3) ||
-        (*it)->getOption().matches(Id4) ||
-        (*it)->getOption().matches(Id5) ||
-        (*it)->getOption().matches(Id6)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
-}
-
-Arg *ArgList::getLastArg(OptSpecifier Id0, OptSpecifier Id1,
-                         OptSpecifier Id2, OptSpecifier Id3,
-                         OptSpecifier Id4, OptSpecifier Id5,
-                         OptSpecifier Id6, OptSpecifier Id7) const {
-  Arg *Res = nullptr;
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it) {
-    if ((*it)->getOption().matches(Id0) ||
-        (*it)->getOption().matches(Id1) ||
-        (*it)->getOption().matches(Id2) ||
-        (*it)->getOption().matches(Id3) ||
-        (*it)->getOption().matches(Id4) ||
-        (*it)->getOption().matches(Id5) ||
-        (*it)->getOption().matches(Id6) ||
-        (*it)->getOption().matches(Id7)) {
-      Res = *it;
-      Res->claim();
-    }
-  }
-
-  return Res;
+void ArgList::eraseArg(OptSpecifier Id) {
+  // Zero out the removed entries but keep them around so that we don't
+  // need to invalidate OptRanges.
+  for (Arg *const &A : filtered(Id)) {
+    // Avoid the need for a non-const filtered iterator variant.
+    Arg **ArgsBegin = Args.data();
+    ArgsBegin[&A - ArgsBegin] = nullptr;
+  }
+  OptRanges.erase(Id.getID());
+}
+
+ArgList::OptRange
+ArgList::getRange(std::initializer_list<OptSpecifier> Ids) const {
+  OptRange R = emptyRange();
+  for (auto Id : Ids) {
+    auto I = OptRanges.find(Id.getID());
+    if (I != OptRanges.end()) {
+      R.first = std::min(R.first, I->second.first);
+      R.second = std::max(R.second, I->second.second);
+    }
+  }
+  // Map an empty {-1, 0} range to {0, 0} so it can be used to form iterators.
+  if (R.first == -1u)
+    R.first = 0;
+  return R;
 }
 
 bool ArgList::hasFlag(OptSpecifier Pos, OptSpecifier Neg, bool Default) const {
@@ -231,8 +72,7 @@ bool ArgList::hasFlag(OptSpecifier Pos,
   return Default;
 }
 
-StringRef ArgList::getLastArgValue(OptSpecifier Id,
-                                         StringRef Default) const {
+StringRef ArgList::getLastArgValue(OptSpecifier Id, StringRef Default) const {
   if (Arg *A = getLastArg(Id))
     return A->getValue();
   return Default;
@@ -262,7 +102,7 @@ void ArgList::AddLastArg(ArgStringList &
 void ArgList::AddAllArgsExcept(ArgStringList &Output,
                                ArrayRef<OptSpecifier> Ids,
                                ArrayRef<OptSpecifier> ExcludeIds) const {
-  for (const Arg *Arg : Args) {
+  for (const Arg *Arg : *this) {
     bool Excluded = false;
     for (OptSpecifier Id : ExcludeIds) {
       if (Arg->getOption().matches(Id)) {
@@ -325,14 +165,14 @@ void ArgList::AddAllArgsTranslated(ArgSt
 }
 
 void ArgList::ClaimAllArgs(OptSpecifier Id0) const {
-  for (auto Arg : filtered(Id0))
+  for (auto *Arg : filtered(Id0))
     Arg->claim();
 }
 
 void ArgList::ClaimAllArgs() const {
-  for (const_iterator it = begin(), ie = end(); it != ie; ++it)
-    if (!(*it)->isClaimed())
-      (*it)->claim();
+  for (auto *Arg : *this)
+    if (!Arg->isClaimed())
+      Arg->claim();
 }
 
 const char *ArgList::GetOrMakeJoinedArgString(unsigned Index,




More information about the llvm-commits mailing list