[libcxx-commits] [libcxx] f32f3db - [libc++] Split the various iterator types out of <iterator>

Louis Dionne via libcxx-commits libcxx-commits at lists.llvm.org
Mon Jun 28 09:25:46 PDT 2021


Author: Louis Dionne
Date: 2021-06-28T12:25:40-04:00
New Revision: f32f3db9fcbf43b1a603c5da882557ebed62f1c5

URL: https://github.com/llvm/llvm-project/commit/f32f3db9fcbf43b1a603c5da882557ebed62f1c5
DIFF: https://github.com/llvm/llvm-project/commit/f32f3db9fcbf43b1a603c5da882557ebed62f1c5.diff

LOG: [libc++] Split the various iterator types out of <iterator>

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

Added: 
    libcxx/include/__iterator/back_insert_iterator.h
    libcxx/include/__iterator/front_insert_iterator.h
    libcxx/include/__iterator/insert_iterator.h
    libcxx/include/__iterator/istream_iterator.h
    libcxx/include/__iterator/istreambuf_iterator.h
    libcxx/include/__iterator/iterator.h
    libcxx/include/__iterator/move_iterator.h
    libcxx/include/__iterator/ostream_iterator.h
    libcxx/include/__iterator/ostreambuf_iterator.h
    libcxx/include/__iterator/reverse_iterator.h
    libcxx/include/__iterator/wrap_iter.h
    libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.verify.cpp

Modified: 
    libcxx/include/CMakeLists.txt
    libcxx/include/iterator
    libcxx/include/module.modulemap
    libcxx/include/regex
    libcxx/include/span
    libcxx/include/string
    libcxx/include/vector

Removed: 
    libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.fail.cpp


