2015-08-24 Jonathan Wakely <jwakely@redhat.com>
+ PR libstdc++/65049
+ * include/bits/char_traits.h (char_traits<char>::compare,
+ char_traits<char>::find, char_traits<char>::move,
+ char_traits<char>::copy, char_traits<char>::assign): Check for zero
+ length.
+ (char_traits<wchar_t>::compare, char_traits<wchar_t>::find,
+ char_traits<wchar_t>::move, char_traits<wchar_t>::copy,
+ char_traits<wchar_t>::assign): Likewise.
+ (char_traits<char16_t>::move, char_traits<char16_t>::copy): Likewise.
+ (char_traits<char32_t>::move, char_traits<char32_t>::copy): Likewise.
+ * include/ext/pod_char_traits.h (char_traits<character<>>::move,
+ char_traits<character<>>::copy): Likewise.
+ * testsuite/21_strings/char_traits/requirements/char/65049.cc: New.
+ * testsuite/21_strings/char_traits/requirements/char16_t/65049.cc:
+ New.
+ * testsuite/21_strings/char_traits/requirements/char32_t/65049.cc:
+ New.
+ * testsuite/21_strings/char_traits/requirements/wchar_t/65049.cc:
+ New.
+
PR libstdc++/67309
* include/bits/random.tcc
(poisson_distribution::param_type::_M_initialize): Use max<double>.
static int
compare(const char_type* __s1, const char_type* __s2, size_t __n)
- { return __builtin_memcmp(__s1, __s2, __n); }
+ {
+ if (__n == 0)
+ return 0;
+ return __builtin_memcmp(__s1, __s2, __n);
+ }
static size_t
length(const char_type* __s)
static const char_type*
find(const char_type* __s, size_t __n, const char_type& __a)
- { return static_cast<const char_type*>(__builtin_memchr(__s, __a, __n)); }
+ {
+ if (__n == 0)
+ return 0;
+ return static_cast<const char_type*>(__builtin_memchr(__s, __a, __n));
+ }
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
- { return static_cast<char_type*>(__builtin_memmove(__s1, __s2, __n)); }
+ {
+ if (__n == 0)
+ return __s1;
+ return static_cast<char_type*>(__builtin_memmove(__s1, __s2, __n));
+ }
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
- { return static_cast<char_type*>(__builtin_memcpy(__s1, __s2, __n)); }
+ {
+ if (__n == 0)
+ return __s1;
+ return static_cast<char_type*>(__builtin_memcpy(__s1, __s2, __n));
+ }
static char_type*
assign(char_type* __s, size_t __n, char_type __a)
- { return static_cast<char_type*>(__builtin_memset(__s, __a, __n)); }
+ {
+ if (__n == 0)
+ return __s;
+ return static_cast<char_type*>(__builtin_memset(__s, __a, __n));
+ }
static _GLIBCXX_CONSTEXPR char_type
to_char_type(const int_type& __c) _GLIBCXX_NOEXCEPT
static int
compare(const char_type* __s1, const char_type* __s2, size_t __n)
- { return wmemcmp(__s1, __s2, __n); }
+ {
+ if (__n == 0)
+ return 0;
+ return wmemcmp(__s1, __s2, __n);
+ }
static size_t
length(const char_type* __s)
static const char_type*
find(const char_type* __s, size_t __n, const char_type& __a)
- { return wmemchr(__s, __a, __n); }
+ {
+ if (__n == 0)
+ return 0;
+ return wmemchr(__s, __a, __n);
+ }
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
- { return wmemmove(__s1, __s2, __n); }
+ {
+ if (__n == 0)
+ return __s1;
+ return wmemmove(__s1, __s2, __n);
+ }
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
- { return wmemcpy(__s1, __s2, __n); }
+ {
+ if (__n == 0)
+ return __s1;
+ return wmemcpy(__s1, __s2, __n);
+ }
static char_type*
assign(char_type* __s, size_t __n, char_type __a)
- { return wmemset(__s, __a, __n); }
+ {
+ if (__n == 0)
+ return __s;
+ return wmemset(__s, __a, __n);
+ }
static _GLIBCXX_CONSTEXPR char_type
to_char_type(const int_type& __c) _GLIBCXX_NOEXCEPT
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
return (static_cast<char_type*>
(__builtin_memmove(__s1, __s2, __n * sizeof(char_type))));
}
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
return (static_cast<char_type*>
(__builtin_memcpy(__s1, __s2, __n * sizeof(char_type))));
}
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
return (static_cast<char_type*>
(__builtin_memmove(__s1, __s2, __n * sizeof(char_type))));
}
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
return (static_cast<char_type*>
(__builtin_memcpy(__s1, __s2, __n * sizeof(char_type))));
}
static char_type*
move(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
return static_cast<char_type*>
(__builtin_memmove(__s1, __s2, __n * sizeof(char_type)));
}
static char_type*
copy(char_type* __s1, const char_type* __s2, size_t __n)
{
+ if (__n == 0)
+ return __s1;
std::copy(__s2, __s2 + __n, __s1);
return __s1;
}
--- /dev/null
+// Copyright (C) 2015 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 3, 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 COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++11" }
+
+// libstdc++/65049
+
+#include <string>
+#include <testsuite_hooks.h>
+
+using C = char;
+
+void
+test01()
+{
+ const C* p = 0;
+ C* q = 0;
+ auto c = std::char_traits<C>::compare(p, q, 0);
+ VERIFY( c == 0 );
+ auto r = std::char_traits<C>::find(p, 0, '0');
+ VERIFY( r == nullptr );
+ r = std::char_traits<C>::move(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::copy(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::assign(q, 0, '0');
+ VERIFY( r == q );
+}
+
+int
+main()
+{
+ test01();
+}
--- /dev/null
+// Copyright (C) 2015 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 3, 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 COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++11" }
+
+// libstdc++/65049
+
+#include <string>
+#include <testsuite_hooks.h>
+
+using C = char16_t;
+
+void
+test01()
+{
+ const C* p = 0;
+ C* q = 0;
+ auto c = std::char_traits<C>::compare(p, q, 0);
+ VERIFY( c == 0 );
+ auto r = std::char_traits<C>::find(p, 0, '0');
+ VERIFY( r == nullptr );
+ r = std::char_traits<C>::move(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::copy(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::assign(q, 0, '0');
+ VERIFY( r == q );
+}
+
+int
+main()
+{
+ test01();
+}
--- /dev/null
+// Copyright (C) 2015 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 3, 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 COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++11" }
+
+// libstdc++/65049
+
+#include <string>
+#include <testsuite_hooks.h>
+
+using C = char32_t;
+
+void
+test01()
+{
+ const C* p = 0;
+ C* q = 0;
+ auto c = std::char_traits<C>::compare(p, q, 0);
+ VERIFY( c == 0 );
+ auto r = std::char_traits<C>::find(p, 0, '0');
+ VERIFY( r == nullptr );
+ r = std::char_traits<C>::move(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::copy(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::assign(q, 0, '0');
+ VERIFY( r == q );
+}
+
+int
+main()
+{
+ test01();
+}
--- /dev/null
+// Copyright (C) 2015 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 3, 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 COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+// { dg-options "-std=gnu++11" }
+
+// libstdc++/65049
+
+#include <string>
+#include <testsuite_hooks.h>
+
+using C = wchar_t;
+
+void
+test01()
+{
+ const C* p = 0;
+ C* q = 0;
+ auto c = std::char_traits<C>::compare(p, q, 0);
+ VERIFY( c == 0 );
+ auto r = std::char_traits<C>::find(p, 0, '0');
+ VERIFY( r == nullptr );
+ r = std::char_traits<C>::move(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::copy(q, p, 0);
+ VERIFY( r == q );
+ r = std::char_traits<C>::assign(q, 0, '0');
+ VERIFY( r == q );
+}
+
+int
+main()
+{
+ test01();
+}