OSDN Git Service

2007-12-26 Paolo Carlini <pcarlini@suse.de>
authorpaolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 26 Dec 2007 21:58:49 +0000 (21:58 +0000)
committerpaolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 26 Dec 2007 21:58:49 +0000 (21:58 +0000)
PR libstdc++/34595
* include/bits/stl_algobase.h (struct __cm_assign): Remove.
(struct __copy_move<true, false, _Category>,
struct __copy_move<true, false, random_access_iterator_tag>,
struct __copy_move_backward<true, false, _Category>,
struct __copy_move_backward<true, false, random_access_iterator_tag>):
Add.
(struct __copy_move, struct __copy_move_backward,
struct __copy_move<false, false, random_access_iterator_tag>,
struct __copy_move_backward<false, false, random_access_iterator_tag>):
Adjust.
* testsuite/25_algorithms/copy/34595.C: New.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@131188 138bc75d-0d04-0410-961f-82ee72b054a4

libstdc++-v3/ChangeLog
libstdc++-v3/include/bits/stl_algobase.h
libstdc++-v3/testsuite/25_algorithms/copy/34595.C [new file with mode: 0644]

index ae3ca7a..28a509e 100644 (file)
@@ -1,3 +1,18 @@
+2007-12-26  Paolo Carlini  <pcarlini@suse.de>
+
+       PR libstdc++/34595
+       * include/bits/stl_algobase.h (struct __cm_assign): Remove.
+       (struct __copy_move<true, false, _Category>,
+       struct __copy_move<true, false, random_access_iterator_tag>,
+       struct __copy_move_backward<true, false, _Category>,
+       struct __copy_move_backward<true, false, random_access_iterator_tag>):
+       Add.
+       (struct __copy_move, struct __copy_move_backward,
+       struct __copy_move<false, false, random_access_iterator_tag>,
+       struct __copy_move_backward<false, false, random_access_iterator_tag>):
+       Adjust.
+       * testsuite/25_algorithms/copy/34595.C: New.
+
 2007-12-26  Chris Fairles  <chris.fairles@gmail.com>
            Paolo Carlini  <pcarlini@suse.de>
 
index 52f2ca4..8f19453 100644 (file)
@@ -295,34 +295,13 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
       { return __it.base(); }
     };
 
-  // Used in __copy_move and __copy_move_backward below.
-  template<bool _IsMove>
-    struct __cm_assign
-    {
-      template<typename _IteratorL, typename _IteratorR>
-        static void
-        __a(_IteratorL __lhs, _IteratorR __rhs) 
-       { *__lhs = *__rhs; }
-    };
-
-#ifdef __GXX_EXPERIMENTAL_CXX0X__
-  template<>
-    struct __cm_assign<true>
-    {
-      template<typename _IteratorL, typename _IteratorR>
-        static void
-        __a(_IteratorL __lhs, _IteratorR __rhs) 
-       { *__lhs = std::move(*__rhs); }
-    };
-#endif
-
   // All of these auxiliary structs serve two purposes.  (1) Replace
   // calls to copy with memmove whenever possible.  (Memmove, not memcpy,
   // because the input and output ranges are permitted to overlap.)
   // (2) If we're using random access iterators, then write the loop as
   // a for loop with an explicit count.
 
-  template<bool _IsMove, bool, typename>
+  template<bool, bool, typename>
     struct __copy_move
     {
       template<typename _II, typename _OI>
@@ -330,13 +309,47 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
         __copy_m(_II __first, _II __last, _OI __result)
         {
          for (; __first != __last; ++__result, ++__first)
-           std::__cm_assign<_IsMove>::__a(__result, __first);
+           *__result = *__first;
+         return __result;
+       }
+    };
+
+#ifdef __GXX_EXPERIMENTAL_CXX0X__
+  template<typename _Category>
+    struct __copy_move<true, false, _Category>
+    {
+      template<typename _II, typename _OI>
+        static _OI
+        __copy_m(_II __first, _II __last, _OI __result)
+        {
+         for (; __first != __last; ++__result, ++__first)
+           *__result = std::move(*__first);
+         return __result;
+       }
+    };
+#endif
+
+  template<>
+    struct __copy_move<false, false, random_access_iterator_tag>
+    {
+      template<typename _II, typename _OI>
+        static _OI
+        __copy_m(_II __first, _II __last, _OI __result)
+        { 
+         typedef typename iterator_traits<_II>::difference_type _Distance;
+         for(_Distance __n = __last - __first; __n > 0; --__n)
+           {
+             *__result = *__first;
+             ++__first;
+             ++__result;
+           }
          return __result;
        }
     };
 
