This is the mail archive of the libstdc++@gcc.gnu.org mailing list for the libstdc++ project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Patch] ADL issues: vector


Hi again,

as expected, a longer patch, but nothing particularly interesting.
Forgot to mention together with the string bits that the new testcases
are fine also in debug mode (that's why I added consistently the
operator- also for _Safe_iterator). Tested x86-linux.

Time to start porting older and newer improvements to mainline...

Paolo.

////////////////
2005-12-01  Paolo Carlini  <pcarlini@suse.de>

	* include/bits/stl_vector.h (vector<>::size, resize, capacity,
	operator[]): Avoid troubles with ADL, user defined operators
	and __normal_iterator.
	(_M_erase_at_end): Fix to take a pointer.
	(clear): Adjust call.
	* include/bits/vector.tcc (vector<>::insert(iterator, const
	value_type&), erase(iterator, iterator), operator=(const
	vector<>&), _M_assign_aux(input_iterator_tag), _M_insert_aux,
	_M_fill_insert, _M_range_insert): Likewise.
	(_M_fill_assign, _M_assign_aux(forward_iterator_tag)): Adjust
	_M_erase_at_end call.
	* testsuite/23_containers/vector/types/1.cc: New.

	
Index: include/bits/stl_vector.h
===================================================================
--- include/bits/stl_vector.h	(revision 107718)
+++ include/bits/stl_vector.h	(working copy)
@@ -363,7 +363,7 @@
        */
       iterator
       begin()
-      { return iterator (this->_M_impl._M_start); }
+      { return iterator(this->_M_impl._M_start); }
 
       /**
        *  Returns a read-only (constant) iterator that points to the
@@ -372,7 +372,7 @@
        */
       const_iterator
       begin() const
-      { return const_iterator (this->_M_impl._M_start); }
+      { return const_iterator(this->_M_impl._M_start); }
 
       /**
        *  Returns a read/write iterator that points one past the last
@@ -381,7 +381,7 @@
        */
       iterator
       end()
-      { return iterator (this->_M_impl._M_finish); }
+      { return iterator(this->_M_impl._M_finish); }
 
       /**
        *  Returns a read-only (constant) iterator that points one past
@@ -390,7 +390,7 @@
        */
       const_iterator
       end() const
-      { return const_iterator (this->_M_impl._M_finish); }
+      { return const_iterator(this->_M_impl._M_finish); }
 
       /**
        *  Returns a read/write reverse iterator that points to the
@@ -432,7 +432,7 @@
       /**  Returns the number of elements in the %vector.  */
       size_type
       size() const
-      { return size_type(end() - begin()); }
+      { return size_type(this->_M_impl._M_finish - this->_M_impl._M_start); }
 
       /**  Returns the size() of the largest possible %vector.  */
       size_type
@@ -454,7 +454,7 @@
       resize(size_type __new_size, value_type __x = value_type())
       {
 	if (__new_size < size())
-	  _M_erase_at_end(begin() + __new_size);
+	  _M_erase_at_end(this->_M_impl._M_start + __new_size);
 	else
 	  insert(end(), __new_size - size(), __x);
       }
@@ -465,8 +465,8 @@
        */
       size_type
       capacity() const
-      { return size_type(const_iterator(this->_M_impl._M_end_of_storage)
-			 - begin()); }
+      { return size_type(this->_M_impl._M_end_of_storage
+			 - this->_M_impl._M_start); }
 
       /**
        *  Returns true if the %vector is empty.  (Thus begin() would
@@ -510,7 +510,7 @@
        */
       reference
       operator[](size_type __n)
-      { return *(begin() + __n); }
+      { return *(this->_M_impl._M_start + __n); }
 
       /**
        *  @brief  Subscript access to the data contained in the %vector.
@@ -525,7 +525,7 @@
        */
       const_reference
       operator[](size_type __n) const
-      { return *(begin() + __n); }
+      { return *(this->_M_impl._M_start + __n); }
 
     protected:
       /// @if maint Safety check used only from at().  @endif
@@ -803,7 +803,7 @@
        */
       void
       clear()
