2017-06-02 Jonathan Wakely <jwakely@redhat.com>
+ PR libstdc++/80624
+ * doc/xml/manual/status_cxx2011.xml: Document to_int_type behaviour.
+ * include/bits/char_traits.h (char_traits<char16_t>::to_int_type):
+ Transform eof value to U+FFFD.
+ * testsuite/21_strings/char_traits/requirements/char16_t/eof.cc: New.
+ * testsuite/27_io/basic_streambuf/sgetc/char16_t/80624.cc: New.
+ * testsuite/27_io/basic_streambuf/sputc/char16_t/80624.cc: New.
+
* libsupc++/Makefile.am: Remove custom targets for files that need to
be compiled as C++11 or C++14.
* libsupc++/Makefile.in: Regenerate.
<classname>u32streampos</classname> are both synonyms for
<classname>fpos<mbstate_t></classname>.
The function <function>eof</function> returns <code>int_type(-1)</code>.
+ <function>char_traits<char16_t>::to_int_type</function> will
+ transform the "noncharacter" U+FFFF to U+FFFD (REPLACEMENT CHARACTER).
+ This is done to ensure that <function>to_int_type</function> never
+ returns the same value as <function>eof</function>, which is U+FFFF.
</para>
<para>
static constexpr int_type
to_int_type(const char_type& __c) noexcept
- { return int_type(__c); }
+ { return __c == eof() ? int_type(0xfffd) : int_type(__c); }
static constexpr bool
eq_int_type(const int_type& __c1, const int_type& __c2) noexcept
--- /dev/null
+// Copyright (C) 2017 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-do compile { target c++11 } }
+
+#include <string>
+
+
+constexpr bool not_equal_to_eof(char16_t c)
+{
+ using T = std::char_traits<char16_t>;
+ return T::eq_int_type(T::eof(), T::to_int_type(c)) == false;
+}
+
+// Last two code points of the BMP are noncharacters:
+static_assert(not_equal_to_eof(u'\uFFFE'), "U+FFFE compares unequal to eof");
+static_assert(not_equal_to_eof(u'\uFFFF'), "U+FFFF compares unequal to eof");
--- /dev/null
+// Copyright (C) 2017 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-do run { target c++11 } }
+
+#include <streambuf>
+#include <testsuite_hooks.h>
+
+struct streambuf : std::basic_streambuf<char16_t>
+{
+ basic_streambuf* setbuf(char_type* s, std::streamsize n) override
+ {
+ setp(s, s + n);
+ setg(s, s, s + n);
+ return this;
+ }
+};
+
+void
+test01()
+{
+ using traits = streambuf::traits_type;
+
+ char16_t buf[2] = { streambuf::char_type(-1), streambuf::char_type(-2) };
+ streambuf sb;
+ sb.pubsetbuf(buf, 2);
+
+ streambuf::int_type res;
+
+ res = sb.sbumpc();
+ VERIFY( traits::eq_int_type(res, traits::eof()) == false );
+ res = sb.sbumpc();
+ VERIFY( traits::eq_int_type(res, traits::eof()) == false );
+ res = sb.sbumpc();
+ VERIFY( traits::eq_int_type(res, traits::eof()) == true );
+}
+
+int
+main()
+{
+ test01();
+}
--- /dev/null
+// Copyright (C) 2017 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-do run { target c++11 } }
+
+#include <streambuf>
+#include <testsuite_hooks.h>
+
+struct streambuf : std::basic_streambuf<char16_t>
+{
+ basic_streambuf* setbuf(char_type* s, std::streamsize n) override
+ {
+ setp(s, s + n);
+ setg(s, s, s + n);
+ return this;
+ }
+};
+
+void
+test01()
+{
+ using traits = streambuf::traits_type;
+
+ char16_t buf[2] = { };
+ streambuf sb;
+ sb.pubsetbuf(buf, 2);
+
+ streambuf::int_type res;
+
+ res = sb.sputc(streambuf::char_type(-1));
+ VERIFY( traits::eq_int_type(res, traits::eof()) == false );
+ res = sb.sputc(streambuf::char_type(-2));
+ VERIFY( traits::eq_int_type(res, traits::eof()) == false );
+ res = sb.sputc(streambuf::char_type(1));
+ VERIFY( traits::eq_int_type(res, traits::eof()) == true );
+
+ VERIFY( buf[0] == streambuf::char_type(-1) );
+ VERIFY( buf[1] == streambuf::char_type(-2) );
+}
+
+int
+main()
+{
+ test01();
+}