-  template<bool _IsMove, bool _IsSimple>
-    struct __copy_move<_IsMove, _IsSimple, random_access_iterator_tag>
+#ifdef __GXX_EXPERIMENTAL_CXX0X__
+  template<>
+    struct __copy_move<true, false, random_access_iterator_tag>
     {
       template<typename _II, typename _OI>
         static _OI
@@ -345,13 +358,14 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
          typedef typename iterator_traits<_II>::difference_type _Distance;
          for(_Distance __n = __last - __first; __n > 0; --__n)
            {
-             std::__cm_assign<_IsMove>::__a(__result, __first);
+             *__result = std::move(*__first);
              ++__first;
              ++__result;
            }
          return __result;
        }
     };
+#endif
 
   template<bool _IsMove>
     struct __copy_move<_IsMove, true, random_access_iterator_tag>
@@ -489,7 +503,7 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
 #define _GLIBCXX_MOVE3(_Tp, _Up, _Vp) std::copy(_Tp, _Up, _Vp)
 #endif
 
-  template<bool _IsMove, bool, typename>
+  template<bool, bool, typename>
     struct __copy_move_backward
     {
       template<typename _BI1, typename _BI2>
@@ -497,13 +511,28 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
         __copy_move_b(_BI1 __first, _BI1 __last, _BI2 __result)
         {
          while (__first != __last)
-           std::__cm_assign<_IsMove>::__a(--__result, --__last);
+           *--__result = *--__last;
          return __result;
        }
     };
 
-  template<bool _IsMove, bool _IsSimple>
-    struct __copy_move_backward<_IsMove, _IsSimple, random_access_iterator_tag>
+#ifdef __GXX_EXPERIMENTAL_CXX0X__
+  template<typename _Category>
+    struct __copy_move_backward<true, false, _Category>
+    {
+      template<typename _BI1, typename _BI2>
+        static _BI2
+        __copy_move_b(_BI1 __first, _BI1 __last, _BI2 __result)
+        {
+         while (__first != __last)
+           *--__result = std::move(*--__last);
+         return __result;
+       }
+    };
+#endif
+
+  template<>
+    struct __copy_move_backward<false, false, random_access_iterator_tag>
     {
       template<typename _BI1, typename _BI2>
         static _BI2
@@ -511,11 +540,27 @@ _GLIBCXX_BEGIN_NAMESPACE(std)
         {
          typename iterator_traits<_BI1>::difference_type __n;
          for (__n = __last - __first; __n > 0; --__n)
-           std::__cm_assign<_IsMove>::__a(--__result, --__last);
+           *--__result = *--__last;
          return __result;
        }
     };
 
+#ifdef __GXX_EXPERIMENTAL_CXX0X__
+  template<>
+    struct __copy_move_backward<true, false, random_access_iterator_tag>
+    {
+      template<typename _BI1, typename _BI2>
+        static _BI2
+        __copy_move_b(_BI1 __first, _BI1 __last, _BI2 __result)
+        {
+         typename iterator_traits<_BI1>::difference_type __n;
+         for (__n = __last - __first; __n > 0; --__n)
+           *--__result = std::move(*--__last);
+         return __result;
+       }
+    };
+#endif
+
   template<bool _IsMove>
     struct __copy_move_backward<_IsMove, true, random_access_iterator_tag>
     {
diff --git a/libstdc++-v3/testsuite/25_algorithms/copy/34595.C b/libstdc++-v3/testsuite/25_algorithms/copy/34595.C
new file mode 100644 (file)
index 0000000..85bef55
--- /dev/null
@@ -0,0 +1,55 @@
+// Copyright (C) 2007 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 Pred 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.
+
+// 25.2.1 [lib.alg.copy] Copy.
+
+#include <algorithm>
+#include <testsuite_hooks.h>
+
+class Counting_output_iterator
+: public std::iterator< std::output_iterator_tag, void, void, void, void >
+{
+  std::size_t c;
+public:
+  Counting_output_iterator() : c(0) {}
+  Counting_output_iterator& operator++() { return *this; }
+  Counting_output_iterator& operator*() { return *this; }
+  
+  template <typename T>
+  void operator=(const T&) { ++c; }
+  
+  std::size_t current_counter() const { return c; }
+};
+
+// libstdc++/34595
+void test01()
+{
+  bool test __attribute__((unused)) = true;
+  
+  int t[10] = {0,};
+  Counting_output_iterator cnt;
+  std::size_t res = std::copy(t+0, t+5, cnt).current_counter();
+
+  VERIFY( res == 5 );
+}
+
+int main()
+{
+  test01();
+  return 0;
+}