Index: libstdc++-v3/include/Makefile.in
===================================================================
--- libstdc++-v3/include/Makefile.in	(revision 141460)
+++ libstdc++-v3/include/Makefile.in	(working copy)
@@ -748,10 +748,12 @@
 	${ext_srcdir}/atomicity.h \
 	${ext_srcdir}/array_allocator.h \
 	${ext_srcdir}/bitmap_allocator.h \
+	${ext_srcdir}/cast.h \
 	${ext_srcdir}/codecvt_specializations.h \
 	${ext_srcdir}/concurrence.h \
 	${ext_srcdir}/debug_allocator.h \
 	${ext_srcdir}/enc_filebuf.h \
+	${ext_srcdir}/extptr_allocator.h \
 	${ext_srcdir}/stdio_filebuf.h \
 	${ext_srcdir}/stdio_sync_filebuf.h \
 	${ext_srcdir}/functional \
@@ -763,6 +765,7 @@
 	${ext_srcdir}/numeric \
 	${ext_srcdir}/numeric_traits.h \
 	${ext_srcdir}/pod_char_traits.h \
+	${ext_srcdir}/pointer.h \
 	${ext_srcdir}/pool_allocator.h \
 	${ext_srcdir}/rb_tree \
 	${ext_srcdir}/rope \