################################################################################
diff  --git a/libcxx/include/CMakeLists.txt b/libcxx/include/CMakeLists.txt
index a594b57866ab..3b03ec668578 100644
--- a/libcxx/include/CMakeLists.txt
+++ b/libcxx/include/CMakeLists.txt
@@ -103,25 +103,36 @@ set(files
   __format/format_error.h
   __format/format_parse_context.h
   __function_like.h
-  __functional/search.h
   __functional_03
   __functional_base
   __functional_base_03
   __functional/hash.h
+  __functional/search.h
   __functional/unary_function.h
   __functional/unwrap_ref.h
   __hash_table
   __iterator/advance.h
+  __iterator/back_insert_iterator.h
   __iterator/concepts.h
   __iterator/default_sentinel.h
+  __iterator/front_insert_iterator.h
   __iterator/incrementable_traits.h
+  __iterator/insert_iterator.h
+  __iterator/istream_iterator.h
+  __iterator/istreambuf_iterator.h
   __iterator/iter_move.h
   __iterator/iter_swap.h
   __iterator/iterator_traits.h
+  __iterator/iterator.h
+  __iterator/move_iterator.h
   __iterator/next.h
+  __iterator/ostream_iterator.h
+  __iterator/ostreambuf_iterator.h
   __iterator/prev.h
   __iterator/projected.h
   __iterator/readable_traits.h
+  __iterator/reverse_iterator.h
+  __iterator/wrap_iter.h
   __libcpp_version
   __locale
   __memory/addressof.h

diff  --git a/libcxx/include/__iterator/back_insert_iterator.h b/libcxx/include/__iterator/back_insert_iterator.h
new file mode 100644
index 000000000000..61ac90dfffca
--- /dev/null
+++ b/libcxx/include/__iterator/back_insert_iterator.h
@@ -0,0 +1,75 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_BACK_INSERT_ITERATOR_H
+#define _LIBCPP___ITERATOR_BACK_INSERT_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <cstddef>
+#include <utility> // std::move
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Container>
+class _LIBCPP_TEMPLATE_VIS back_insert_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<output_iterator_tag, void, void, void, void>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+protected:
+    _Container* container;
+public:
+    typedef output_iterator_tag iterator_category;
+    typedef void value_type;
+#if _LIBCPP_STD_VER > 17
+    typedef ptr
diff _t 
diff erence_type;
+#else
+    typedef void 
diff erence_type;
+#endif
+    typedef void pointer;
+    typedef void reference;
+    typedef _Container container_type;
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit back_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(const typename _Container::value_type& __value_)
+        {container->push_back(__value_); return *this;}
+#ifndef _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(typename _Container::value_type&& __value_)
+        {container->push_back(_VSTD::move(__value_)); return *this;}
+#endif // _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator*()     {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator++()    {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator  operator++(int) {return *this;}
+};
+
+template <class _Container>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
+back_insert_iterator<_Container>
+back_inserter(_Container& __x)
+{
+    return back_insert_iterator<_Container>(__x);
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_BACK_INSERT_ITERATOR_H

diff  --git a/libcxx/include/__iterator/front_insert_iterator.h b/libcxx/include/__iterator/front_insert_iterator.h
new file mode 100644
index 000000000000..d5d86f51849c
--- /dev/null
+++ b/libcxx/include/__iterator/front_insert_iterator.h
@@ -0,0 +1,75 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_FRONT_INSERT_ITERATOR_H
+#define _LIBCPP___ITERATOR_FRONT_INSERT_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <cstddef>
+#include <utility> // std::move
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Container>
+class _LIBCPP_TEMPLATE_VIS front_insert_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<output_iterator_tag, void, void, void, void>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+protected:
+    _Container* container;
+public:
+    typedef output_iterator_tag iterator_category;
+    typedef void value_type;
+#if _LIBCPP_STD_VER > 17
+    typedef ptr
diff _t 
diff erence_type;
+#else
+    typedef void 
diff erence_type;
+#endif
+    typedef void pointer;
+    typedef void reference;
+    typedef _Container container_type;
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit front_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(const typename _Container::value_type& __value_)
+        {container->push_front(__value_); return *this;}
+#ifndef _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(typename _Container::value_type&& __value_)
+        {container->push_front(_VSTD::move(__value_)); return *this;}
+#endif // _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator*()     {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator++()    {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator  operator++(int) {return *this;}
+};
+
+template <class _Container>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
+front_insert_iterator<_Container>
+front_inserter(_Container& __x)
+{
+    return front_insert_iterator<_Container>(__x);
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_FRONT_INSERT_ITERATOR_H

diff  --git a/libcxx/include/__iterator/insert_iterator.h b/libcxx/include/__iterator/insert_iterator.h
new file mode 100644
index 000000000000..40555a4c9d34
--- /dev/null
+++ b/libcxx/include/__iterator/insert_iterator.h
@@ -0,0 +1,77 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_INSERT_ITERATOR_H
+#define _LIBCPP___ITERATOR_INSERT_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <cstddef>
+#include <utility> // std::move
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Container>
+class _LIBCPP_TEMPLATE_VIS insert_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<output_iterator_tag, void, void, void, void>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+protected:
+    _Container* container;
+    typename _Container::iterator iter; // FIXME: `ranges::iterator_t<Container>` in C++20 mode
+public:
+    typedef output_iterator_tag iterator_category;
+    typedef void value_type;
+#if _LIBCPP_STD_VER > 17
+    typedef ptr
diff _t 
diff erence_type;
+#else
+    typedef void 
diff erence_type;
+#endif
+    typedef void pointer;
+    typedef void reference;
+    typedef _Container container_type;
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator(_Container& __x, typename _Container::iterator __i)
+        : container(_VSTD::addressof(__x)), iter(__i) {}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(const typename _Container::value_type& __value_)
+        {iter = container->insert(iter, __value_); ++iter; return *this;}
+#ifndef _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(typename _Container::value_type&& __value_)
+        {iter = container->insert(iter, _VSTD::move(__value_)); ++iter; return *this;}
+#endif // _LIBCPP_CXX03_LANG
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator*()        {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++()       {return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++(int)    {return *this;}
+};
+
+template <class _Container>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
+insert_iterator<_Container>
+inserter(_Container& __x, typename _Container::iterator __i)
+{
+    return insert_iterator<_Container>(__x, __i);
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_INSERT_ITERATOR_H

diff  --git a/libcxx/include/__iterator/istream_iterator.h b/libcxx/include/__iterator/istream_iterator.h
new file mode 100644
index 000000000000..1dd57f0d49cf
--- /dev/null
+++ b/libcxx/include/__iterator/istream_iterator.h
@@ -0,0 +1,104 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_ISTREAM_ITERATOR_H
+#define _LIBCPP___ITERATOR_ISTREAM_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <cstddef>
+#include <iosfwd> // for forward declarations of char_traits and basic_istream
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Tp, class _CharT = char,
+          class _Traits = char_traits<_CharT>, class _Distance = ptr
diff _t>
+class _LIBCPP_TEMPLATE_VIS istream_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<input_iterator_tag, _Tp, _Distance, const _Tp*, const _Tp&>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+public:
+    typedef input_iterator_tag iterator_category;
+    typedef _Tp value_type;
+    typedef _Distance 
diff erence_type;
+    typedef const _Tp* pointer;
+    typedef const _Tp& reference;
+    typedef _CharT char_type;
+    typedef _Traits traits_type;
+    typedef basic_istream<_CharT,_Traits> istream_type;
+private:
+    istream_type* __in_stream_;
+    _Tp __value_;
+public:
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istream_iterator() : __in_stream_(nullptr), __value_() {}
+    _LIBCPP_INLINE_VISIBILITY istream_iterator(istream_type& __s) : __in_stream_(_VSTD::addressof(__s))
+        {
+            if (!(*__in_stream_ >> __value_))
+                __in_stream_ = nullptr;
+        }
+
+    _LIBCPP_INLINE_VISIBILITY const _Tp& operator*() const {return __value_;}
+    _LIBCPP_INLINE_VISIBILITY const _Tp* operator->() const {return _VSTD::addressof((operator*()));}
+    _LIBCPP_INLINE_VISIBILITY istream_iterator& operator++()
+        {
+            if (!(*__in_stream_ >> __value_))
+                __in_stream_ = nullptr;
+            return *this;
+        }
+    _LIBCPP_INLINE_VISIBILITY istream_iterator  operator++(int)
+        {istream_iterator __t(*this); ++(*this); return __t;}
+
+    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
+    friend _LIBCPP_INLINE_VISIBILITY
+    bool
+    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
+               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
+
+    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
+    friend _LIBCPP_INLINE_VISIBILITY
+    bool
+    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
+               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
+};
+
+template <class _Tp, class _CharT, class _Traits, class _Distance>
+inline _LIBCPP_INLINE_VISIBILITY
+bool
+operator==(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
+           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
+{
+    return __x.__in_stream_ == __y.__in_stream_;
+}
+
+template <class _Tp, class _CharT, class _Traits, class _Distance>
+inline _LIBCPP_INLINE_VISIBILITY
+bool
+operator!=(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
+           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
+{
+    return !(__x == __y);
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_ISTREAM_ITERATOR_H

diff  --git a/libcxx/include/__iterator/istreambuf_iterator.h b/libcxx/include/__iterator/istreambuf_iterator.h
new file mode 100644
index 000000000000..910d57efc3ba
--- /dev/null
+++ b/libcxx/include/__iterator/istreambuf_iterator.h
@@ -0,0 +1,110 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_ISTREAMBUF_ITERATOR_H
+#define _LIBCPP___ITERATOR_ISTREAMBUF_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <iosfwd> // for forward declaration of basic_streambuf
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template<class _CharT, class _Traits>
+class _LIBCPP_TEMPLATE_VIS istreambuf_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<input_iterator_tag, _CharT,
+                      typename _Traits::off_type, _CharT*,
+                      _CharT>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+public:
+    typedef input_iterator_tag              iterator_category;
+    typedef _CharT                          value_type;
+    typedef typename _Traits::off_type      
diff erence_type;
+    typedef _CharT*                         pointer;
+    typedef _CharT                          reference;
+    typedef _CharT                          char_type;
+    typedef _Traits                         traits_type;
+    typedef typename _Traits::int_type      int_type;
+    typedef basic_streambuf<_CharT,_Traits> streambuf_type;
+    typedef basic_istream<_CharT,_Traits>   istream_type;
+private:
+    mutable streambuf_type* __sbuf_;
+
+    class __proxy
+    {
+        char_type __keep_;
+        streambuf_type* __sbuf_;
+        _LIBCPP_INLINE_VISIBILITY __proxy(char_type __c, streambuf_type* __s)
+            : __keep_(__c), __sbuf_(__s) {}
+        friend class istreambuf_iterator;
+    public:
+        _LIBCPP_INLINE_VISIBILITY char_type operator*() const {return __keep_;}
+    };
+
+    _LIBCPP_INLINE_VISIBILITY
+    bool __test_for_eof() const
+    {
+        if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sgetc(), traits_type::eof()))
+            __sbuf_ = nullptr;
+        return __sbuf_ == nullptr;
+    }
+public:
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istreambuf_iterator() _NOEXCEPT : __sbuf_(nullptr) {}
+    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(istream_type& __s) _NOEXCEPT
+        : __sbuf_(__s.rdbuf()) {}
+    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(streambuf_type* __s) _NOEXCEPT
+        : __sbuf_(__s) {}
+    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(const __proxy& __p) _NOEXCEPT
+        : __sbuf_(__p.__sbuf_) {}
+
+    _LIBCPP_INLINE_VISIBILITY char_type  operator*() const
+        {return static_cast<char_type>(__sbuf_->sgetc());}
+    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator& operator++()
+        {
+            __sbuf_->sbumpc();
+            return *this;
+        }
+    _LIBCPP_INLINE_VISIBILITY __proxy              operator++(int)
+        {
+            return __proxy(__sbuf_->sbumpc(), __sbuf_);
+        }
+
+    _LIBCPP_INLINE_VISIBILITY bool equal(const istreambuf_iterator& __b) const
+        {return __test_for_eof() == __b.__test_for_eof();}
+};
+
+template <class _CharT, class _Traits>
+inline _LIBCPP_INLINE_VISIBILITY
+bool operator==(const istreambuf_iterator<_CharT,_Traits>& __a,
+                const istreambuf_iterator<_CharT,_Traits>& __b)
+                {return __a.equal(__b);}
+
+template <class _CharT, class _Traits>
+inline _LIBCPP_INLINE_VISIBILITY
+bool operator!=(const istreambuf_iterator<_CharT,_Traits>& __a,
+                const istreambuf_iterator<_CharT,_Traits>& __b)
+                {return !__a.equal(__b);}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_ISTREAMBUF_ITERATOR_H

diff  --git a/libcxx/include/__iterator/iterator.h b/libcxx/include/__iterator/iterator.h
new file mode 100644
index 000000000000..dfd481e35712
--- /dev/null
+++ b/libcxx/include/__iterator/iterator.h
@@ -0,0 +1,40 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_ITERATOR_H
+#define _LIBCPP___ITERATOR_ITERATOR_H
+
+#include <__config>
+#include <cstddef>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+template<class _Category, class _Tp, class _Distance = ptr
diff _t,
+         class _Pointer = _Tp*, class _Reference = _Tp&>
+struct _LIBCPP_TEMPLATE_VIS _LIBCPP_DEPRECATED_IN_CXX17 iterator
+{
+    typedef _Tp        value_type;
+    typedef _Distance  
diff erence_type;
+    typedef _Pointer   pointer;
+    typedef _Reference reference;
+    typedef _Category  iterator_category;
+};
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_ITERATOR_H

diff  --git a/libcxx/include/__iterator/move_iterator.h b/libcxx/include/__iterator/move_iterator.h
new file mode 100644
index 000000000000..7819743bdb39
--- /dev/null
+++ b/libcxx/include/__iterator/move_iterator.h
@@ -0,0 +1,189 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_MOVE_ITERATOR_H
+#define _LIBCPP___ITERATOR_MOVE_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <type_traits>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+template <class _Iter>
+class _LIBCPP_TEMPLATE_VIS move_iterator
+{
+private:
+    _Iter __i;
+public:
+    typedef _Iter                                            iterator_type;
+    typedef typename iterator_traits<iterator_type>::value_type value_type;
+    typedef typename iterator_traits<iterator_type>::
diff erence_type 
diff erence_type;
+    typedef iterator_type pointer;
+    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
+        random_access_iterator_tag,
+        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
+#if _LIBCPP_STD_VER > 17
+    typedef input_iterator_tag                               iterator_concept;
+#endif
+
+#ifndef _LIBCPP_CXX03_LANG
+    typedef typename iterator_traits<iterator_type>::reference __reference;
+    typedef typename conditional<
+            is_reference<__reference>::value,
+            typename remove_reference<__reference>::type&&,
+            __reference
+        >::type reference;
+#else
+    typedef typename iterator_traits<iterator_type>::reference reference;
+#endif
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator() : __i() {}
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    explicit move_iterator(_Iter __x) : __i(__x) {}
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator(const move_iterator<_Up>& __u) : __i(__u.base()) {}
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value &&
+        is_convertible<_Up const&, _Iter>::value &&
+        is_assignable<_Iter&, _Up const&>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator& operator=(const move_iterator<_Up>& __u) {
+        __i = __u.base();
+        return *this;
+    }
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 _Iter base() const {return __i;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reference operator*() const { return static_cast<reference>(*__i); }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    pointer  operator->() const { return __i;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator& operator++() {++__i; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator  operator++(int) {move_iterator __tmp(*this); ++__i; return __tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator& operator--() {--__i; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator  operator--(int) {move_iterator __tmp(*this); --__i; return __tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator  operator+ (
diff erence_type __n) const {return move_iterator(__i + __n);}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator& operator+=(
diff erence_type __n) {__i += __n; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator  operator- (
diff erence_type __n) const {return move_iterator(__i - __n);}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    move_iterator& operator-=(
diff erence_type __n) {__i -= __n; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reference operator[](
diff erence_type __n) const { return static_cast<reference>(__i[__n]); }
+};
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator==(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() == __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator<(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() < __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator!=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() != __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator>(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() > __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator>=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() >= __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator<=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() <= __y.base();
+}
+
+#ifndef _LIBCPP_CXX03_LANG
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+auto
+operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+-> decltype(__x.base() - __y.base())
+{
+    return __x.base() - __y.base();
+}
+#else
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY
+typename move_iterator<_Iter1>::
diff erence_type
+operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
+{
+    return __x.base() - __y.base();
+}
+#endif
+
+template <class _Iter>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+move_iterator<_Iter>
+operator+(typename move_iterator<_Iter>::
diff erence_type __n, const move_iterator<_Iter>& __x)
+{
+    return move_iterator<_Iter>(__x.base() + __n);
+}
+
+template <class _Iter>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+move_iterator<_Iter>
+make_move_iterator(_Iter __i)
+{
+    return move_iterator<_Iter>(__i);
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_MOVE_ITERATOR_H

diff  --git a/libcxx/include/__iterator/ostream_iterator.h b/libcxx/include/__iterator/ostream_iterator.h
new file mode 100644
index 000000000000..2615b21b059f
--- /dev/null
+++ b/libcxx/include/__iterator/ostream_iterator.h
@@ -0,0 +1,76 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_OSTREAM_ITERATOR_H
+#define _LIBCPP___ITERATOR_OSTREAM_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <cstddef>
+#include <iosfwd> // for forward declarations of char_traits and basic_ostream
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Tp, class _CharT = char, class _Traits = char_traits<_CharT> >
+class _LIBCPP_TEMPLATE_VIS ostream_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<output_iterator_tag, void, void, void, void>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+public:
+    typedef output_iterator_tag             iterator_category;
+    typedef void                            value_type;
+#if _LIBCPP_STD_VER > 17
+    typedef ptr
diff _t                       
diff erence_type;
+#else
+    typedef void                            
diff erence_type;
+#endif
+    typedef void                            pointer;
+    typedef void                            reference;
+    typedef _CharT                          char_type;
+    typedef _Traits                         traits_type;
+    typedef basic_ostream<_CharT, _Traits>  ostream_type;
+
+private:
+    ostream_type* __out_stream_;
+    const char_type* __delim_;
+public:
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s) _NOEXCEPT
+        : __out_stream_(_VSTD::addressof(__s)), __delim_(nullptr) {}
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s, const _CharT* __delimiter) _NOEXCEPT
+        : __out_stream_(_VSTD::addressof(__s)), __delim_(__delimiter) {}
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator=(const _Tp& __value_)
+        {
+            *__out_stream_ << __value_;
+            if (__delim_)
+                *__out_stream_ << __delim_;
+            return *this;
+        }
+
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator*()     {return *this;}
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++()    {return *this;}
+    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++(int) {return *this;}
+};
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_OSTREAM_ITERATOR_H

diff  --git a/libcxx/include/__iterator/ostreambuf_iterator.h b/libcxx/include/__iterator/ostreambuf_iterator.h
new file mode 100644
index 000000000000..4676fc70ffbe
--- /dev/null
+++ b/libcxx/include/__iterator/ostreambuf_iterator.h
@@ -0,0 +1,81 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_OSTREAMBUF_ITERATOR_H
+#define _LIBCPP___ITERATOR_OSTREAMBUF_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <iosfwd> // for forward declaration of basic_streambuf
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _CharT, class _Traits>
+class _LIBCPP_TEMPLATE_VIS ostreambuf_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<output_iterator_tag, void, void, void, void>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+public:
+    typedef output_iterator_tag                 iterator_category;
+    typedef void                                value_type;
+#if _LIBCPP_STD_VER > 17
+    typedef ptr
diff _t                           
diff erence_type;
+#else
+    typedef void                                
diff erence_type;
+#endif
+    typedef void                                pointer;
+    typedef void                                reference;
+    typedef _CharT                              char_type;
+    typedef _Traits                             traits_type;
+    typedef basic_streambuf<_CharT, _Traits>    streambuf_type;
+    typedef basic_ostream<_CharT, _Traits>      ostream_type;
+
+private:
+    streambuf_type* __sbuf_;
+public:
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(ostream_type& __s) _NOEXCEPT
+        : __sbuf_(__s.rdbuf()) {}
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(streambuf_type* __s) _NOEXCEPT
+        : __sbuf_(__s) {}
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator=(_CharT __c)
+        {
+            if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sputc(__c), traits_type::eof()))
+                __sbuf_ = nullptr;
+            return *this;
+        }
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator*()     {return *this;}
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++()    {return *this;}
+    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++(int) {return *this;}
+    _LIBCPP_INLINE_VISIBILITY bool failed() const _NOEXCEPT {return __sbuf_ == nullptr;}
+
+    template <class _Ch, class _Tr>
+    friend
+    _LIBCPP_HIDDEN
+    ostreambuf_iterator<_Ch, _Tr>
+    __pad_and_output(ostreambuf_iterator<_Ch, _Tr> __s,
+                     const _Ch* __ob, const _Ch* __op, const _Ch* __oe,
+                     ios_base& __iob, _Ch __fl);
+};
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_OSTREAMBUF_ITERATOR_H

diff  --git a/libcxx/include/__iterator/reverse_iterator.h b/libcxx/include/__iterator/reverse_iterator.h
new file mode 100644
index 000000000000..77f7143b4305
--- /dev/null
+++ b/libcxx/include/__iterator/reverse_iterator.h
@@ -0,0 +1,239 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_REVERSE_ITERATOR_H
+#define _LIBCPP___ITERATOR_REVERSE_ITERATOR_H
+
+#include <__config>
+#include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__memory/addressof.h>
+#include <type_traits>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+template <class _Tp, class = void>
+struct __is_stashing_iterator : false_type {};
+
+template <class _Tp>
+struct __is_stashing_iterator<_Tp, typename __void_t<typename _Tp::__stashing_iterator_tag>::type>
+  : true_type {};
+
+_LIBCPP_SUPPRESS_DEPRECATED_PUSH
+template <class _Iter>
+class _LIBCPP_TEMPLATE_VIS reverse_iterator
+#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
+    : public iterator<typename iterator_traits<_Iter>::iterator_category,
+                      typename iterator_traits<_Iter>::value_type,
+                      typename iterator_traits<_Iter>::
diff erence_type,
+                      typename iterator_traits<_Iter>::pointer,
+                      typename iterator_traits<_Iter>::reference>
+#endif
+{
+_LIBCPP_SUPPRESS_DEPRECATED_POP
+private:
+#ifndef _LIBCPP_ABI_NO_ITERATOR_BASES
+    _Iter __t; // no longer used as of LWG #2360, not removed due to ABI break
+#endif
+
+    static_assert(!__is_stashing_iterator<_Iter>::value,
+      "The specified iterator type cannot be used with reverse_iterator; "
+      "Using stashing iterators with reverse_iterator causes undefined behavior");
+
+protected:
+    _Iter current;
+public:
+    typedef _Iter                                            iterator_type;
+    typedef typename iterator_traits<_Iter>::
diff erence_type 
diff erence_type;
+    typedef typename iterator_traits<_Iter>::reference       reference;
+    typedef typename iterator_traits<_Iter>::pointer         pointer;
+    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
+        random_access_iterator_tag,
+        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
+    typedef typename iterator_traits<_Iter>::value_type      value_type;
+
+#if _LIBCPP_STD_VER > 17
+    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
+        random_access_iterator_tag,
+        bidirectional_iterator_tag>                          iterator_concept;
+#endif
+
+#ifndef _LIBCPP_ABI_NO_ITERATOR_BASES
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator() : __t(), current() {}
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    explicit reverse_iterator(_Iter __x) : __t(__x), current(__x) {}
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator(const reverse_iterator<_Up>& __u)
+        : __t(__u.base()), current(__u.base())
+    { }
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value &&
+        is_convertible<_Up const&, _Iter>::value &&
+        is_assignable<_Up const&, _Iter>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator=(const reverse_iterator<_Up>& __u) {
+        __t = current = __u.base();
+        return *this;
+    }
+#else
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator() : current() {}
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    explicit reverse_iterator(_Iter __x) : current(__x) {}
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator(const reverse_iterator<_Up>& __u)
+        : current(__u.base())
+    { }
+
+    template <class _Up, class = _EnableIf<
+        !is_same<_Up, _Iter>::value &&
+        is_convertible<_Up const&, _Iter>::value &&
+        is_assignable<_Up const&, _Iter>::value
+    > >
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator=(const reverse_iterator<_Up>& __u) {
+        current = __u.base();
+        return *this;
+    }
+#endif
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    _Iter base() const {return current;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reference operator*() const {_Iter __tmp = current; return *--__tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    pointer  operator->() const {return _VSTD::addressof(operator*());}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator++() {--current; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator  operator++(int) {reverse_iterator __tmp(*this); --current; return __tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator--() {++current; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator  operator--(int) {reverse_iterator __tmp(*this); ++current; return __tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator  operator+ (
diff erence_type __n) const {return reverse_iterator(current - __n);}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator+=(
diff erence_type __n) {current -= __n; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator  operator- (
diff erence_type __n) const {return reverse_iterator(current + __n);}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reverse_iterator& operator-=(
diff erence_type __n) {current += __n; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+    reference         operator[](
diff erence_type __n) const {return *(*this + __n);}
+};
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator==(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() == __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator<(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() > __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator!=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() != __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator>(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() < __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator>=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() <= __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+bool
+operator<=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __x.base() >= __y.base();
+}
+
+#ifndef _LIBCPP_CXX03_LANG
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+auto
+operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+-> decltype(__y.base() - __x.base())
+{
+    return __y.base() - __x.base();
+}
+#else
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY
+typename reverse_iterator<_Iter1>::
diff erence_type
+operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
+{
+    return __y.base() - __x.base();
+}
+#endif
+
+template <class _Iter>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+reverse_iterator<_Iter>
+operator+(typename reverse_iterator<_Iter>::
diff erence_type __n, const reverse_iterator<_Iter>& __x)
+{
+    return reverse_iterator<_Iter>(__x.base() - __n);
+}
+
+#if _LIBCPP_STD_VER > 11
+template <class _Iter>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
+reverse_iterator<_Iter> make_reverse_iterator(_Iter __i)
+{
+    return reverse_iterator<_Iter>(__i);
+}
+#endif
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_REVERSE_ITERATOR_H

diff  --git a/libcxx/include/__iterator/wrap_iter.h b/libcxx/include/__iterator/wrap_iter.h
new file mode 100644
index 000000000000..d3e6f1e9ef51
--- /dev/null
+++ b/libcxx/include/__iterator/wrap_iter.h
@@ -0,0 +1,407 @@
+// -*- C++ -*-
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___ITERATOR_WRAP_ITER_H
+#define _LIBCPP___ITERATOR_WRAP_ITER_H
+
+#include <__config>
+#include <__debug>
+#include <__iterator/iterator_traits.h>
+#include <__memory/pointer_traits.h> // __to_address
+#include <type_traits>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+#pragma GCC system_header
+#endif
+
+_LIBCPP_PUSH_MACROS
+#include <__undef_macros>
+
+_LIBCPP_BEGIN_NAMESPACE_STD
+
+template <class _Iter> class __wrap_iter;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+#ifndef _LIBCPP_CXX03_LANG
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+auto
+operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+-> decltype(__x.base() - __y.base());
+#else
+template <class _Iter1, class _Iter2>
+_LIBCPP_INLINE_VISIBILITY
+typename __wrap_iter<_Iter1>::
diff erence_type
+operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+#endif
+
+template <class _Iter>
+_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+__wrap_iter<_Iter>
+operator+(typename __wrap_iter<_Iter>::
diff erence_type, __wrap_iter<_Iter>) _NOEXCEPT;
+
+template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy(_Ip, _Ip, _Op);
+template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy_backward(_B1, _B1, _B2);
+template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move(_Ip, _Ip, _Op);
+template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move_backward(_B1, _B1, _B2);
+
+template <class _Iter>
+class __wrap_iter
+{
+public:
+    typedef _Iter                                                      iterator_type;
+    typedef typename iterator_traits<iterator_type>::value_type        value_type;
+    typedef typename iterator_traits<iterator_type>::
diff erence_type   
diff erence_type;
+    typedef typename iterator_traits<iterator_type>::pointer           pointer;
+    typedef typename iterator_traits<iterator_type>::reference         reference;
+    typedef typename iterator_traits<iterator_type>::iterator_category iterator_category;
+#if _LIBCPP_STD_VER > 17
+    typedef contiguous_iterator_tag                                    iterator_concept;
+#endif
+
+private:
+    iterator_type __i;
+public:
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter() _NOEXCEPT
+#if _LIBCPP_STD_VER > 11
+                : __i{}
+#endif
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        __get_db()->__insert_i(this);
+#endif
+    }
+    template <class _Up> _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+        __wrap_iter(const __wrap_iter<_Up>& __u,
+            typename enable_if<is_convertible<_Up, iterator_type>::value>::type* = nullptr) _NOEXCEPT
+            : __i(__u.base())
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        __get_db()->__iterator_copy(this, &__u);
+#endif
+    }
+#if _LIBCPP_DEBUG_LEVEL == 2
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+    __wrap_iter(const __wrap_iter& __x)
+        : __i(__x.base())
+    {
+        __get_db()->__iterator_copy(this, &__x);
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+    __wrap_iter& operator=(const __wrap_iter& __x)
+    {
+        if (this != &__x)
+        {
+            __get_db()->__iterator_copy(this, &__x);
+            __i = __x.__i;
+        }
+        return *this;
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+    ~__wrap_iter()
+    {
+        __get_db()->__erase_i(this);
+    }
+#endif
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference operator*() const _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
+                       "Attempted to dereference a non-dereferenceable iterator");
+#endif
+        return *__i;
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG pointer  operator->() const _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
+                       "Attempted to dereference a non-dereferenceable iterator");
+#endif
+        return _VSTD::__to_address(__i);
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator++() _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
+                       "Attempted to increment a non-incrementable iterator");
+#endif
+        ++__i;
+        return *this;
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator++(int) _NOEXCEPT
+        {__wrap_iter __tmp(*this); ++(*this); return __tmp;}
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator--() _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__decrementable(this),
+                       "Attempted to decrement a non-decrementable iterator");
+#endif
+        --__i;
+        return *this;
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator--(int) _NOEXCEPT
+        {__wrap_iter __tmp(*this); --(*this); return __tmp;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator+ (
diff erence_type __n) const _NOEXCEPT
+        {__wrap_iter __w(*this); __w += __n; return __w;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator+=(
diff erence_type __n) _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__addable(this, __n),
+                   "Attempted to add/subtract an iterator outside its valid range");
+#endif
+        __i += __n;
+        return *this;
+    }
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator- (
diff erence_type __n) const _NOEXCEPT
+        {return *this + (-__n);}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator-=(
diff erence_type __n) _NOEXCEPT
+        {*this += -__n; return *this;}
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference    operator[](
diff erence_type __n) const _NOEXCEPT
+    {
+#if _LIBCPP_DEBUG_LEVEL == 2
+        _LIBCPP_ASSERT(__get_const_db()->__subscriptable(this, __n),
+                   "Attempted to subscript an iterator outside its valid range");
+#endif
+        return __i[__n];
+    }
+
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG iterator_type base() const _NOEXCEPT {return __i;}
+
+private:
+#if _LIBCPP_DEBUG_LEVEL == 2
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(const void* __p, iterator_type __x) : __i(__x)
+    {
+        __get_db()->__insert_ic(this, __p);
+    }
+#else
+    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(iterator_type __x) _NOEXCEPT : __i(__x) {}
+#endif
+
+    template <class _Up> friend class __wrap_iter;
+    template <class _CharT, class _Traits, class _Alloc> friend class basic_string;
+    template <class _Tp, class _Alloc> friend class _LIBCPP_TEMPLATE_VIS vector;
+    template <class _Tp, size_t> friend class _LIBCPP_TEMPLATE_VIS span;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    bool
+    operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+
+#ifndef _LIBCPP_CXX03_LANG
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    auto
+    operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+    -> decltype(__x.base() - __y.base());
+#else
+    template <class _Iter1, class _Iter2>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    typename __wrap_iter<_Iter1>::
diff erence_type
+    operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
+#endif
+
+    template <class _Iter1>
+    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
+    __wrap_iter<_Iter1>
+    operator+(typename __wrap_iter<_Iter1>::
diff erence_type, __wrap_iter<_Iter1>) _NOEXCEPT;
+};
+
+#if _LIBCPP_STD_VER <= 17
+template <class _It>
+struct __is_cpp17_contiguous_iterator<__wrap_iter<_It> > : true_type {};
+#endif
+
+template <class _Iter>
+_LIBCPP_CONSTEXPR
+decltype(_VSTD::__to_address(declval<_Iter>()))
+__to_address(__wrap_iter<_Iter> __w) _NOEXCEPT {
+    return _VSTD::__to_address(__w.base());
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator==(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+    return __x.base() == __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator<(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+#if _LIBCPP_DEBUG_LEVEL == 2
+    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
+                   "Attempted to compare incomparable iterators");
+#endif
+    return __x.base() < __y.base();
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+    return !(__x == __y);
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+    return __y < __x;
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+    return !(__x < __y);
+}
+
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+    return !(__y < __x);
+}
+
+template <class _Iter1>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
+{
+    return !(__x == __y);
+}
+
+template <class _Iter1>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
+{
+    return __y < __x;
+}
+
+template <class _Iter1>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
+{
+    return !(__x < __y);
+}
+
+template <class _Iter1>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+bool
+operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
+{
+    return !(__y < __x);
+}
+
+#ifndef _LIBCPP_CXX03_LANG
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+auto
+operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+-> decltype(__x.base() - __y.base())
+{
+#if _LIBCPP_DEBUG_LEVEL == 2
+    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
+                   "Attempted to subtract incompatible iterators");
+#endif
+    return __x.base() - __y.base();
+}
+#else
+template <class _Iter1, class _Iter2>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+typename __wrap_iter<_Iter1>::
diff erence_type
+operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
+{
+#if _LIBCPP_DEBUG_LEVEL == 2
+    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
+                   "Attempted to subtract incompatible iterators");
+#endif
+    return __x.base() - __y.base();
+}
+#endif
+
+template <class _Iter>
+inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
+__wrap_iter<_Iter>
+operator+(typename __wrap_iter<_Iter>::
diff erence_type __n,
+          __wrap_iter<_Iter> __x) _NOEXCEPT
+{
+    __x += __n;
+    return __x;
+}
+
+_LIBCPP_END_NAMESPACE_STD
+
+_LIBCPP_POP_MACROS
+
+#endif // _LIBCPP___ITERATOR_WRAP_ITER_H

diff  --git a/libcxx/include/iterator b/libcxx/include/iterator
index 092e5898fc26..b4e15c283d93 100644
--- a/libcxx/include/iterator
+++ b/libcxx/include/iterator
@@ -558,16 +558,27 @@ template <class E> constexpr const E* data(initializer_list<E> il) noexcept;
 #include <__debug>
 #include <__functional_base>
 #include <__iterator/advance.h>
+#include <__iterator/back_insert_iterator.h>
 #include <__iterator/concepts.h>
 #include <__iterator/default_sentinel.h>
+#include <__iterator/front_insert_iterator.h>
 #include <__iterator/incrementable_traits.h>
+#include <__iterator/insert_iterator.h>
+#include <__iterator/istream_iterator.h>
+#include <__iterator/istreambuf_iterator.h>
 #include <__iterator/iter_move.h>
 #include <__iterator/iter_swap.h>
 #include <__iterator/iterator_traits.h>
+#include <__iterator/iterator.h>
+#include <__iterator/move_iterator.h>
 #include <__iterator/next.h>
+#include <__iterator/ostream_iterator.h>
+#include <__iterator/ostreambuf_iterator.h>
 #include <__iterator/prev.h>
 #include <__iterator/projected.h>
 #include <__iterator/readable_traits.h>
+#include <__iterator/reverse_iterator.h>
+#include <__iterator/wrap_iter.h>
 #include <__memory/addressof.h>
 #include <__memory/pointer_traits.h>
 #include <__utility/forward.h>
@@ -575,7 +586,6 @@ template <class E> constexpr const E* data(initializer_list<E> il) noexcept;
 #include <concepts> // Mandated by the Standard.
 #include <cstddef>
 #include <initializer_list>
-#include <iosfwd> // for forward declarations of vector and string
 #include <type_traits>
 #include <version>
 
@@ -585,17 +595,6 @@ template <class E> constexpr const E* data(initializer_list<E> il) noexcept;
 
 _LIBCPP_BEGIN_NAMESPACE_STD
 
-template<class _Category, class _Tp, class _Distance = ptr
diff _t,
-         class _Pointer = _Tp*, class _Reference = _Tp&>
-struct _LIBCPP_TEMPLATE_VIS _LIBCPP_DEPRECATED_IN_CXX17 iterator
-{
-    typedef _Tp        value_type;
-    typedef _Distance  
diff erence_type;
-    typedef _Pointer   pointer;
-    typedef _Reference reference;
-    typedef _Category  iterator_category;
-};
-
 template <class _InputIter>
 inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
 typename iterator_traits<_InputIter>::
diff erence_type
@@ -623,1120 +622,6 @@ distance(_InputIter __first, _InputIter __last)
     return _VSTD::__distance(__first, __last, typename iterator_traits<_InputIter>::iterator_category());
 }
 
-template <class _Tp, class = void>
-struct __is_stashing_iterator : false_type {};
-
-template <class _Tp>
-struct __is_stashing_iterator<_Tp, typename __void_t<typename _Tp::__stashing_iterator_tag>::type>
-  : true_type {};
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Iter>
-class _LIBCPP_TEMPLATE_VIS reverse_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<typename iterator_traits<_Iter>::iterator_category,
-                      typename iterator_traits<_Iter>::value_type,
-                      typename iterator_traits<_Iter>::
diff erence_type,
-                      typename iterator_traits<_Iter>::pointer,
-                      typename iterator_traits<_Iter>::reference>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-private:
-#ifndef _LIBCPP_ABI_NO_ITERATOR_BASES
-    _Iter __t; // no longer used as of LWG #2360, not removed due to ABI break
-#endif
-
-    static_assert(!__is_stashing_iterator<_Iter>::value,
-      "The specified iterator type cannot be used with reverse_iterator; "
-      "Using stashing iterators with reverse_iterator causes undefined behavior");
-
-protected:
-    _Iter current;
-public:
-    typedef _Iter                                            iterator_type;
-    typedef typename iterator_traits<_Iter>::
diff erence_type 
diff erence_type;
-    typedef typename iterator_traits<_Iter>::reference       reference;
-    typedef typename iterator_traits<_Iter>::pointer         pointer;
-    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
-        random_access_iterator_tag,
-        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
-    typedef typename iterator_traits<_Iter>::value_type      value_type;
-
-#if _LIBCPP_STD_VER > 17
-    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
-        random_access_iterator_tag,
-        bidirectional_iterator_tag>                          iterator_concept;
-#endif
-
-#ifndef _LIBCPP_ABI_NO_ITERATOR_BASES
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator() : __t(), current() {}
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    explicit reverse_iterator(_Iter __x) : __t(__x), current(__x) {}
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator(const reverse_iterator<_Up>& __u)
-        : __t(__u.base()), current(__u.base())
-    { }
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value &&
-        is_convertible<_Up const&, _Iter>::value &&
-        is_assignable<_Up const&, _Iter>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator=(const reverse_iterator<_Up>& __u) {
-        __t = current = __u.base();
-        return *this;
-    }
-#else
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator() : current() {}
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    explicit reverse_iterator(_Iter __x) : current(__x) {}
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator(const reverse_iterator<_Up>& __u)
-        : current(__u.base())
-    { }
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value &&
-        is_convertible<_Up const&, _Iter>::value &&
-        is_assignable<_Up const&, _Iter>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator=(const reverse_iterator<_Up>& __u) {
-        current = __u.base();
-        return *this;
-    }
-#endif
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    _Iter base() const {return current;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reference operator*() const {_Iter __tmp = current; return *--__tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    pointer  operator->() const {return _VSTD::addressof(operator*());}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator++() {--current; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator  operator++(int) {reverse_iterator __tmp(*this); --current; return __tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator--() {++current; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator  operator--(int) {reverse_iterator __tmp(*this); ++current; return __tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator  operator+ (
diff erence_type __n) const {return reverse_iterator(current - __n);}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator+=(
diff erence_type __n) {current -= __n; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator  operator- (
diff erence_type __n) const {return reverse_iterator(current + __n);}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reverse_iterator& operator-=(
diff erence_type __n) {current += __n; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reference         operator[](
diff erence_type __n) const {return *(*this + __n);}
-};
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator==(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() == __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator<(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() > __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator!=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() != __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator>(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() < __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator>=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() <= __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator<=(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __x.base() >= __y.base();
-}
-
-#ifndef _LIBCPP_CXX03_LANG
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-auto
-operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
--> decltype(__y.base() - __x.base())
-{
-    return __y.base() - __x.base();
-}
-#else
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY
-typename reverse_iterator<_Iter1>::
diff erence_type
-operator-(const reverse_iterator<_Iter1>& __x, const reverse_iterator<_Iter2>& __y)
-{
-    return __y.base() - __x.base();
-}
-#endif
-
-template <class _Iter>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-reverse_iterator<_Iter>
-operator+(typename reverse_iterator<_Iter>::
diff erence_type __n, const reverse_iterator<_Iter>& __x)
-{
-    return reverse_iterator<_Iter>(__x.base() - __n);
-}
-
-#if _LIBCPP_STD_VER > 11
-template <class _Iter>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-reverse_iterator<_Iter> make_reverse_iterator(_Iter __i)
-{
-    return reverse_iterator<_Iter>(__i);
-}
-#endif
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Container>
-class _LIBCPP_TEMPLATE_VIS back_insert_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<output_iterator_tag, void, void, void, void>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-protected:
-    _Container* container;
-public:
-    typedef output_iterator_tag iterator_category;
-    typedef void value_type;
-#if _LIBCPP_STD_VER > 17
-    typedef ptr
diff _t 
diff erence_type;
-#else
-    typedef void 
diff erence_type;
-#endif
-    typedef void pointer;
-    typedef void reference;
-    typedef _Container container_type;
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit back_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(const typename _Container::value_type& __value_)
-        {container->push_back(__value_); return *this;}
-#ifndef _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator=(typename _Container::value_type&& __value_)
-        {container->push_back(_VSTD::move(__value_)); return *this;}
-#endif // _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator*()     {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator& operator++()    {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 back_insert_iterator  operator++(int) {return *this;}
-};
-
-template <class _Container>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
-back_insert_iterator<_Container>
-back_inserter(_Container& __x)
-{
-    return back_insert_iterator<_Container>(__x);
-}
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Container>
-class _LIBCPP_TEMPLATE_VIS front_insert_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<output_iterator_tag, void, void, void, void>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-protected:
-    _Container* container;
-public:
-    typedef output_iterator_tag iterator_category;
-    typedef void value_type;
-#if _LIBCPP_STD_VER > 17
-    typedef ptr
diff _t 
diff erence_type;
-#else
-    typedef void 
diff erence_type;
-#endif
-    typedef void pointer;
-    typedef void reference;
-    typedef _Container container_type;
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 explicit front_insert_iterator(_Container& __x) : container(_VSTD::addressof(__x)) {}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(const typename _Container::value_type& __value_)
-        {container->push_front(__value_); return *this;}
-#ifndef _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator=(typename _Container::value_type&& __value_)
-        {container->push_front(_VSTD::move(__value_)); return *this;}
-#endif // _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator*()     {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator& operator++()    {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 front_insert_iterator  operator++(int) {return *this;}
-};
-
-template <class _Container>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
-front_insert_iterator<_Container>
-front_inserter(_Container& __x)
-{
-    return front_insert_iterator<_Container>(__x);
-}
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Container>
-class _LIBCPP_TEMPLATE_VIS insert_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<output_iterator_tag, void, void, void, void>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-protected:
-    _Container* container;
-    typename _Container::iterator iter; // FIXME: `ranges::iterator_t<Container>` in C++20 mode
-public:
-    typedef output_iterator_tag iterator_category;
-    typedef void value_type;
-#if _LIBCPP_STD_VER > 17
-    typedef ptr
diff _t 
diff erence_type;
-#else
-    typedef void 
diff erence_type;
-#endif
-    typedef void pointer;
-    typedef void reference;
-    typedef _Container container_type;
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator(_Container& __x, typename _Container::iterator __i)
-        : container(_VSTD::addressof(__x)), iter(__i) {}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(const typename _Container::value_type& __value_)
-        {iter = container->insert(iter, __value_); ++iter; return *this;}
-#ifndef _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator=(typename _Container::value_type&& __value_)
-        {iter = container->insert(iter, _VSTD::move(__value_)); ++iter; return *this;}
-#endif // _LIBCPP_CXX03_LANG
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator*()        {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++()       {return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 insert_iterator& operator++(int)    {return *this;}
-};
-
-template <class _Container>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
-insert_iterator<_Container>
-inserter(_Container& __x, typename _Container::iterator __i)
-{
-    return insert_iterator<_Container>(__x, __i);
-}
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Tp, class _CharT = char,
-          class _Traits = char_traits<_CharT>, class _Distance = ptr
diff _t>
-class _LIBCPP_TEMPLATE_VIS istream_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<input_iterator_tag, _Tp, _Distance, const _Tp*, const _Tp&>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-public:
-    typedef input_iterator_tag iterator_category;
-    typedef _Tp value_type;
-    typedef _Distance 
diff erence_type;
-    typedef const _Tp* pointer;
-    typedef const _Tp& reference;
-    typedef _CharT char_type;
-    typedef _Traits traits_type;
-    typedef basic_istream<_CharT,_Traits> istream_type;
-private:
-    istream_type* __in_stream_;
-    _Tp __value_;
-public:
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istream_iterator() : __in_stream_(nullptr), __value_() {}
-    _LIBCPP_INLINE_VISIBILITY istream_iterator(istream_type& __s) : __in_stream_(_VSTD::addressof(__s))
-        {
-            if (!(*__in_stream_ >> __value_))
-                __in_stream_ = nullptr;
-        }
-
-    _LIBCPP_INLINE_VISIBILITY const _Tp& operator*() const {return __value_;}
-    _LIBCPP_INLINE_VISIBILITY const _Tp* operator->() const {return _VSTD::addressof((operator*()));}
-    _LIBCPP_INLINE_VISIBILITY istream_iterator& operator++()
-        {
-            if (!(*__in_stream_ >> __value_))
-                __in_stream_ = nullptr;
-            return *this;
-        }
-    _LIBCPP_INLINE_VISIBILITY istream_iterator  operator++(int)
-        {istream_iterator __t(*this); ++(*this); return __t;}
-
-    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
-    friend _LIBCPP_INLINE_VISIBILITY
-    bool
-    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
-               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
-
-    template <class _Up, class _CharU, class _TraitsU, class _DistanceU>
-    friend _LIBCPP_INLINE_VISIBILITY
-    bool
-    operator==(const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __x,
-               const istream_iterator<_Up, _CharU, _TraitsU, _DistanceU>& __y);
-};
-
-template <class _Tp, class _CharT, class _Traits, class _Distance>
-inline _LIBCPP_INLINE_VISIBILITY
-bool
-operator==(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
-           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
-{
-    return __x.__in_stream_ == __y.__in_stream_;
-}
-
-template <class _Tp, class _CharT, class _Traits, class _Distance>
-inline _LIBCPP_INLINE_VISIBILITY
-bool
-operator!=(const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __x,
-           const istream_iterator<_Tp, _CharT, _Traits, _Distance>& __y)
-{
-    return !(__x == __y);
-}
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _Tp, class _CharT = char, class _Traits = char_traits<_CharT> >
-class _LIBCPP_TEMPLATE_VIS ostream_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<output_iterator_tag, void, void, void, void>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-public:
-    typedef output_iterator_tag             iterator_category;
-    typedef void                            value_type;
-#if _LIBCPP_STD_VER > 17
-    typedef ptr
diff _t                       
diff erence_type;
-#else
-    typedef void                            
diff erence_type;
-#endif
-    typedef void                            pointer;
-    typedef void                            reference;
-    typedef _CharT                          char_type;
-    typedef _Traits                         traits_type;
-    typedef basic_ostream<_CharT, _Traits>  ostream_type;
-
-private:
-    ostream_type* __out_stream_;
-    const char_type* __delim_;
-public:
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s) _NOEXCEPT
-        : __out_stream_(_VSTD::addressof(__s)), __delim_(nullptr) {}
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator(ostream_type& __s, const _CharT* __delimiter) _NOEXCEPT
-        : __out_stream_(_VSTD::addressof(__s)), __delim_(__delimiter) {}
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator=(const _Tp& __value_)
-        {
-            *__out_stream_ << __value_;
-            if (__delim_)
-                *__out_stream_ << __delim_;
-            return *this;
-        }
-
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator*()     {return *this;}
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++()    {return *this;}
-    _LIBCPP_INLINE_VISIBILITY ostream_iterator& operator++(int) {return *this;}
-};
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template<class _CharT, class _Traits>
-class _LIBCPP_TEMPLATE_VIS istreambuf_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<input_iterator_tag, _CharT,
-                      typename _Traits::off_type, _CharT*,
-                      _CharT>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-public:
-    typedef input_iterator_tag              iterator_category;
-    typedef _CharT                          value_type;
-    typedef typename _Traits::off_type      
diff erence_type;
-    typedef _CharT*                         pointer;
-    typedef _CharT                          reference;
-    typedef _CharT                          char_type;
-    typedef _Traits                         traits_type;
-    typedef typename _Traits::int_type      int_type;
-    typedef basic_streambuf<_CharT,_Traits> streambuf_type;
-    typedef basic_istream<_CharT,_Traits>   istream_type;
-private:
-    mutable streambuf_type* __sbuf_;
-
-    class __proxy
-    {
-        char_type __keep_;
-        streambuf_type* __sbuf_;
-        _LIBCPP_INLINE_VISIBILITY __proxy(char_type __c, streambuf_type* __s)
-            : __keep_(__c), __sbuf_(__s) {}
-        friend class istreambuf_iterator;
-    public:
-        _LIBCPP_INLINE_VISIBILITY char_type operator*() const {return __keep_;}
-    };
-
-    _LIBCPP_INLINE_VISIBILITY
-    bool __test_for_eof() const
-    {
-        if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sgetc(), traits_type::eof()))
-            __sbuf_ = nullptr;
-        return __sbuf_ == nullptr;
-    }
-public:
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR istreambuf_iterator() _NOEXCEPT : __sbuf_(nullptr) {}
-    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(istream_type& __s) _NOEXCEPT
-        : __sbuf_(__s.rdbuf()) {}
-    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(streambuf_type* __s) _NOEXCEPT
-        : __sbuf_(__s) {}
-    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator(const __proxy& __p) _NOEXCEPT
-        : __sbuf_(__p.__sbuf_) {}
-
-    _LIBCPP_INLINE_VISIBILITY char_type  operator*() const
-        {return static_cast<char_type>(__sbuf_->sgetc());}
-    _LIBCPP_INLINE_VISIBILITY istreambuf_iterator& operator++()
-        {
-            __sbuf_->sbumpc();
-            return *this;
-        }
-    _LIBCPP_INLINE_VISIBILITY __proxy              operator++(int)
-        {
-            return __proxy(__sbuf_->sbumpc(), __sbuf_);
-        }
-
-    _LIBCPP_INLINE_VISIBILITY bool equal(const istreambuf_iterator& __b) const
-        {return __test_for_eof() == __b.__test_for_eof();}
-};
-
-template <class _CharT, class _Traits>
-inline _LIBCPP_INLINE_VISIBILITY
-bool operator==(const istreambuf_iterator<_CharT,_Traits>& __a,
-                const istreambuf_iterator<_CharT,_Traits>& __b)
-                {return __a.equal(__b);}
-
-template <class _CharT, class _Traits>
-inline _LIBCPP_INLINE_VISIBILITY
-bool operator!=(const istreambuf_iterator<_CharT,_Traits>& __a,
-                const istreambuf_iterator<_CharT,_Traits>& __b)
-                {return !__a.equal(__b);}
-
-_LIBCPP_SUPPRESS_DEPRECATED_PUSH
-template <class _CharT, class _Traits>
-class _LIBCPP_TEMPLATE_VIS ostreambuf_iterator
-#if _LIBCPP_STD_VER <= 14 || !defined(_LIBCPP_ABI_NO_ITERATOR_BASES)
-    : public iterator<output_iterator_tag, void, void, void, void>
-#endif
-{
-_LIBCPP_SUPPRESS_DEPRECATED_POP
-public:
-    typedef output_iterator_tag                 iterator_category;
-    typedef void                                value_type;
-#if _LIBCPP_STD_VER > 17
-    typedef ptr
diff _t                           
diff erence_type;
-#else
-    typedef void                                
diff erence_type;
-#endif
-    typedef void                                pointer;
-    typedef void                                reference;
-    typedef _CharT                              char_type;
-    typedef _Traits                             traits_type;
-    typedef basic_streambuf<_CharT, _Traits>    streambuf_type;
-    typedef basic_ostream<_CharT, _Traits>      ostream_type;
-
-private:
-    streambuf_type* __sbuf_;
-public:
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(ostream_type& __s) _NOEXCEPT
-        : __sbuf_(__s.rdbuf()) {}
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator(streambuf_type* __s) _NOEXCEPT
-        : __sbuf_(__s) {}
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator=(_CharT __c)
-        {
-            if (__sbuf_ && traits_type::eq_int_type(__sbuf_->sputc(__c), traits_type::eof()))
-                __sbuf_ = nullptr;
-            return *this;
-        }
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator*()     {return *this;}
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++()    {return *this;}
-    _LIBCPP_INLINE_VISIBILITY ostreambuf_iterator& operator++(int) {return *this;}
-    _LIBCPP_INLINE_VISIBILITY bool failed() const _NOEXCEPT {return __sbuf_ == nullptr;}
-
-    template <class _Ch, class _Tr>
-    friend
-    _LIBCPP_HIDDEN
-    ostreambuf_iterator<_Ch, _Tr>
-    __pad_and_output(ostreambuf_iterator<_Ch, _Tr> __s,
-                     const _Ch* __ob, const _Ch* __op, const _Ch* __oe,
-                     ios_base& __iob, _Ch __fl);
-};
-
-template <class _Iter>
-class _LIBCPP_TEMPLATE_VIS move_iterator
-{
-private:
-    _Iter __i;
-public:
-    typedef _Iter                                            iterator_type;
-    typedef typename iterator_traits<iterator_type>::value_type value_type;
-    typedef typename iterator_traits<iterator_type>::
diff erence_type 
diff erence_type;
-    typedef iterator_type pointer;
-    typedef _If<__is_cpp17_random_access_iterator<_Iter>::value,
-        random_access_iterator_tag,
-        typename iterator_traits<_Iter>::iterator_category>  iterator_category;
-#if _LIBCPP_STD_VER > 17
-    typedef input_iterator_tag                               iterator_concept;
-#endif
-
-#ifndef _LIBCPP_CXX03_LANG
-    typedef typename iterator_traits<iterator_type>::reference __reference;
-    typedef typename conditional<
-            is_reference<__reference>::value,
-            typename remove_reference<__reference>::type&&,
-            __reference
-        >::type reference;
-#else
-    typedef typename iterator_traits<iterator_type>::reference reference;
-#endif
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator() : __i() {}
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    explicit move_iterator(_Iter __x) : __i(__x) {}
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value && is_convertible<_Up const&, _Iter>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator(const move_iterator<_Up>& __u) : __i(__u.base()) {}
-
-    template <class _Up, class = _EnableIf<
-        !is_same<_Up, _Iter>::value &&
-        is_convertible<_Up const&, _Iter>::value &&
-        is_assignable<_Iter&, _Up const&>::value
-    > >
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator& operator=(const move_iterator<_Up>& __u) {
-        __i = __u.base();
-        return *this;
-    }
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14 _Iter base() const {return __i;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reference operator*() const { return static_cast<reference>(*__i); }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    pointer  operator->() const { return __i;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator& operator++() {++__i; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator  operator++(int) {move_iterator __tmp(*this); ++__i; return __tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator& operator--() {--__i; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator  operator--(int) {move_iterator __tmp(*this); --__i; return __tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator  operator+ (
diff erence_type __n) const {return move_iterator(__i + __n);}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator& operator+=(
diff erence_type __n) {__i += __n; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator  operator- (
diff erence_type __n) const {return move_iterator(__i - __n);}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    move_iterator& operator-=(
diff erence_type __n) {__i -= __n; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-    reference operator[](
diff erence_type __n) const { return static_cast<reference>(__i[__n]); }
-};
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator==(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() == __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator<(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() < __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator!=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() != __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator>(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() > __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator>=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() >= __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-bool
-operator<=(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() <= __y.base();
-}
-
-#ifndef _LIBCPP_CXX03_LANG
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-auto
-operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
--> decltype(__x.base() - __y.base())
-{
-    return __x.base() - __y.base();
-}
-#else
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY
-typename move_iterator<_Iter1>::
diff erence_type
-operator-(const move_iterator<_Iter1>& __x, const move_iterator<_Iter2>& __y)
-{
-    return __x.base() - __y.base();
-}
-#endif
-
-template <class _Iter>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-move_iterator<_Iter>
-operator+(typename move_iterator<_Iter>::
diff erence_type __n, const move_iterator<_Iter>& __x)
-{
-    return move_iterator<_Iter>(__x.base() + __n);
-}
-
-template <class _Iter>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX14
-move_iterator<_Iter>
-make_move_iterator(_Iter __i)
-{
-    return move_iterator<_Iter>(__i);
-}
-
-// __wrap_iter
-
-template <class _Iter> class __wrap_iter;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-#ifndef _LIBCPP_CXX03_LANG
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-auto
-operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
--> decltype(__x.base() - __y.base());
-#else
-template <class _Iter1, class _Iter2>
-_LIBCPP_INLINE_VISIBILITY
-typename __wrap_iter<_Iter1>::
diff erence_type
-operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-#endif
-
-template <class _Iter>
-_LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-__wrap_iter<_Iter>
-operator+(typename __wrap_iter<_Iter>::
diff erence_type, __wrap_iter<_Iter>) _NOEXCEPT;
-
-template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy(_Ip, _Ip, _Op);
-template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 copy_backward(_B1, _B1, _B2);
-template <class _Ip, class _Op> _Op _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move(_Ip, _Ip, _Op);
-template <class _B1, class _B2> _B2 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17 move_backward(_B1, _B1, _B2);
-
-template <class _Iter>
-class __wrap_iter
-{
-public:
-    typedef _Iter                                                      iterator_type;
-    typedef typename iterator_traits<iterator_type>::value_type        value_type;
-    typedef typename iterator_traits<iterator_type>::
diff erence_type   
diff erence_type;
-    typedef typename iterator_traits<iterator_type>::pointer           pointer;
-    typedef typename iterator_traits<iterator_type>::reference         reference;
-    typedef typename iterator_traits<iterator_type>::iterator_category iterator_category;
-#if _LIBCPP_STD_VER > 17
-    typedef contiguous_iterator_tag                                    iterator_concept;
-#endif
-
-private:
-    iterator_type __i;
-public:
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter() _NOEXCEPT
-#if _LIBCPP_STD_VER > 11
-                : __i{}
-#endif
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        __get_db()->__insert_i(this);
-#endif
-    }
-    template <class _Up> _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-        __wrap_iter(const __wrap_iter<_Up>& __u,
-            typename enable_if<is_convertible<_Up, iterator_type>::value>::type* = nullptr) _NOEXCEPT
-            : __i(__u.base())
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        __get_db()->__iterator_copy(this, &__u);
-#endif
-    }
-#if _LIBCPP_DEBUG_LEVEL == 2
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-    __wrap_iter(const __wrap_iter& __x)
-        : __i(__x.base())
-    {
-        __get_db()->__iterator_copy(this, &__x);
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-    __wrap_iter& operator=(const __wrap_iter& __x)
-    {
-        if (this != &__x)
-        {
-            __get_db()->__iterator_copy(this, &__x);
-            __i = __x.__i;
-        }
-        return *this;
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-    ~__wrap_iter()
-    {
-        __get_db()->__erase_i(this);
-    }
-#endif
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference operator*() const _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
-                       "Attempted to dereference a non-dereferenceable iterator");
-#endif
-        return *__i;
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG pointer  operator->() const _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
-                       "Attempted to dereference a non-dereferenceable iterator");
-#endif
-        return _VSTD::__to_address(__i);
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator++() _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__dereferenceable(this),
-                       "Attempted to increment a non-incrementable iterator");
-#endif
-        ++__i;
-        return *this;
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator++(int) _NOEXCEPT
-        {__wrap_iter __tmp(*this); ++(*this); return __tmp;}
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator--() _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__decrementable(this),
-                       "Attempted to decrement a non-decrementable iterator");
-#endif
-        --__i;
-        return *this;
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator--(int) _NOEXCEPT
-        {__wrap_iter __tmp(*this); --(*this); return __tmp;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator+ (
diff erence_type __n) const _NOEXCEPT
-        {__wrap_iter __w(*this); __w += __n; return __w;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator+=(
diff erence_type __n) _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__addable(this, __n),
-                   "Attempted to add/subtract an iterator outside its valid range");
-#endif
-        __i += __n;
-        return *this;
-    }
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter  operator- (
diff erence_type __n) const _NOEXCEPT
-        {return *this + (-__n);}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter& operator-=(
diff erence_type __n) _NOEXCEPT
-        {*this += -__n; return *this;}
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG reference    operator[](
diff erence_type __n) const _NOEXCEPT
-    {
-#if _LIBCPP_DEBUG_LEVEL == 2
-        _LIBCPP_ASSERT(__get_const_db()->__subscriptable(this, __n),
-                   "Attempted to subscript an iterator outside its valid range");
-#endif
-        return __i[__n];
-    }
-
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG iterator_type base() const _NOEXCEPT {return __i;}
-
-private:
-#if _LIBCPP_DEBUG_LEVEL == 2
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(const void* __p, iterator_type __x) : __i(__x)
-    {
-        __get_db()->__insert_ic(this, __p);
-    }
-#else
-    _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG __wrap_iter(iterator_type __x) _NOEXCEPT : __i(__x) {}
-#endif
-
-    template <class _Up> friend class __wrap_iter;
-    template <class _CharT, class _Traits, class _Alloc> friend class basic_string;
-    template <class _Tp, class _Alloc> friend class _LIBCPP_TEMPLATE_VIS vector;
-    template <class _Tp, size_t> friend class _LIBCPP_TEMPLATE_VIS span;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator==(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator<(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator!=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator>(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator>=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    bool
-    operator<=(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-
-#ifndef _LIBCPP_CXX03_LANG
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    auto
-    operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-    -> decltype(__x.base() - __y.base());
-#else
-    template <class _Iter1, class _Iter2>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    typename __wrap_iter<_Iter1>::
diff erence_type
-    operator-(const __wrap_iter<_Iter1>&, const __wrap_iter<_Iter2>&) _NOEXCEPT;
-#endif
-
-    template <class _Iter1>
-    _LIBCPP_CONSTEXPR_IF_NODEBUG friend
-    __wrap_iter<_Iter1>
-    operator+(typename __wrap_iter<_Iter1>::
diff erence_type, __wrap_iter<_Iter1>) _NOEXCEPT;
-};
-
-#if _LIBCPP_STD_VER <= 17
-template <class _It>
-struct __is_cpp17_contiguous_iterator<__wrap_iter<_It> > : true_type {};
-#endif
-
-template <class _Iter>
-_LIBCPP_CONSTEXPR
-decltype(_VSTD::__to_address(declval<_Iter>()))
-__to_address(__wrap_iter<_Iter> __w) _NOEXCEPT {
-    return _VSTD::__to_address(__w.base());
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator==(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-    return __x.base() == __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator<(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-#if _LIBCPP_DEBUG_LEVEL == 2
-    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
-                   "Attempted to compare incomparable iterators");
-#endif
-    return __x.base() < __y.base();
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-    return !(__x == __y);
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-    return __y < __x;
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-    return !(__x < __y);
-}
-
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-    return !(__y < __x);
-}
-
-template <class _Iter1>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator!=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
-{
-    return !(__x == __y);
-}
-
-template <class _Iter1>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
-{
-    return __y < __x;
-}
-
-template <class _Iter1>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator>=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
-{
-    return !(__x < __y);
-}
-
-template <class _Iter1>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-bool
-operator<=(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter1>& __y) _NOEXCEPT
-{
-    return !(__y < __x);
-}
-
-#ifndef _LIBCPP_CXX03_LANG
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-auto
-operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
--> decltype(__x.base() - __y.base())
-{
-#if _LIBCPP_DEBUG_LEVEL == 2
-    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
-                   "Attempted to subtract incompatible iterators");
-#endif
-    return __x.base() - __y.base();
-}
-#else
-template <class _Iter1, class _Iter2>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-typename __wrap_iter<_Iter1>::
diff erence_type
-operator-(const __wrap_iter<_Iter1>& __x, const __wrap_iter<_Iter2>& __y) _NOEXCEPT
-{
-#if _LIBCPP_DEBUG_LEVEL == 2
-    _LIBCPP_ASSERT(__get_const_db()->__less_than_comparable(&__x, &__y),
-                   "Attempted to subtract incompatible iterators");
-#endif
-    return __x.base() - __y.base();
-}
-#endif
-
-template <class _Iter>
-inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_IF_NODEBUG
-__wrap_iter<_Iter>
-operator+(typename __wrap_iter<_Iter>::
diff erence_type __n,
-          __wrap_iter<_Iter> __x) _NOEXCEPT
-{
-    __x += __n;
-    return __x;
-}
-
 template <class _Tp, size_t _Np>
 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
 _Tp*

diff  --git a/libcxx/include/module.modulemap b/libcxx/include/module.modulemap
index 48573377bb7b..da0a988c00c8 100644
--- a/libcxx/include/module.modulemap
+++ b/libcxx/include/module.modulemap
@@ -453,17 +453,28 @@ module std [system] {
     export *
 
     module __iterator {
-      module advance              { header "__iterator/advance.h"              }
-      module concepts             { header "__iterator/concepts.h"             }
-      module default_sentinel     { header "__iterator/default_sentinel.h"     }
-      module incrementable_traits { header "__iterator/incrementable_traits.h" }
-      module iter_move            { header "__iterator/iter_move.h"            }
-      module iter_swap            { header "__iterator/iter_swap.h"            }
-      module iterator_traits      { header "__iterator/iterator_traits.h"      }
-      module next                 { header "__iterator/next.h"                 }
-      module prev                 { header "__iterator/prev.h"                 }
-      module projected            { header "__iterator/projected.h"            }
-      module readable_traits      { header "__iterator/readable_traits.h"      }
+      module advance                { header "__iterator/advance.h"               }
+      module back_insert_iterator   { header "__iterator/back_insert_iterator.h"  }
+      module concepts               { header "__iterator/concepts.h"              }
+      module default_sentinel       { header "__iterator/default_sentinel.h"      }
+      module front_insert_iterator  { header "__iterator/front_insert_iterator.h" }
+      module incrementable_traits   { header "__iterator/incrementable_traits.h"  }
+      module insert_iterator        { header "__iterator/insert_iterator.h"       }
+      module istream_iterator       { header "__iterator/istream_iterator.h"      }
+      module istreambuf_iterator    { header "__iterator/istreambuf_iterator.h"   }
+      module iter_move              { header "__iterator/iter_move.h"             }
+      module iter_swap              { header "__iterator/iter_swap.h"             }
+      module iterator               { header "__iterator/iterator.h"              }
+      module iterator_traits        { header "__iterator/iterator_traits.h"       }
+      module move_iterator          { header "__iterator/move_iterator.h"         }
+      module next                   { header "__iterator/next.h"                  }
+      module ostream_iterator       { header "__iterator/ostream_iterator.h"      }
+      module ostreambuf_iterator    { header "__iterator/ostreambuf_iterator.h"   }
+      module prev                   { header "__iterator/prev.h"                  }
+      module projected              { header "__iterator/projected.h"             }
+      module readable_traits        { header "__iterator/readable_traits.h"       }
+      module reverse_iterator       { header "__iterator/reverse_iterator.h"      }
+      module wrap_iter              { header "__iterator/wrap_iter.h"             }
     }
   }
   module latch {

diff  --git a/libcxx/include/regex b/libcxx/include/regex
index 5d4c52c40a18..9e5c6ed39998 100644
--- a/libcxx/include/regex
+++ b/libcxx/include/regex
@@ -765,6 +765,7 @@ typedef regex_token_iterator<wstring::const_iterator> wsregex_token_iterator;
 #include <__config>
 #include <__debug>
 #include <__functional/search.h>
+#include <__iterator/wrap_iter.h>
 #include <__locale>
 #include <compare>
 #include <deque>

diff  --git a/libcxx/include/span b/libcxx/include/span
index 80c550daa3a5..0892e25a59bc 100644
--- a/libcxx/include/span
+++ b/libcxx/include/span
@@ -129,6 +129,7 @@ template<class Container>
 
 #include <__config>
 #include <__debug>
+#include <__iterator/wrap_iter.h>
 #include <__ranges/enable_borrowed_range.h>
 #include <__ranges/enable_view.h>
 #include <array>        // for array

diff  --git a/libcxx/include/string b/libcxx/include/string
index 9b76be30ad7d..c5e0745250ee 100644
--- a/libcxx/include/string
+++ b/libcxx/include/string
@@ -516,6 +516,7 @@ basic_string<char32_t> operator "" s( const char32_t *str, size_t len ); // C++1
 #include <__config>
 #include <__debug>
 #include <__functional_base>
+#include <__iterator/wrap_iter.h>
 #include <algorithm>
 #include <compare>
 #include <cstdio>  // EOF

diff  --git a/libcxx/include/vector b/libcxx/include/vector
index bf193e5ba4c9..69babd04f7e6 100644
--- a/libcxx/include/vector
+++ b/libcxx/include/vector
@@ -275,6 +275,7 @@ erase_if(vector<T, Allocator>& c, Predicate pred);    // C++20
 #include <__bit_reference>
 #include <__debug>
 #include <__functional_base>
+#include <__iterator/wrap_iter.h>
 #include <__split_buffer>
 #include <__utility/forward.h>
 #include <algorithm>

diff  --git a/libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.fail.cpp b/libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.verify.cpp
similarity index 75%
rename from libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.fail.cpp
rename to libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.verify.cpp
index 84dcbfa49c8d..c4abf6d89f9d 100644
--- a/libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.fail.cpp
+++ b/libcxx/test/libcxx/input.output/filesystems/class.path/path.itr/reverse_iterator_produces_diagnostic.verify.cpp
@@ -20,7 +20,7 @@ int main(int, char**) {
   using namespace fs;
   using RIt = std::reverse_iterator<path::iterator>;
 
-  // expected-error-re at iterator:* {{static_assert failed{{.*}} "The specified iterator type cannot be used with reverse_iterator; Using stashing iterators with reverse_iterator causes undefined behavior"}}
+  // expected-error-re@*:* {{static_assert failed{{.*}} "The specified iterator type cannot be used with reverse_iterator; Using stashing iterators with reverse_iterator causes undefined behavior"}}
   {
     RIt r;
     ((void)r);


        


More information about the libcxx-commits mailing list