-      { _M_erase_at_end(begin()); }
+      { _M_erase_at_end(this->_M_impl._M_start); }
 
     protected:
       /**
@@ -999,11 +999,10 @@
       // Called by erase(q1,q2), clear(), resize(), _M_fill_assign,
       // _M_assign_aux.
       void
-      _M_erase_at_end(iterator __pos)
+      _M_erase_at_end(pointer __pos)
       {
-	std::_Destroy(__pos.base(), this->_M_impl._M_finish,
-		      _M_get_Tp_allocator());
-	this->_M_impl._M_finish = __pos.base();
+	std::_Destroy(__pos, this->_M_impl._M_finish, _M_get_Tp_allocator());
+	this->_M_impl._M_finish = __pos;
       }
     };
 
Index: include/bits/vector.tcc
===================================================================
--- include/bits/vector.tcc	(revision 106945)
+++ include/bits/vector.tcc	(working copy)
@@ -73,8 +73,7 @@
       if (this->capacity() < __n)
 	{
 	  const size_type __old_size = size();
-	  pointer __tmp = _M_allocate_and_move(__n,
-					       this->_M_impl._M_start,
+	  pointer __tmp = _M_allocate_and_move(__n, this->_M_impl._M_start,
 					       this->_M_impl._M_finish);
 	  std::_Destroy(this->_M_impl._M_start, this->_M_impl._M_finish,
 			_M_get_Tp_allocator());
@@ -101,7 +100,7 @@
 	}
       else
         _M_insert_aux(__position, __x);
-      return begin() + __n;
+      return iterator(this->_M_impl._M_start + __n);
     }
 
   template<typename _Tp, typename _Alloc>
@@ -123,7 +122,7 @@
     {
       if (__last != end())
 	std::__move(__last, end(), __first);
-      _M_erase_at_end(__first + (end() - __last));
+      _M_erase_at_end(__first.base() + (end() - __last));
       return __first;
     }
 
@@ -149,15 +148,16 @@
 	    }
 	  else if (size() >= __xlen)
 	    {
-	      iterator __i(std::copy(__x.begin(), __x.end(), begin()));
-	      std::_Destroy(__i, end(), _M_get_Tp_allocator());
+	      std::_Destroy(std::copy(__x.begin(), __x.end(), begin()),
+			    end(), _M_get_Tp_allocator());
 	    }
 	  else
 	    {
-	      std::copy(__x.begin(), __x.begin() + size(),
+	      std::copy(__x._M_impl._M_start, __x._M_impl._M_start + size(),
 			this->_M_impl._M_start);
-	      std::__uninitialized_copy_a(__x.begin() + size(),
-					  __x.end(), this->_M_impl._M_finish,
+	      std::__uninitialized_copy_a(__x._M_impl._M_start + size(),
+					  __x._M_impl._M_finish,
+					  this->_M_impl._M_finish,
 					  _M_get_Tp_allocator());
 	    }
 	  this->_M_impl._M_finish = this->_M_impl._M_start + __xlen;
@@ -184,7 +184,7 @@
 	  this->_M_impl._M_finish += __n - size();
 	}
       else
-        _M_erase_at_end(std::fill_n(begin(), __n, __val));
+        _M_erase_at_end(std::fill_n(this->_M_impl._M_start, __n, __val));
     }
 
   template<typename _Tp, typename _Alloc>
@@ -194,8 +194,9 @@
       _M_assign_aux(_InputIterator __first, _InputIterator __last,
 		    std::input_iterator_tag)
       {
-	iterator __cur(begin());
-	for (; __first != __last && __cur != end(); ++__cur, ++__first)
+	pointer __cur(this->_M_impl._M_start);
+	for (; __first != __last && __cur != this->_M_impl._M_finish;
+	     ++__cur, ++__first)
 	  *__cur = *__first;
 	if (__first == __last)
 	  _M_erase_at_end(__cur);
@@ -225,11 +226,7 @@
 	    this->_M_impl._M_end_of_storage = this->_M_impl._M_finish;
 	  }
 	else if (size() >= __len)
-	  {
-	    iterator __new_finish(std::copy(__first, __last,
-					    this->_M_impl._M_start));
-	    _M_erase_at_end(__new_finish);
-	  }
+	  _M_erase_at_end(std::copy(__first, __last, this->_M_impl._M_start));
 	else
 	  {
 	    _ForwardIterator __mid = __first;
@@ -256,9 +253,9 @@
 						  - 1)),
 			      _M_get_Tp_allocator());
 	    ++this->_M_impl._M_finish;
-	    std::__move_backward(__position,
-				 iterator(this->_M_impl._M_finish-2),
-				 iterator(this->_M_impl._M_finish-1));
+	    std::__move_backward(__position.base(),
+				 this->_M_impl._M_finish - 2,
+				 this->_M_impl._M_finish - 1);
 	    *__position = __gnu_cxx::__move(__x_copy);
 	  }
 	else
@@ -274,36 +271,37 @@
 	    if (__len < __old_size)
 	      __len = this->max_size();
 	    
-	    iterator __new_start(this->_M_allocate(__len));
-	    iterator __new_finish(__new_start);
+	    pointer __new_start(this->_M_allocate(__len));
+	    pointer __new_finish(__new_start);
 	    try
 	      {
 		__new_finish =
-		  std::__uninitialized_move_a(iterator(this->_M_impl._M_start),
-					      __position, __new_start,
+		  std::__uninitialized_move_a(this->_M_impl._M_start,
+					      __position.base(), __new_start,
 					      _M_get_Tp_allocator());
-		_Construct_a(__new_finish.base(), __gnu_cxx::__move(__x_copy),
+		_Construct_a(__new_finish, __gnu_cxx::__move(__x_copy),
 			     _M_get_Tp_allocator());
 		++__new_finish;
 		__new_finish =
-		  std::__uninitialized_move_a(__position,
-					      iterator(this->_M_impl._M_finish),
+		  std::__uninitialized_move_a(__position.base(),
+					      this->_M_impl._M_finish,
 					      __new_finish,
 					      _M_get_Tp_allocator());
 	      }
 	    catch(...)
 	      {
 		std::_Destroy(__new_start, __new_finish, _M_get_Tp_allocator());
-		_M_deallocate(__new_start.base(),__len);
+		_M_deallocate(__new_start, __len);
 		__throw_exception_again;
 	      }
-	    std::_Destroy(begin(), end(), _M_get_Tp_allocator());
+	    std::_Destroy(this->_M_impl._M_start, this->_M_impl._M_finish,
+			  _M_get_Tp_allocator());
 	    _M_deallocate(this->_M_impl._M_start,
 			  this->_M_impl._M_end_of_storage
 			  - this->_M_impl._M_start);
-	    this->_M_impl._M_start = __new_start.base();
-	    this->_M_impl._M_finish = __new_finish.base();
-	    this->_M_impl._M_end_of_storage = __new_start.base() + __len;
+	    this->_M_impl._M_start = __new_start;
+	    this->_M_impl._M_finish = __new_finish;
+	    this->_M_impl._M_end_of_storage = __new_start + __len;
 	  }
       }
 
@@ -319,7 +317,7 @@
 	    {
 	      value_type __x_copy = __x;
 	      const size_type __elems_after = end() - __position;
-	      iterator __old_finish(this->_M_impl._M_finish);
+	      pointer __old_finish(this->_M_impl._M_finish);
 	      if (__elems_after > __n)
 		{
 		  std::__uninitialized_move_a(this->_M_impl._M_finish - __n,
@@ -327,9 +325,10 @@
 					      this->_M_impl._M_finish,
 					      _M_get_Tp_allocator());
 		  this->_M_impl._M_finish += __n;
-		  std::__move_backward(__position, __old_finish - __n,
-				     __old_finish);
-		  std::fill(__position, __position + __n, __x_copy);
+		  std::__move_backward(__position.base(), __old_finish - __n,
+				       __old_finish);
+		  std::fill(__position.base(), __position.base() + __n,
+			    __x_copy);
 		}
 	      else
 		{
@@ -338,11 +337,11 @@
 						__x_copy,
 						_M_get_Tp_allocator());
 		  this->_M_impl._M_finish += __n - __elems_after;
-		  std::__uninitialized_move_a(__position, __old_finish,
+		  std::__uninitialized_move_a(__position.base(), __old_finish,
 					      this->_M_impl._M_finish,
 					      _M_get_Tp_allocator());
 		  this->_M_impl._M_finish += __elems_after;
-		  std::fill(__position, __old_finish, __x_copy);
+		  std::fill(__position.base(), __old_finish, __x_copy);
 		}
 	    }
 	  else
@@ -357,26 +356,29 @@
 	      if (__len < __old_size)
 		__len = this->max_size();
 
-	      iterator __new_start(this->_M_allocate(__len));
-	      iterator __new_finish(__new_start);
+	      pointer __new_start(this->_M_allocate(__len));
+	      pointer __new_finish(__new_start);
 	      try
 		{
 		  __new_finish =
-		    std::__uninitialized_move_a(begin(), __position,
+		    std::__uninitialized_move_a(this->_M_impl._M_start,
+						__position.base(),
 						__new_start,
 						_M_get_Tp_allocator());
 		  std::__uninitialized_fill_n_a(__new_finish, __n, __x_copy,
 						_M_get_Tp_allocator());
 		  __new_finish += __n;
 		  __new_finish =
-		    std::__uninitialized_move_a(__position, end(), __new_finish,
+		    std::__uninitialized_move_a(__position.base(),
+						this->_M_impl._M_finish,
+						__new_finish,
 						_M_get_Tp_allocator());
 		}
 	      catch(...)
 		{
 		  std::_Destroy(__new_start, __new_finish,
 				_M_get_Tp_allocator());
-		  _M_deallocate(__new_start.base(), __len);
+		  _M_deallocate(__new_start, __len);
 		  __throw_exception_again;
 		}
 	      std::_Destroy(this->_M_impl._M_start, this->_M_impl._M_finish,
@@ -384,9 +386,9 @@
 	      _M_deallocate(this->_M_impl._M_start,
 			    this->_M_impl._M_end_of_storage
 			    - this->_M_impl._M_start);
-	      this->_M_impl._M_start = __new_start.base();
-	      this->_M_impl._M_finish = __new_finish.base();
-	      this->_M_impl._M_end_of_storage = __new_start.base() + __len;
+	      this->_M_impl._M_start = __new_start;
+	      this->_M_impl._M_finish = __new_finish;
+	      this->_M_impl._M_end_of_storage = __new_start + __len;
 	    }
 	}
     }
@@ -418,7 +420,7 @@
 			  - this->_M_impl._M_finish) >= __n)
 	      {
 		const size_type __elems_after = end() - __position;
-		iterator __old_finish(this->_M_impl._M_finish);
+		pointer __old_finish(this->_M_impl._M_finish);
 		if (__elems_after > __n)
 		  {
 		    std::__uninitialized_move_a(this->_M_impl._M_finish - __n,
@@ -426,7 +428,7 @@
 						this->_M_impl._M_finish,
 						_M_get_Tp_allocator());
 		    this->_M_impl._M_finish += __n;
-		    std::__move_backward(__position, __old_finish - __n,
+		    std::__move_backward(__position.base(), __old_finish - __n,
 					 __old_finish);
 		    std::copy(__first, __last, __position);
 		  }
@@ -438,7 +440,8 @@
 						this->_M_impl._M_finish,
 						_M_get_Tp_allocator());
 		    this->_M_impl._M_finish += __n - __elems_after;
-		    std::__uninitialized_move_a(__position, __old_finish,
+		    std::__uninitialized_move_a(__position.base(),
+						__old_finish,
 						this->_M_impl._M_finish,
 						_M_get_Tp_allocator());
 		    this->_M_impl._M_finish += __elems_after;
@@ -456,30 +459,29 @@
 		if (__len < __old_size)
 		  __len = this->max_size();
 
-		iterator __new_start(this->_M_allocate(__len));
-		iterator __new_finish(__new_start);
+		pointer __new_start(this->_M_allocate(__len));
+		pointer __new_finish(__new_start);
 		try
 		  {
 		    __new_finish =
-		      std::__uninitialized_move_a(iterator(this->
-							   _M_impl._M_start),
-						  __position, __new_start,
+		      std::__uninitialized_move_a(this->_M_impl._M_start,
+						  __position.base(),
+						  __new_start,
 						  _M_get_Tp_allocator());
 		    __new_finish =
 		      std::__uninitialized_copy_a(__first, __last, __new_finish,
 						  _M_get_Tp_allocator());
 		    __new_finish =
-		      std::__uninitialized_move_a(__position,
-						  iterator(this->
-							   _M_impl._M_finish),
+		      std::__uninitialized_move_a(__position.base(), 
+						  this->_M_impl._M_finish,
 						  __new_finish,
 						  _M_get_Tp_allocator());
 		  }
 		catch(...)
 		  {
-		    std::_Destroy(__new_start,__new_finish,
+		    std::_Destroy(__new_start, __new_finish,
 				  _M_get_Tp_allocator());
-		    _M_deallocate(__new_start.base(), __len);
+		    _M_deallocate(__new_start, __len);
 		    __throw_exception_again;
 		  }
 		std::_Destroy(this->_M_impl._M_start, this->_M_impl._M_finish,
@@ -487,9 +489,9 @@
 		_M_deallocate(this->_M_impl._M_start,
 			      this->_M_impl._M_end_of_storage
 			      - this->_M_impl._M_start);
-		this->_M_impl._M_start = __new_start.base();
-		this->_M_impl._M_finish = __new_finish.base();
-		this->_M_impl._M_end_of_storage = __new_start.base() + __len;
+		this->_M_impl._M_start = __new_start;
+		this->_M_impl._M_finish = __new_finish;
+		this->_M_impl._M_end_of_storage = __new_start + __len;
 	      }
 	  }
       }
Index: testsuite/23_containers/vector/types/1.cc
===================================================================
--- testsuite/23_containers/vector/types/1.cc	(revision 0)
+++ testsuite/23_containers/vector/types/1.cc	(revision 0)
@@ -0,0 +1,54 @@
+// 2005-12-01  Paolo Carlini  <pcarlini@suse.de>
+
+// Copyright (C) 2005 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.
+
+// { dg-do compile }
+
+#include <vector>
+
+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> v(5);
+  const std::vector<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 Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]