/* A safe iterator for GDB, the GNU debugger.
   Copyright (C) 2018-2021 Free Software Foundation, Inc.

   This file is part of GDB.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */

#ifndef COMMON_SAFE_ITERATOR_H
#define COMMON_SAFE_ITERATOR_H

/* A forward iterator that wraps Iterator, such that when iterating
   with iterator IT, it is possible to delete *IT without invalidating
   IT.  Suitably wrapped in a range type and used with range-for, this
   allow convenient patterns like this:

     // range_safe() returns a range type whose begin()/end() methods
     // return safe iterators.
     for (foo *f : range_safe ())
       {
	 if (f->should_delete ())
	   {
	     // The ++it operation implicitly done by the range-for is
	     // still OK after this.
	     delete f;
	   }
       }
*/

template<typename Iterator>
class basic_safe_iterator
{
public:
  typedef basic_safe_iterator self_type;
  typedef typename Iterator::value_type value_type;
  typedef typename Iterator::reference reference;
  typedef typename Iterator::pointer pointer;
  typedef typename Iterator::iterator_category iterator_category;
  typedef typename Iterator::difference_type difference_type;

  /* Construct using the given argument; the end iterator is default
     constructed.  */
  template<typename Arg>
  explicit basic_safe_iterator (Arg &&arg)
    : m_it (std::forward<Arg> (arg)),
      m_next (m_it)
  {
    if (m_it != m_end)
      ++m_next;
  }

  /* Construct the iterator using the first argument, and construct
     the end iterator using the second argument.  */
  template<typename Arg>
  explicit basic_safe_iterator (Arg &&arg, Arg &&arg2)
    : m_it (std::forward<Arg> (arg)),
      m_next (m_it),
      m_end (std::forward<Arg> (arg2))
  {
    if (m_it != m_end)
      ++m_next;
  }

  /* Create a one-past-end iterator.  */
  basic_safe_iterator ()
  {}

  value_type operator* () const { return *m_it; }

  self_type &operator++ ()
  {
    m_it = m_next;
    if (m_it != m_end)
      ++m_next;
    return *this;
  }

  bool operator== (const self_type &other) const
  { return m_it == other.m_it; }

  bool operator!= (const self_type &other) const
  { return m_it != other.m_it; }

private:
  /* The current element.  */
  Iterator m_it {};

  /* The next element.  Always one element ahead of M_IT.  */
  Iterator m_next {};

  /* A one-past-end iterator.  */
  Iterator m_end {};
};

/* A range adapter that wraps another range, and then returns safe
   iterators wrapping the original range's iterators.  */

template<typename Range>
class basic_safe_range
{
public:

  typedef basic_safe_iterator<typename Range::iterator> iterator;

  explicit basic_safe_range (Range range)
    : m_range (range)
  {
  }

  iterator begin ()
  {
    return iterator (m_range.begin (), m_range.end ());
  }

  iterator end ()
  {
    return iterator (m_range.end (), m_range.end ());
  }

private:

  Range m_range;
};

#endif /* COMMON_SAFE_ITERATOR_H */