Index: libstdc++-v3/include/ext/cast.h
===================================================================
--- libstdc++-v3/include/ext/cast.h	(revision 0)
+++ libstdc++-v3/include/ext/cast.h	(revision 0)
@@ -0,0 +1,69 @@
+// <cast.h> -*- C++ -*-
+
+// Copyright (C) 2008 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License
+// along with this library; see the file COPYING.  If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02110-1301, USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#ifndef _EXT_CAST_
+#define _EXT_CAST_
+
+_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx);
+
+  /**
+   * These functions are here to allow containers to support non standard
+   * pointer types.  For normal pointers, these resolve to the use of the
+   * standard cast operation.  Specific pointer classes can overload these
+   * functions to provide any needed customization on how casts are done,
+   * and to support explicit casting to normal pointer types.
+   */
+
+  template<typename _ToType, typename _FromType>
+    _ToType
+    __static_pointer_cast(_FromType* arg)
+    { return static_cast<_ToType>(arg); }
+
+
+  template<typename _ToType, typename _FromType>
+    _ToType
+    __dynamic_pointer_cast(_FromType* arg)
+    { return dynamic_cast<_ToType>(arg); }
+
+
+  template<typename _ToType, typename _FromType>
+    _ToType
+    __const_pointer_cast(_FromType* arg)
+    { return const_cast<_ToType>(arg); }
+
+
+  template<typename _ToType, typename _FromType>
+    _ToType
+    __reinterpret_pointer_cast(_FromType* arg)
+    { return reinterpret_cast<_ToType>(arg); }
+
+
+_GLIBCXX_END_NAMESPACE
+
+#endif
Index: libstdc++-v3/include/ext/pointer.h
===================================================================
--- libstdc++-v3/include/ext/pointer.h	(revision 0)
+++ libstdc++-v3/include/ext/pointer.h	(revision 0)
@@ -0,0 +1,610 @@
+// Custom pointer adapter and sample storage policies
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+/**
+ * @file ext/pointer.h
+ * @author Bob Walters
+ *
+ * Provides reusable _Pointer_adapter for assisting in the development of
+ * custom pointer types that can be used with libstdc++ STL containers via
+ * the allocator::pointer and allocator::const_pointer typedefs.
+ */
+
+#ifndef _EXT_POINTER_ADAPTER
+#define _EXT_POINTER_ADAPTER 1
+
+#include <ostream>
+#include <ext/cast.h>
+#include <bits/concept_check.h>
+
+
+// forward declaration of the iterator tag
+namespace std {
+  struct random_access_iterator_tag;
+};
+
+
+_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
+
+  /** 
+   * @brief A storage policy for use with _Pointer_adapter<> which yields a
+   *        standard pointer.
+   * 
+   *  A _Storage_policy is required to provide 5 things:
+   *    1) A get() API for returning the stored pointer value.
+   *    2) An set() API for storing a pointer value.
+   *    3) An element_type typedef to define the type this points to.
+   *    4) An operator<() to support pointer comparison.
+   *    5) An operator==() to support pointer comparison.
+   */
+  template<typename _Type> 
+    class _Std_pointer_impl 
+    {
+    public:
+      // the type this pointer points to.
+      typedef _Type element_type;
+  
+      // A method to fetch the pointer value as a standard T* value;
+      inline _Type* 
+      get() const 
+      { return _M_value; }
+  
+      // A method to set the pointer value, from a standard T* value;
+      inline void 
+      set(element_type* __arg) 
+      { _M_value = __arg; }
+  
+      // Comparison of pointers
+      inline bool
+      operator<(const _Std_pointer_impl& __rarg) const
+      { return (_M_value < __rarg._M_value); }
+  
+      inline bool
+      operator==(const _Std_pointer_impl& __rarg) const
+      { return (_M_value == __rarg._M_value); }
+
+    private:
+      element_type* _M_value;
+    };
+
+
+  /**
+   * @brief A storage policy for use with _Pointer_adapter<> which stores
+   *        the pointer's address as an offset value which is relative to
+   *        its own address.
+   * 
+   * This is intended for pointers
+   * within shared memory regions which might be mapped at different
+   * addresses by different processes.  For null pointers, a value of 1 is
+   * used.  (0 is legitimate sometimes for nodes in circularly linked lists)
+   * This value was chosen as the least likely to generate an incorrect null,
+   * As there is no reason why any normal pointer would point 1 byte into
+   * its own pointer address.
+   */
+  template<typename _Type> 
+    class _Relative_pointer_impl 
+    {
+    public:
+      typedef _Type element_type;
+  
+      _Type* 
+      get() const 
+      {
+        if (_M_diff == 1)
+          return NULL;
+        else
+          return reinterpret_cast<_Type*>(
+                 const_cast<char*>(reinterpret_cast<const char*>(this))
+                 + _M_diff);
+      }
+  
+      void 
+      set(_Type* __arg)
+      {
+        if (__arg == NULL)
+          _M_diff = 1;
+        else
+          _M_diff = reinterpret_cast<char*>(__arg) 
+                    - reinterpret_cast<char*>(this);
+      }
+  
+      // Comparison of pointers
+      inline bool
+      operator<(const _Relative_pointer_impl& __rarg) const
+      { return (this->get() < __rarg.get()); }
+
+      inline bool
+      operator==(const _Relative_pointer_impl& __rarg) const
+      { return (this->get() == __rarg.get()); }
+
+    private:
+      ptrdiff_t _M_diff;
+    };
+  
+  /**
+   * Relative_pointer_impl needs a specialization for const T because of
+   * the casting done during pointer arithmetic.
+   */
+  template<typename _Type> 
+    class _Relative_pointer_impl<const _Type> 
+    {
+    public:
+      typedef const _Type element_type;
+  
+      const _Type* 
+      get() const
+      {
+        if (_M_diff == 1)
+          return NULL;
+        else
+          return reinterpret_cast<const _Type*>(
+                  (reinterpret_cast<const char*>(this)) + _M_diff);
+      }
+  
+      void 
+      set(const _Type* __arg) 
+      {
+        if (__arg == NULL)
+          _M_diff = 1;
+        else
+          _M_diff = reinterpret_cast<const char*>(__arg) 
+                    - reinterpret_cast<const char*>(this);
+      }
+  
+      // Comparison of pointers
+      inline bool
+      operator<(const _Relative_pointer_impl& __rarg) const
+      { return (this->get() < __rarg.get()); }
+
+      inline bool
+      operator==(const _Relative_pointer_impl& __rarg) const
+      { return (this->get() == __rarg.get()); }
+  
+    private:
+      ptrdiff_t _M_diff;
+    };
+
+
+  /**
+   * The specialization on this type helps resolve the problem of
+   * reference to void, and eliminates the need to specialize _Pointer_adapter
+   * for cases of void*, const void*, and so on.
+   */
+  struct _Invalid_type { };
+  
+  template<typename _Tp>
+    struct _Reference_type 
+    {
+      typedef _Tp& reference;
+    };
+
+  template<> 
+    struct _Reference_type<void> 
+    {
+      typedef _Invalid_type& reference;
+    };
+
+  template<> 
+    struct _Reference_type<const void> 
+    {
+      typedef const _Invalid_type& reference;
+    };
+
+  template<> 
+    struct _Reference_type<volatile void> 
+    {
+      typedef volatile _Invalid_type&  reference;
+    };
+
+  template<> 
+    struct _Reference_type<volatile const void> 
+    {
+      typedef const volatile _Invalid_type&  reference;
+    };
+
+
+  /**
+   * This structure accomodates the way in which std::iterator_traits<>
+   * is normally specialized for const T*, so that value_type is still T.
+   */
+  template<typename _Tp> 
+    struct _Unqualified_type 
+    {
+      typedef _Tp type;
+    };
+    
+  template<typename _Tp> 
+    struct _Unqualified_type<const _Tp> 
+    {
+      typedef _Tp type;
+    };
+    
+  template<typename _Tp> 
+    struct _Unqualified_type<volatile _Tp> 
+    {
+      typedef volatile _Tp type;
+    };
+    
+  template<typename _Tp> 
+    struct _Unqualified_type<volatile const _Tp> 
+    {
+      typedef volatile _Tp type;
+    };
+    
+  
+  
+  /**
+   * The following provides an 'alternative pointer' that works with 
+   * libstdc++-v3 containers when specified as the pointer typedef of the 
+   * allocator.
+   * 
+   * The pointer type used with the containers doesn't have to be this class,
+   * but it must support the implicit conversions, pointer arithmetic,
+   * comparison operators, etc. that are supported by this class, and avoid
+   * raising compile-time ambiguities.  Because creating a working pointer can
+   * be challenging, this pointer template was designed to wrapper an 
+   * easier storage policy type, so that it becomes reusable for creating
+   * other pointer types. 
+   *
+   * A key point of this class is also that it allows container writers to
+   * 'assume' Alocator::pointer is a typedef for a normal pointer.  This class
+   * supports most of the conventions of a true pointer, and can, for instance
+   * handle implicit conversion to const and base class pointer types.  The
+   * only impositions on container writers to support extended pointers are:
+   * 1) use the Allocator::pointer typedef appropriately for pointer types.
+   * 2) if you need pointer casting, use the __pointer_cast<> functions
+   *    from ext/cast.h.  This allows pointer cast operations to be overloaded
+   *    is necessary by custom pointers.
+   *
+   * Note:  The const qualifier works with this pointer adapter as follows:
+   *
+   * _Tp*             == _Pointer_adapter<_Std_pointer_impl<_Tp> >;
+   * const _Tp*       == _Pointer_adapter<_Std_pointer_impl<const _Tp> >;
+   * _Tp* const       == const _Pointer_adapter<_Std_pointer_impl<_Tp> >;
+   * const _Tp* const == const _Pointer_adapter<_Std_pointer_impl<const _Tp> >;
+   */
+ 
+  template<typename _Storage_policy >
+    class _Pointer_adapter : public _Storage_policy 
+    {
+    public:
+      typedef typename _Storage_policy::element_type element_type;
+  
+      // These are needed for iterator_traits
+      typedef std::random_access_iterator_tag                iterator_category;
+      typedef typename _Unqualified_type<element_type>::type value_type;
+      typedef ptrdiff_t                                      difference_type;
+      typedef _Pointer_adapter                               pointer;
+      typedef typename _Reference_type<element_type>::reference  reference;
+  
+      // Reminder: 'const' methods mean that the method is valid when the 
+      // pointer is immutable, and has nothing to do with whether the 
+      // 'pointee' is const.
+
+      // Default Constructor (Convert from element_type*)
+      _Pointer_adapter(element_type* __arg = NULL)
+      { _Storage_policy::set(__arg); }
+  
+      // Copy constructor from _Pointer_adapter of same type.
+      _Pointer_adapter(const _Pointer_adapter& __arg) 
+      { _Storage_policy::set(__arg.get()); }
+  
+      // Convert from _Up* if conversion to element_type* is valid.
+      template<typename _Up>
+        _Pointer_adapter(_Up*__arg)
+        {
+          __glibcxx_function_requires(_ConvertibleConcept<element_type*, _Up*>);
+          _Storage_policy::set(__arg); 
+        }
+  
+      // Conversion from another _Pointer_adapter if _Up if static cast is valid.
+      template<typename _Up>
+        _Pointer_adapter(const _Pointer_adapter<_Up>& __arg)
+        { 
+          __glibcxx_function_requires(_ConvertibleConcept<element_type*, 
+            typename _Pointer_adapter<_Up>::element_type*>);
+          _Storage_policy::set(__arg.get()); 
+        }
+  
+      // Destructor
+      ~_Pointer_adapter() { }
+  
+      // Assignment operator
+      _Pointer_adapter&
+      operator=(const _Pointer_adapter& __arg) 
+      {
+        _Storage_policy::set(__arg.get()); 
+        return *this; 
+      }
+ 
+      template<typename _Up>
+        _Pointer_adapter&
+        operator=(const _Pointer_adapter<_Up>& __arg)
+        {
+          _Storage_policy::set(__arg.get()); 
+          return *this; 
+        }
+
+      template<typename _Up>
+        _Pointer_adapter&
+        operator=(_Up* __arg)
+        {
+          _Storage_policy::set(__arg); 
+          return *this; 
+        }
+
+      // Operator*, returns element_type&
+      inline reference 
+      operator*() const 
+      { return *(_Storage_policy::get()); }
+  
+      // Operator->, returns element_type*
+      inline element_type* 
+      operator->() const 
+      { return _Storage_policy::get(); }
+  
+      // Operator[], returns a element_type& to the item at that loc.
+      inline reference 
+      operator[](int __index) const
+      { return _Storage_policy::get()[__index]; }
+  
+      // To allow implicit conversion to "bool", for "if (ptr)..."
+    private:
+      typedef element_type*(_Pointer_adapter::*__unspecified_bool_type)() const;
+
+    public:
+      operator __unspecified_bool_type() const
+      {
+        return _Storage_policy::get() == 0 ? 0 : 
+                         &_Pointer_adapter::operator->; 
+      }
+
+      // ! operator (for: if (!ptr)...)
+      inline bool 
+      operator!() const 
+      { return (_Storage_policy::get()==NULL); }
+  
+      // Pointer differences
+      inline friend std::ptrdiff_t 
+      operator-(const _Pointer_adapter& __lhs, element_type* __rhs) 
+      { return (__lhs.get() - __rhs); }
+  
+      inline friend std::ptrdiff_t 
+      operator-(element_type* __lhs, const _Pointer_adapter& __rhs) 
+      { return (__lhs - __rhs.get()); }
+  
+      template<class _Up>
+        inline friend std::ptrdiff_t 
+        operator-(const _Pointer_adapter& __lhs, _Up* __rhs) 
+        { return (__lhs.get() - __rhs); }
+    
+      template<class _Up>
+        inline friend std::ptrdiff_t 
+        operator-(_Up* __lhs, const _Pointer_adapter& __rhs)
+        { return (__lhs - __rhs.get()); }
+
+      template<typename _Up>
+        inline std::ptrdiff_t 
+        operator-(const _Pointer_adapter<_Up>& __rhs) const 
+        { return (_Storage_policy::get() - __rhs.get()); }
+  
+      // Pointer math
+      // Note: There is a reason for all this overloading based on different
+      // integer types.  In some libstdc++-v3 test cases, a templated
+      // operator+ is declared which can match any types.  This operator
+      // tends to "steal" the recognition of _Pointer_adapter's own operator+ 
+      // unless the integer type matches perfectly.
+
+#define _CXX_POINTER_ARITH_OPERATOR_SET(INT_TYPE) \
+      inline friend _Pointer_adapter \
+      operator+(const _Pointer_adapter& __lhs, INT_TYPE __offset) \
+      { return _Pointer_adapter(__lhs.get() + __offset); } \
+\
+      inline friend _Pointer_adapter \
+      operator+(INT_TYPE __offset, const _Pointer_adapter& __rhs) \
+      { return _Pointer_adapter(__rhs.get() + __offset); } \
+\
+      inline friend _Pointer_adapter \
+      operator-(const _Pointer_adapter& __lhs, INT_TYPE __offset) \
+      { return _Pointer_adapter(__lhs.get() - __offset); } \
+\
+      inline _Pointer_adapter& \
+      operator+=(INT_TYPE __offset) \
+      { \
+        _Storage_policy::set(_Storage_policy::get() + __offset); \
+        return *this; \
+      } \
+\
+      inline _Pointer_adapter& \
+      operator-=(INT_TYPE __offset) \
+      { \
+        _Storage_policy::set(_Storage_policy::get() - __offset); \
+        return *this; \
+      } \
+// END of _CXX_POINTER_ARITH_OPERATOR_SET macro
+  
+      // Expand into the various pointer arithmatic operators needed.
+      _CXX_POINTER_ARITH_OPERATOR_SET(short);
+      _CXX_POINTER_ARITH_OPERATOR_SET(unsigned short);
+      _CXX_POINTER_ARITH_OPERATOR_SET(int);
+      _CXX_POINTER_ARITH_OPERATOR_SET(unsigned int);
+      _CXX_POINTER_ARITH_OPERATOR_SET(long);
+      _CXX_POINTER_ARITH_OPERATOR_SET(unsigned long);
+
+      // Mathematical Manipulators
+      inline _Pointer_adapter& 
+      operator++()
+      {
+        _Storage_policy::set(_Storage_policy::get() + 1); 
+        return *this;
+      }
+  
+      inline _Pointer_adapter 
+      operator++(int __unused) 
+      {
+        _Pointer_adapter tmp(*this);
+        _Storage_policy::set(_Storage_policy::get() + 1);
+        return tmp;
+      }
+  
+      inline _Pointer_adapter& 
+      operator--() 
+      {
+        _Storage_policy::set(_Storage_policy::get() - 1); 
+        return *this;
+      }
+  
+      inline _Pointer_adapter
+      operator--(int __unused) 
+      {
+        _Pointer_adapter tmp(*this);
+        _Storage_policy::set(_Storage_policy::get() - 1);
+        return tmp;
+      }
+  
+    }; // class _Pointer_adapter
+
+
+#define _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(OPERATOR,BLANK) \
+  template<typename _Tp1, typename _Tp2> \
+    inline bool \
+    operator OPERATOR##BLANK (const _Pointer_adapter<_Tp1>& __lhs, _Tp2 __rhs) \
+    { return __lhs.get() OPERATOR##BLANK __rhs; } \
+\
+  template<typename _Tp1, typename _Tp2> \
+    inline bool \
+    operator OPERATOR##BLANK (_Tp1 __lhs, const _Pointer_adapter<_Tp2>& __rhs) \
+    { return __lhs OPERATOR##BLANK __rhs.get(); } \
+\
+  template<typename _Tp1, typename _Tp2> \
+    inline bool \
+    operator OPERATOR##BLANK (const _Pointer_adapter<_Tp1>& __lhs, \
+                              const _Pointer_adapter<_Tp2>& __rhs) \
+    { return __lhs.get() OPERATOR##BLANK __rhs.get(); } \
+\
+// End GCC_CXX_POINTER_COMPARISON_OPERATION_SET Macro
+  
+  // Expand into the various comparison operators needed.
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(==,);
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(!=,);
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(<,);
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(<=,);
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(>,);
+  _GCC_CXX_POINTER_COMPARISON_OPERATION_SET(>=,);
+
+  /**
+   * Comparison operators for _Pointer_adapter defer to the base class'es
+   * comparison operators, when possible.
+   */
+  template<typename _Tp>
+    inline bool
+    operator==(const _Pointer_adapter<_Tp>& __lhs, 
+               const _Pointer_adapter<_Tp>& __rhs)
+    { return __lhs._Tp::operator==(__rhs); }
+  
+  template<typename _Tp>
+    inline bool
+    operator<=(const _Pointer_adapter<_Tp>& __lhs, 
+               const _Pointer_adapter<_Tp>& __rhs)
+    { return __lhs._Tp::operator<(__rhs) || __lhs._Tp::operator==(__rhs); }
+  
+  template<typename _Tp>
+    inline bool
+    operator!=(const _Pointer_adapter<_Tp>& __lhs, 
+               const _Pointer_adapter<_Tp>& __rhs)
+    { return !(__lhs._Tp::operator==(__rhs)); }
+  
+  template<typename _Tp>
+    inline bool
+    operator>(const _Pointer_adapter<_Tp>& __lhs, 
+              const _Pointer_adapter<_Tp>& __rhs)
+    { return !(__lhs._Tp::operator<(__rhs) || __lhs._Tp::operator==(__rhs)); }
+  
+  template<typename _Tp>
+    inline bool
+    operator>=(const _Pointer_adapter<_Tp>& __lhs, 
+               const _Pointer_adapter<_Tp>& __rhs)
+    { return !(__lhs._Tp::operator<(__rhs)); }
+  
+  
+  template<class _CharT, class _Traits, class _StoreT>
+    std::basic_ostream<_CharT, _Traits>&
+    operator<<(std::basic_ostream<_CharT, _Traits> &os, 
+               const _Pointer_adapter<_StoreT>& __p)
+    {
+      os << __p.get();
+      return os;
+    }
+
+  /**
+   * This type supports the semantics of the pointer cast operators (below.)
+   */
+  template<typename _ToType> 
+    struct caster 
+    {
+      typedef typename _ToType::element_type*  type;
+    };
+  template<typename _ToType> 
+    struct caster<_ToType*> 
+    {
+      typedef _ToType*  type;
+    };
+
+  /**
+   * _Pointer_adapter overloads the pointer_cast() functions of cast.h to
+   * provide casting between _Pointer_adapter types.  These functions support
+   * the casting of a _Pointer_adapter to another type of _Pointer_adapter
+   * or to a type of raw pointer, as long as the equivalent raw pointer cast
+   * would be valid.
+   */
+  template<typename _ToType, typename _FromType>
+    inline _ToType
+    __static_pointer_cast(const _Pointer_adapter<_FromType>& arg)
+    { return _ToType(static_cast<typename caster<_ToType>::type>(arg.get())); }
+
+  template<typename _ToType, typename _FromType>
+    inline _ToType
+    __dynamic_pointer_cast(const _Pointer_adapter<_FromType>& arg)
+    { return _ToType(dynamic_cast<typename caster<_ToType>::type>(arg.get())); }
+
+  template<typename _ToType, typename _FromType>
+    inline _ToType
+    __const_pointer_cast(const _Pointer_adapter<_FromType>& arg)
+    { return _ToType(const_cast<typename caster<_ToType>::type>(arg.get())); }
+
+  template<typename _ToType, typename _FromType>
+    inline _ToType
+    __reinterpret_pointer_cast(const _Pointer_adapter<_FromType>& arg)
+    { return _ToType(reinterpret_cast<typename caster<_ToType>::type>(arg.get())); }
+
+ 
+_GLIBCXX_END_NAMESPACE
+
+#endif /* _GCC_EXT_POINTER_ADAPTER */
Index: libstdc++-v3/include/ext/extptr_allocator.h
===================================================================
--- libstdc++-v3/include/ext/extptr_allocator.h	(revision 0)
+++ libstdc++-v3/include/ext/extptr_allocator.h	(revision 0)
@@ -0,0 +1,184 @@
+// <extptr_allocator.h> -*- C++ -*-
+
+// Copyright (C) 2008 Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License
+// along with this library; see the file COPYING.  If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02110-1301, USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+/**
+ * @file ext/extptr_allocator.h
+ * @author Bob Walters
+ *
+ * An example allocator which uses an alternative pointer type from
+ * bits/pointer.h.  Supports test cases which confirm container support
+ * for alternative pointers.
+ */
+
+#ifndef _EXTPTR_ALLOCATOR_H
+#define _EXTPTR_ALLOCATOR_H 1
+
+#include <memory>
+#include <limits>
+#include <ext/pointer.h>
+
+using __gnu_cxx::_Pointer_adapter;
+using __gnu_cxx::_Relative_pointer_impl;
+using __gnu_cxx::__static_pointer_cast;
+using __gnu_cxx::__const_pointer_cast;
+
+
+_GLIBCXX_BEGIN_NAMESPACE(__gnu_cxx)
+
+
+  // forward declaration
+  template<typename _Tp>
+    class _ExtPtr_allocator;
+
+
+  // _ExtPtr_allocator<void> specialization.
+  template<>
+    class _ExtPtr_allocator<void>
+    {
+    public:
+      typedef size_t      size_type;
+      typedef ptrdiff_t   difference_type;
+      typedef void        value_type;
+
+      // Note the non-standard pointer types
+      typedef _Pointer_adapter<_Relative_pointer_impl<void> >       pointer;
+      typedef _Pointer_adapter<_Relative_pointer_impl<const void> > const_pointer;
+
+      template<typename _Up>
+        struct rebind
+        { typedef _ExtPtr_allocator<_Up> other; };
+    };
+
+
+  /**
+   * @brief An example allocator which uses a non-standard pointer type.
+   *
+   * This allocator specifies that containers use a 'relative pointer' as it's
+   * pointer type.  (See bits/pointer.h)  Memory allocation in this example
+   * is still performed using std::allocator.
+   */
+  template<typename _Tp>
+    class _ExtPtr_allocator
+    {
+    public:
+      typedef size_t     size_type;
+      typedef ptrdiff_t  difference_type;
+
+      // Note the non-standard pointer types.
+      typedef _Pointer_adapter<_Relative_pointer_impl<_Tp> >       pointer;
+      typedef _Pointer_adapter<_Relative_pointer_impl<const _Tp> > const_pointer;
+
+      typedef _Tp&       reference;
+      typedef const _Tp& const_reference;
+      typedef _Tp        value_type;
+
+      template<typename _Up>
+        struct rebind
+        { typedef _ExtPtr_allocator<_Up> other; };
+
+      _ExtPtr_allocator() throw() 
+      : _m_real_alloc() { }
+
+      _ExtPtr_allocator(const _ExtPtr_allocator &__rarg) throw()
+      : _m_real_alloc(__rarg._m_real_alloc) { }
+
+      template<class _Up>
+        _ExtPtr_allocator(const _ExtPtr_allocator<_Up>& __rarg) throw()
+        : _m_real_alloc(__rarg._M_getUnderlyingImp()) { }
+
+      ~_ExtPtr_allocator() throw()
+      { }
+
+      pointer address(reference __x) const
+      { return &__x; }
+
+      const_pointer address(const_reference __x) const
+      { return &__x; }
+
+      pointer allocate(size_type __n, void* __hint = 0)
+      { return _m_real_alloc.allocate(__n,__hint); }
+
+      void deallocate(pointer __p, size_type __n)
+      { _m_real_alloc.deallocate(__static_pointer_cast<_Tp*>(__p), __n); }
+
+      size_type max_size() const throw()
+      { return std::numeric_limits<size_type>::max() / sizeof(_Tp); }
+
+      void construct(pointer __p, const _Tp& __val)
+      { ::new(__static_pointer_cast<void*>(__p)) _Tp(__val); }
+
+      void destroy(pointer __p)
+      { __p->~_Tp(); }
+
+      template<typename _Up>
+        inline bool
+        operator==(const _ExtPtr_allocator<_Up>& __rarg)
+        { return _m_real_alloc == __rarg._M_getUnderlyingImp(); }
+
+      inline bool
+      operator==(const _ExtPtr_allocator& __rarg)
+      { return _m_real_alloc == __rarg._m_real_alloc; }
+
+      template<typename _Up>
+        inline bool
+        operator!=(const _ExtPtr_allocator<_Up>& __rarg)
+        { return _m_real_alloc != __rarg._M_getUnderlyingImp(); }
+
+      inline bool
+      operator!=(const _ExtPtr_allocator& __rarg)
+      { return _m_real_alloc != __rarg._m_real_alloc; }
+
+      template<typename _Up>
+        inline friend void
+        swap(_ExtPtr_allocator<_Up>& __larg, _ExtPtr_allocator<_Up>& __rarg);
+
+      // A method specific to this implementation.
+      const std::allocator<_Tp>&
+      _M_getUnderlyingImp() const
+      { return _m_real_alloc; }
+
+    private:
+      // simlated state data.
+      std::allocator<_Tp>  _m_real_alloc;
+    };
+
+
+  template<typename _Tp>
+    inline void
+    swap(_ExtPtr_allocator<_Tp>& __larg, _ExtPtr_allocator<_Tp>& __rarg)
+    {
+      std::allocator<_Tp> temp( __rarg._m_real_alloc );
+      __rarg._m_real_alloc = __larg._m_real_alloc;
+      __larg._m_real_alloc = temp;
+    }
+
+
+_GLIBCXX_END_NAMESPACE
+
+#endif /* _EXTPTR_ALLOCATOR_H */
Index: libstdc++-v3/include/Makefile.am
===================================================================
--- libstdc++-v3/include/Makefile.am	(revision 141460)
+++ libstdc++-v3/include/Makefile.am	(working copy)
@@ -484,10 +484,12 @@
 	${ext_srcdir}/atomicity.h \
 	${ext_srcdir}/array_allocator.h \
 	${ext_srcdir}/bitmap_allocator.h \
+	${ext_srcdir}/cast.h \
 	${ext_srcdir}/codecvt_specializations.h \
 	${ext_srcdir}/concurrence.h \
 	${ext_srcdir}/debug_allocator.h \
 	${ext_srcdir}/enc_filebuf.h \
+	${ext_srcdir}/extptr_allocator.h \
 	${ext_srcdir}/stdio_filebuf.h \
 	${ext_srcdir}/stdio_sync_filebuf.h \
 	${ext_srcdir}/functional \
@@ -499,6 +501,7 @@
 	${ext_srcdir}/numeric \
 	${ext_srcdir}/numeric_traits.h \
 	${ext_srcdir}/pod_char_traits.h \
+	${ext_srcdir}/pointer.h \
 	${ext_srcdir}/pool_allocator.h \
 	${ext_srcdir}/rb_tree \
 	${ext_srcdir}/rope \
Index: libstdc++-v3/ChangeLog
===================================================================
--- libstdc++-v3/ChangeLog	(revision 141460)
+++ libstdc++-v3/ChangeLog	(working copy)
@@ -1,3 +1,20 @@
+2008-10-29  Bob Walters <bob.s.walters@gmail.com>
+
+	* include/ext/pointer.h: Add experimental support for non-standard
+	pointer types in containers via the allocator::pointer typedef.
+	(Currently only supported/working with vector<>)
+	* include/ext/cast.h: Add overload-able pointer casting functions
+	for use in containers supporting non-standard pointer types.
+	* include/ext/extptr_allocator.h: Add funtional allocator designating
+	* include/Makefile.am: Add ext/pointer.h, ext/extptr_allocator.h,
+	ext/cast.h
+	* include/Makefile.in: Regenerate.
+	non-standard pointer type (for testing/example)
+	* testsuite/ext/ext_pointer/*: Add new tests to confirm ext/pointer.h 
+	adherance to pointer semantics.
+	* testsuite/23_containers/vector/ext_pointer/*: Add new tests for 
+	vector<> using non-standard pointer types via extptr_allocator.
+
 2008-10-27  Paolo Carlini  <paolo.carlini@oracle.com>
 
 	PR libstdc++/37919
Index: libstdc++-v3/testsuite/ext/ext_pointer/1.cc
===================================================================
--- libstdc++-v3/testsuite/ext/ext_pointer/1.cc	(revision 0)
+++ libstdc++-v3/testsuite/ext/ext_pointer/1.cc	(revision 0)
@@ -0,0 +1,201 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <algorithm>
+#include <testsuite_hooks.h>
+#include <ext/pointer.h>
+
+using __gnu_cxx::_Pointer_adapter;
+using __gnu_cxx::_Relative_pointer_impl;
+using __gnu_cxx::__static_pointer_cast;
+using __gnu_cxx::__const_pointer_cast;
+
+
+void 
+test01() {
+
+  typedef _Pointer_adapter<_Relative_pointer_impl<int> >       pointer;
+  typedef _Pointer_adapter<_Relative_pointer_impl<const int> > const_pointer;
+
+  int A[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
+
+  // basic pointer assignment/access tests.
+  pointer x = &A[0];
+  VERIFY(*x == 0);
+  VERIFY(std::equal(x, x+10, A)); 
+  pointer y(&A[9]);
+  VERIFY(*y == 9);
+
+  // assignability
+  pointer z(x);
+  VERIFY(z==x);
+  VERIFY(*z == 0);
+
+  z = y;
+  VERIFY(z==y);
+  VERIFY(z!=x);
+  VERIFY(z>x);
+  VERIFY(*z == 9);
+  
+  // pointer arithmetic
+  VERIFY(*++x == 1);
+  VERIFY(*--x == 0);
+  VERIFY(*(x++) == 0);
+  VERIFY(*(x--) == 1);
+  VERIFY(*(x+2) == 2);
+  VERIFY(*(2+x) == 2);
+  VERIFY(*(y-2) == 7);
+  VERIFY(y - x == 9);
+  VERIFY(&*y - x == 9);
+  VERIFY(y - &*x == 9);
+  
+  size_t s(y - x);
+  VERIFY(s == 9);
+}
+
+
+struct A {
+  mutable int i;
+};
+struct B : public A{
+  mutable int j;
+};
+typedef _Pointer_adapter<_Relative_pointer_impl<B> >       B_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<A> >       A_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<const A> > const_A_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<const B> > const_B_pointer; 
+
+
+// Test implicit conversion from B* to A*
+void inc(_Pointer_adapter<_Relative_pointer_impl<A> > a) {
+  a->i++;
+}
+// Test implicit conversion from B* to const B*
+void inc2(_Pointer_adapter<_Relative_pointer_impl<const B> > b) {
+  b->i++;
+  b->j++;
+}
+// Test implicit conversion from B* to const A*
+void inc3(_Pointer_adapter<_Relative_pointer_impl<const A> > a) {
+  a->i++;
+}
+
+void test02() {
+  B b;
+  b.i = 2;
+  b.j = 2;
+
+  B_pointer Bptr(&b);
+  VERIFY(Bptr->i == 2);
+  Bptr->i++;
+  VERIFY(b.i == 3);
+  
+  const_B_pointer cBptr(&b);
+  b.i++;
+  VERIFY(cBptr->i == 4);
+  
+  A_pointer Aptr(&b);
+  b.i++;
+  VERIFY(Aptr->i == 5);
+  Aptr->i++;
+  VERIFY(b.i == 6);
+  
+  const_A_pointer cAptr(&b);
+  b.i++;
+  VERIFY(cAptr->i == 7);
+
+  const_B_pointer cBptr2(Bptr);
+  b.i++;
+  VERIFY(cBptr2->i == 8);
+  
+  A_pointer Aptr2(Bptr);
+  b.i++;
+  VERIFY(Aptr2->i == 9);
+  Aptr2->i++;
+  VERIFY(b.i == 10);
+
+  const_A_pointer cAptr2(Bptr);
+  b.i++;
+  VERIFY(cAptr2->i == 11);
+
+  // Implicit casting during invocation
+  inc(Bptr);
+  VERIFY(Bptr->i == 12);
+  inc2(Bptr);
+  VERIFY(Bptr->i == 13);
+  VERIFY(Bptr->j == 3);
+  inc3(Bptr);
+  VERIFY(Bptr->i == 14);
+}
+
+void test03() {
+
+  B b;
+  B* bPtr = &b;
+  A* aPtr = static_cast<A*>(bPtr);
+  const A *caPtr = static_cast<const A*>(bPtr);
+  const B *cbPtr = static_cast<const B*>(bPtr);
+
+  B_pointer Bptr2 = &b;
+
+  const A* caPtr2 = __static_pointer_cast<const A*>(Bptr2);
+  A * aPtr2 = __static_pointer_cast<A*>(Bptr2);
+  const B* cbPtr2 = __const_pointer_cast<const B*>(Bptr2);
+
+  const_A_pointer caPtr3 = __static_pointer_cast<const A*>(Bptr2);
+  A_pointer aPtr3 = __static_pointer_cast<A*>(Bptr2);
+  const_B_pointer cbPtr3 = __const_pointer_cast<const B*>(Bptr2);
+}
+
+// Confirm the usability of the __static_pointer_cast<> template function
+// to transform between _Pointer_adapter and standard versions.
+void test04() {
+  B b;
+  B_pointer bPtr = &b;
+
+  A_pointer aPtr = __static_pointer_cast<A_pointer>(bPtr);
+  VERIFY(aPtr == bPtr);
+  B_pointer bPtr2 = __static_pointer_cast<B_pointer>(aPtr);
+  VERIFY(bPtr2 == aPtr);
+
+  A* aPtr3 = __static_pointer_cast<A*>(bPtr);
+  VERIFY(aPtr3 == bPtr);
+  B* bPtr3 = __static_pointer_cast<B*>(aPtr);
+  VERIFY(bPtr3 == aPtr);
+}
+
+int main()
+{
+  test01();
+  test02();
+  test03();
+  test04();
+  return 0;
+}
Index: libstdc++-v3/testsuite/ext/ext_pointer/1_neg.cc
===================================================================
--- libstdc++-v3/testsuite/ext/ext_pointer/1_neg.cc	(revision 0)
+++ libstdc++-v3/testsuite/ext/ext_pointer/1_neg.cc	(revision 0)
@@ -0,0 +1,110 @@
+// Bob Walters 10-2008
+
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+// { dg-do compile }
+
+#include <algorithm>
+#include <testsuite_hooks.h>
+#include <ext/pointer.h>
+
+using __gnu_cxx::_Pointer_adapter;
+using __gnu_cxx::_Relative_pointer_impl;
+using __gnu_cxx::__static_pointer_cast;
+using __gnu_cxx::__const_pointer_cast;
+
+
+struct A {
+  int i;
+};
+struct B : public A{
+  int j;
+};
+typedef _Pointer_adapter<_Relative_pointer_impl<B> > B_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<const B> > const_B_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<A> > A_pointer; 
+typedef _Pointer_adapter<_Relative_pointer_impl<const A> > const_A_pointer; 
+
+
+void test01(void) {
+  A a;
+  B b;
+
+  A_pointer aptr( &a );
+
+  // Can't implicitly cast from A* to B*
+  B_pointer bptr1(aptr); // { dg-error "instantiated from here" 31 }
+  B_pointer bptr2(&a); // { dg-error "instantiated from here" 32 }
+
+  // but explicit cast/conversion is OK.
+  B_pointer bptr3(__static_pointer_cast<B_pointer>(aptr)); // ok
+  B_pointer bptr4(__static_pointer_cast<B_pointer>(&a)); // ok
+
+  // Can't implicitly cast from A* to B*
+  bptr1 = aptr; // { dg-error "instantiated from here" 39 }
+  bptr1 = &a; // { dg-error "instantiated from here" 40 }
+
+  // but explicit cast/conversion is OK.
+  bptr1 = __static_pointer_cast<B_pointer>(aptr); // ok
+  bptr1 = __static_pointer_cast<B_pointer>(&a); // ok
+
+  // Similarly, can't shed constness via implicit cast
+  const_A_pointer captr(&a);
+  A_pointer aptr2(captr); // { dg-error "instantiated from here" 48 }
+
+  // but explicit cast/conversion is OK.
+  A_pointer aptr3(__const_pointer_cast<A_pointer>(captr)); // ok
+
+  // Similarly, can't shed constness via implicit cast
+  aptr2 = captr; // { dg-error "instantiated from here" 54 }
+
+  // but explicit cast/conversion is OK.
+  aptr3 = __const_pointer_cast<A_pointer>(captr); // ok
+
+  // Combine explicit const cast with implicit downcast.
+  const_B_pointer cbptr(&b);
+  A_pointer aptr4(cbptr); // { dg-error "instantiated from here" 61 }
+  aptr4 = cbptr; // { dg-error "instantiated from here" 62 }
+
+  A_pointer aptr5(__const_pointer_cast<B_pointer>(cbptr)); // ok
+  aptr5 = __const_pointer_cast<B_pointer>(cbptr);  // ok
+}
+
+// { dg-error "invalid conversion " "" { target *-*-* } 333 }
+// { dg-error "initializing argument 1 of" "" { target *-*-* } 333 }
+// { dg-error "invalid conversion " "" { target *-*-* } 324 }
+// { dg-error "initializing argument 1 of" "" { target *-*-* } 324 }
+// { dg-error "invalid conversion " "" { target *-*-* } 351 }
+// { dg-error "initializing argument 1 of" "" { target *-*-* } 351 }
+// { dg-error "invalid conversion " "" { target *-*-* } 359 }
+// { dg-error "initializing argument 1 of" "" { target *-*-* } 359 }
+// { dg-excess-errors "In constructor" }
+
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/erase.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/erase.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/erase.cc	(revision 0)
@@ -0,0 +1,153 @@
+// Bob Walters 10-2008
+
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+
+const int  A[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15};
+const int A1[] = {0, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15};
+const int A2[] = {0, 2, 3, 4, 10, 11, 12, 13, 14, 15};
+const int A3[] = {0, 2, 3, 4, 10, 11};
+const int A4[] = {4, 10, 11};
+const int A5[] = {4, 10};
+const unsigned int  N = sizeof(A)  / sizeof(int);
+const unsigned int N1 = sizeof(A1) / sizeof(int);
+const unsigned int N2 = sizeof(A2) / sizeof(int);
+const unsigned int N3 = sizeof(A3) / sizeof(int);
+const unsigned int N4 = sizeof(A4) / sizeof(int);
+const unsigned int N5 = sizeof(A5) / sizeof(int);
+
+void
+test01()
+{
+  bool test __attribute__((unused)) = true;
+
+  typedef std::vector<int,__gnu_cxx::_ExtPtr_allocator<int> >  vec_type;
+  typedef vec_type::iterator iterator_type;
+
+  vec_type v(A, A + N);
+  std::cout << v.size() << std::endl;
+  std::cout << v.capacity() << std::endl;
+  std::cout << v.max_size() << std::endl;
+
+  iterator_type it1 = v.erase(v.begin() + 1);
+  VERIFY( it1 == v.begin() + 1 );
+  std::cout << N << std::endl << v.size() << std::endl;
+  VERIFY( v.size() == N1 );
+  VERIFY( std::equal(v.begin(), v.end(), A1) );
+  
+  iterator_type it2 = v.erase(v.begin() + 4, v.begin() + 9);
+  VERIFY( it2 == v.begin() + 4 );
+  VERIFY( v.size() == N2 );
+  VERIFY( std::equal(v.begin(), v.end(), A2) );
+  
+  iterator_type it3 = v.erase(v.begin() + 6, v.end());
+  VERIFY( it3 == v.begin() + 6 );
+  VERIFY( v.size() == N3 );
+  VERIFY( std::equal(v.begin(), v.end(), A3) );
+
+  iterator_type it4 = v.erase(v.begin(), v.begin() + 3);
+  VERIFY( it4 == v.begin() );
+  VERIFY( v.size() == N4 );
+  VERIFY( std::equal(v.begin(), v.end(), A4) );
+
+  iterator_type it5 = v.erase(v.begin() + 2);
+  VERIFY( it5 == v.begin() + 2 );
+  VERIFY( v.size() == N5 );
+  VERIFY( std::equal(v.begin(), v.end(), A5) );
+
+  iterator_type it6 = v.erase(v.begin(), v.end());
+  VERIFY( it6 == v.begin() );
+  VERIFY( v.empty() );
+}
+
+void
+test02()
+{
+  bool test __attribute__((unused)) = true;
+
+  typedef __gnu_cxx::_ExtPtr_allocator<int> int_alloc_type;
+  typedef __gnu_cxx::_ExtPtr_allocator< std::vector<int, int_alloc_type> > vec_alloc_type;
+  typedef std::vector<std::vector<int, int_alloc_type >,vec_alloc_type>  vec_type; 
+  typedef vec_type::iterator          iterator_type;
+
+  vec_type v, v1, v2, v3, v4, v5;
+  for (unsigned int i = 0; i < N; ++i)
+    v.push_back(std::vector<int,int_alloc_type>(1, A[i]));
+  for (unsigned int i = 0; i < N1; ++i)
+    v1.push_back(std::vector<int,int_alloc_type>(1, A1[i]));
+  for (unsigned int i = 0; i < N2; ++i)
+    v2.push_back(std::vector<int,int_alloc_type>(1, A2[i]));
+  for (unsigned int i = 0; i < N3; ++i)
+    v3.push_back(std::vector<int,int_alloc_type>(1, A3[i]));
+  for (unsigned int i = 0; i < N4; ++i)
+    v4.push_back(std::vector<int,int_alloc_type>(1, A4[i]));
+  for (unsigned int i = 0; i < N5; ++i)
+    v5.push_back(std::vector<int,int_alloc_type>(1, A5[i]));
+  
+  iterator_type it1 = v.erase(v.begin() + 1);
+  VERIFY( it1 == v.begin() + 1 );
+  VERIFY( v.size() == N1 );
+  VERIFY( std::equal(v.begin(), v.end(), v1.begin()) );
+  
+  iterator_type it2 = v.erase(v.begin() + 4, v.begin() + 9);
+  VERIFY( it2 == v.begin() + 4 );
+  VERIFY( v.size() == N2 );
+  VERIFY( std::equal(v.begin(), v.end(), v2.begin()) );
+  
+  iterator_type it3 = v.erase(v.begin() + 6, v.end());
+  VERIFY( it3 == v.begin() + 6 );
+  VERIFY( v.size() == N3 );
+  VERIFY( std::equal(v.begin(), v.end(), v3.begin()) );
+
+  iterator_type it4 = v.erase(v.begin(), v.begin() + 3);
+  VERIFY( it4 == v.begin() );
+  VERIFY( v.size() == N4 );
+  VERIFY( std::equal(v.begin(), v.end(), v4.begin()) );
+
+  iterator_type it5 = v.erase(v.begin() + 2);
+  VERIFY( it5 == v.begin() + 2 );
+  VERIFY( v.size() == N5 );
+  VERIFY( std::equal(v.begin(), v.end(), v5.begin()) );
+
+  iterator_type it6 = v.erase(v.begin(), v.end());
+  VERIFY( it6 == v.begin() );
+  VERIFY( v.empty() );
+}
+
+int main()
+{
+  test01();
+  test02();
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/insert.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/insert.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/insert.cc	(revision 0)
@@ -0,0 +1,76 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+#include <stdexcept>
+
+void test01() 
+{ 
+  bool test __attribute__((unused)) = true;
+
+  __gnu_cxx::_ExtPtr_allocator<int> alloc;
+  std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> > iv(alloc);
+  VERIFY( iv.get_allocator() == alloc );
+  VERIFY( iv.size() == 0 );
+  
+  int A[] = { 0, 1, 2, 3, 4 };
+  int B[] = { 5, 5, 5, 5, 5 };
+  int C[] = { 6, 7 };
+  iv.insert(iv.end(), A, A+5 );
+  VERIFY( iv.size() == 5 );
+  iv.insert(iv.begin(), 5, 5 );
+  iv.insert(iv.begin()+5, 7);
+  iv.insert(iv.begin()+5, 6);
+  VERIFY( std::equal(iv.begin(), iv.begin()+5, B ));
+  VERIFY( std::equal(iv.begin()+5, iv.begin()+7, C));
+  VERIFY( std::equal(iv.begin()+7, iv.end(), A));
+  VERIFY( iv.size() == 12 );
+
+  try
+    {
+      iv.insert(iv.end(), iv.max_size() + 1, 1);
+    }
+  catch(std::length_error&)
+    {
+      VERIFY( true );
+    }
+  catch(...)
+    {
+      VERIFY( false );
+    }
+}
+
+int main()
+{
+  test01();
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/element.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/element.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/modifiers/element.cc	(revision 0)
@@ -0,0 +1,86 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+
+// General tests element access and manipulation
+void test01() 
+{
+  bool test __attribute__((unused)) = true;
+
+  int A[] = { 0, 1, 2, 3, 4 };
+  __gnu_cxx::_ExtPtr_allocator<int> alloc;
+  std::vector<int,__gnu_cxx::_ExtPtr_allocator<int> > mv( A, A+5, alloc );
+
+  VERIFY( mv.size() == 5 );
+  VERIFY( mv.front() == 0 );
+  VERIFY( mv.back() == 4 );
+  VERIFY( mv.at(2) == 2 );
+  VERIFY( mv[3] == 3);
+  mv.front() = 5;
+  mv.back() = 6;
+  mv.at(2) = 7;
+  mv[3] = 8;
+  VERIFY( mv.size() == 5 );
+  VERIFY( mv.front() == 5 );
+  VERIFY( mv.back() == 6 );
+  VERIFY( mv.at(2) == 7 );
+  VERIFY( mv[3] == 8 );
+
+  try 
+    {
+  	mv.at(100) = 8;
+    }
+  catch(std::out_of_range&)
+    {
+      VERIFY( true );
+    }
+  catch(...)
+    {
+      VERIFY( false );
+    }
+  
+  const std::vector<int,__gnu_cxx::_ExtPtr_allocator<int> > cmv( mv );
+  VERIFY( cmv.get_allocator() == mv.get_allocator() );
+  VERIFY( mv.size() == 5 );
+  VERIFY( mv.front() == 5 );
+  VERIFY( mv.back() == 6 );
+  VERIFY( mv.at(2) == 7 );
+  VERIFY( mv[3] == 8 );	
+}
+
+
+int main()
+{
+  test01();
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/citerators.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/citerators.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/citerators.cc	(revision 0)
@@ -0,0 +1,55 @@
+// { dg-options "-std=gnu++0x" }
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+
+// Ensures equivalence of iterators based on low-level comparison
+// between const / non-const Pointer types.
+void
+test01()
+{
+  bool test __attribute__((unused)) = true;
+
+  std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> > v(7);
+  VERIFY( v.cbegin() == v.begin() );
+  VERIFY( v.cend() == v.end() );
+  VERIFY( v.crbegin() == v.rbegin() );
+  VERIFY( v.crend() == v.rend() );
+  VERIFY( v.cbegin() != v.cend() );
+  VERIFY( v.crbegin() != v.crend() );  
+}
+
+int main()
+{
+  test01();
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/types/1.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/types/1.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/types/1.cc	(revision 0)
@@ -0,0 +1,70 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+// This is a copy of vector/types/1.cc with altered allocator.
+// The operator+()s in this test initially failed the test -
+// they stress the accurate recognition, by the compiler,
+// of _Pointer_adapter's own pointer arithmetic functions,
+// which have to match perfectly on the int type to get
+// chosen by the compiler when it sees: _Pointer_adapter<T> + int, etc.
+
+#include <vector>
+#include <ext/extptr_allocator.h>
+
+namespace N
+{
+  struct X { };
+
+  template<typename T>
+    X operator+(T, std::size_t)
+    { return X(); }
+
+  template<typename T>
+    X operator-(T, T)
+    { return X(); }
+}
+
+int main()
+{
+  std::vector<N::X, __gnu_cxx::_ExtPtr_allocator<N::X> > v(5);
+  const std::vector<N::X, __gnu_cxx::_ExtPtr_allocator<N::X> > w(1);
+
+  v[0];
+  w[0];
+  v.size();
+  v.capacity();
+  v.resize(1);
+  v.insert(v.begin(), N::X());
+  v.insert(v.begin(), 1, N::X());
+  v.insert(v.begin(), w.begin(), w.end());
+  v = w;
+
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/1.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/1.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/1.cc	(revision 0)
@@ -0,0 +1,36 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <ext/extptr_allocator.h>
+
+// { dg-do compile }
+
+template class std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> >;
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/3.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/3.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/explicit_instantiation/3.cc	(revision 0)
@@ -0,0 +1,37 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <ext/extptr_allocator.h>
+
+// { dg-do compile }
+
+// libstdc++/21770
+template class std::vector<int, __gnu_cxx::_ExtPtr_allocator<char> >;
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/resize.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/resize.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/resize.cc	(revision 0)
@@ -0,0 +1,74 @@
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <stdexcept>
+#include <testsuite_allocator.h>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+
+
+void test01()
+{
+  // non POD types
+  bool test __attribute__((unused)) = true;
+  
+  std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> > vec01;
+  typedef std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> >::size_type size_type;
+
+  VERIFY(vec01.empty());
+
+  const int A[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };    
+
+  // Test resize of the vector based on reserve
+  size_type sz01 = vec01.capacity();
+  vec01.reserve(100);
+  size_type sz02 = vec01.capacity();
+  VERIFY(sz02 >= sz01);
+
+  // grow/shrink
+  vec01.assign( A, A+10 );
+  sz01 = vec01.size() + 100;
+  vec01.resize(sz01);
+  sz02 = vec01.size();
+  VERIFY(sz01 == sz02);
+  VERIFY(std::equal(vec01.begin(), vec01.begin()+10, A));
+  
+  sz01 = vec01.size() - 100;
+  vec01.resize(sz01);
+  sz02 = vec01.size();
+  VERIFY(sz01 == sz02);
+  VERIFY(std::equal(vec01.begin(), vec01.end(), A));
+}
+
+int main()
+{
+  test01();
+  return 0;
+}
Index: libstdc++-v3/testsuite/23_containers/vector/ext_pointer/data_access.cc
===================================================================
--- libstdc++-v3/testsuite/23_containers/vector/ext_pointer/data_access.cc	(revision 0)
+++ libstdc++-v3/testsuite/23_containers/vector/ext_pointer/data_access.cc	(revision 0)
@@ -0,0 +1,62 @@
+// Test for Container using non-standard pointer types.
+
+// Copyright (C) 2008
+// Free Software Foundation, Inc.
+//
+// This file is part of the GNU ISO C++ Library.  This library is free
+// software; you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 2, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING.  If not, write to the Free
+// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
+// USA.
+
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
+
+#include <vector>
+#include <testsuite_hooks.h>
+#include <ext/extptr_allocator.h>
+
+// libstdc++/23578
+void test01() 
+{ 
+  bool test __attribute__((unused)) = true;
+  typedef std::vector<int, __gnu_cxx::_ExtPtr_allocator<int> > vector_type;
+
+  {
+    const int A[] = { 0, 1, 2, 3, 4 };    
+    vector_type v(A, A + 5);
+    VERIFY( v.data() == &v.front() );
+    int* pi = &* v.data();
+    VERIFY( *pi == 0 );
+  }
+
+  {
+    const int A[] = { 4, 3, 2, 1, 0 };    
+    const vector_type cv(A, A + 5);
+    VERIFY( cv.data() == &cv.front() );
+    const int* pci = &* cv.data();
+    VERIFY( *pci == 4 );
+  }
+}
+
+int main()
+{
+  test01();
+  return 0;
+}
