diff options
author | paolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4> | 2006-02-17 10:46:57 +0000 |
---|---|---|
committer | paolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4> | 2006-02-17 10:46:57 +0000 |
commit | e8f3af83e7e3ef43c437a7ed1edca1df67e186d4 (patch) | |
tree | 7d5556d4cc5632af4f60606bdc602c9e59bb2854 /libstdc++-v3 | |
parent | 8dbf774a27ebfe14b083c5b244cab23756eb2662 (diff) | |
download | gcc-e8f3af83e7e3ef43c437a7ed1edca1df67e186d4.tar.gz |
2006-02-17 Paolo Carlini <pcarlini@suse.de>
Howard Hinnant <hhinnant@apple.com>
PR libstdc++/26250
* include/bits/sstream.tcc (basic_stringbuf<>::overflow): Tweak
to leave epgtr() just past the new write position, as per the
relevant bits of 27.7.1.3/8 (not changed by DR 432).
* testsuite/27_io/basic_stringbuf/overflow/char/26250.cc: New.
* testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc: Same.
* docs/html/ext/howto.html: Add entries for DR 169 and DR 432.
* include/std/std_sstream.h (basic_stringbuf<>::_M_sync): Move out
of line...
* include/bits/sstream.tcc: ... here.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@111177 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'libstdc++-v3')
-rw-r--r-- | libstdc++-v3/ChangeLog | 16 | ||||
-rw-r--r-- | libstdc++-v3/docs/html/ext/howto.html | 13 | ||||
-rw-r--r-- | libstdc++-v3/include/bits/sstream.tcc | 54 | ||||
-rw-r--r-- | libstdc++-v3/include/std/std_sstream.h | 35 | ||||
-rw-r--r-- | libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/char/26250.cc | 58 | ||||
-rw-r--r-- | libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc | 58 |
6 files changed, 196 insertions, 38 deletions
diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index e001cbdd317..99af0811454 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,19 @@ +2006-02-17 Paolo Carlini <pcarlini@suse.de> + Howard Hinnant <hhinnant@apple.com> + + PR libstdc++/26250 + * include/bits/sstream.tcc (basic_stringbuf<>::overflow): Tweak + to leave epgtr() just past the new write position, as per the + relevant bits of 27.7.1.3/8 (not changed by DR 432). + * testsuite/27_io/basic_stringbuf/overflow/char/26250.cc: New. + * testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc: Same. + + * docs/html/ext/howto.html: Add entries for DR 169 and DR 432. + + * include/std/std_sstream.h (basic_stringbuf<>::_M_sync): Move out + of line... + * include/bits/sstream.tcc: ... here. + 2006-02-16 Joseph S. Myers <joseph@codesourcery.com> PR libstdc++/14939 diff --git a/libstdc++-v3/docs/html/ext/howto.html b/libstdc++-v3/docs/html/ext/howto.html index 6aaf994ae50..cf87f6c55fa 100644 --- a/libstdc++-v3/docs/html/ext/howto.html +++ b/libstdc++-v3/docs/html/ext/howto.html @@ -358,6 +358,12 @@ calculating an incorrect number of characters to write. </dd> + <dt><a href="lwg-defects.html#169">169</a>: + <em>Bad efficiency of overflow() mandated</em> + </dt> + <dd>Grow efficiently the internal array object. + </dd> + <dt><a href="lwg-defects.html#171">171</a>: <em>Strange seekpos() semantics due to joint position</em> </dt> @@ -536,6 +542,13 @@ <dd>Implement Option 3, as per N1599. </dd> + <dt><a href="lwg-defects.html#432">432</a>: + <em>432. stringbuf::overflow() makes only one write position + available</em> + </dt> + <dd>Implement the resolution, beyond DR 169. + </dd> + <dt><a href="lwg-defects.html#434">434</a>: <em>bitset::to_string() hard to use</em> </dt> diff --git a/libstdc++-v3/include/bits/sstream.tcc b/libstdc++-v3/include/bits/sstream.tcc index eb12ca45891..95d3d4699be 100644 --- a/libstdc++-v3/include/bits/sstream.tcc +++ b/libstdc++-v3/include/bits/sstream.tcc @@ -1,6 +1,6 @@ // String based streams -*- C++ -*- -// Copyright (C) 1997, 1998, 1999, 2001, 2002, 2003, 2004, 2005 +// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006 // Free Software Foundation, Inc. // // This file is part of the GNU ISO C++ Library. This library is free @@ -101,14 +101,18 @@ _GLIBCXX_BEGIN_NAMESPACE(std) // Try to append __c into output sequence in one of two ways. // Order these tests done in is unspecified by the standard. + const char_type __conv = traits_type::to_char_type(__c); if (!__testput) { - // NB: Start ostringstream buffers at 512 chars. This is an + // NB: Start ostringstream buffers at 512 chars. This is an // experimental value (pronounced "arbitrary" in some of the // hipper english-speaking countries), and can be changed to // suit particular needs. - // Then, in virtue of DR 169 (TC) we are allowed to grow more - // than one char. + // + // _GLIBCXX_RESOLVE_LIB_DEFECTS + // 169. Bad efficiency of overflow() mandated + // 432. stringbuf::overflow() makes only one write position + // available const __size_type __opt_len = std::max(__size_type(2 * __capacity), __size_type(512)); const __size_type __len = std::min(__opt_len, __max_size); @@ -116,11 +120,15 @@ _GLIBCXX_BEGIN_NAMESPACE(std) __tmp.reserve(__len); if (this->pbase()) __tmp.assign(this->pbase(), this->epptr() - this->pbase()); + __tmp.push_back(__conv); _M_string.swap(__tmp); _M_sync(const_cast<char_type*>(_M_string.data()), this->gptr() - this->eback(), this->pptr() - this->pbase()); } - return this->sputc(traits_type::to_char_type(__c)); + else + *this->pptr() = __conv; + this->pbump(1); + return __c; } template <class _CharT, class _Traits, class _Alloc> @@ -203,8 +211,8 @@ _GLIBCXX_BEGIN_NAMESPACE(std) _M_update_egptr(); const off_type __pos(__sp); - const bool __testpos = 0 <= __pos - && __pos <= this->egptr() - __beg; + const bool __testpos = (0 <= __pos + && __pos <= this->egptr() - __beg); if (__testpos) { if (__testin) @@ -217,6 +225,38 @@ _GLIBCXX_BEGIN_NAMESPACE(std) return __ret; } + // Assumes: contents of _M_string and internal buffer match exactly. + // __i == _M_in_cur - _M_in_beg + // __o == _M_out_cur - _M_out_beg + template <class _CharT, class _Traits, class _Alloc> + void + basic_stringbuf<_CharT, _Traits, _Alloc>:: + _M_sync(char_type* __base, __size_type __i, __size_type __o) + { + const bool __testin = _M_mode & ios_base::in; + const bool __testout = _M_mode & ios_base::out; + char_type* __end = __base + _M_string.size(); + + if (__testin) + this->setg(__base, __base + __i, __end); + if (__testout) + { + // If __base comes from setbuf we cannot trust capacity() + // to match the size of the buffer area: in general, after + // Step 1 in setbuf, _M_string.capacity() >= __n. + if (__base == _M_string.data()) + this->setp(__base, __base + _M_string.capacity()); + else + this->setp(__base, __end); + this->pbump(__o); + // egptr() always tracks the string end. When !__testin, + // for the correct functioning of the streambuf inlines + // the other get area pointers are identical. + if (!__testin) + this->setg(__end, __end, __end); + } + } + // Inhibit implicit instantiations for required instantiations, // which are defined via explicit instantiations elsewhere. // NB: This syntax is a GNU extension. diff --git a/libstdc++-v3/include/std/std_sstream.h b/libstdc++-v3/include/std/std_sstream.h index 162c2a6cc7d..712bf7ba3c7 100644 --- a/libstdc++-v3/include/std/std_sstream.h +++ b/libstdc++-v3/include/std/std_sstream.h @@ -1,6 +1,6 @@ // String based streams -*- C++ -*- -// Copyright (C) 1997, 1998, 1999, 2002, 2003, 2004, 2005 +// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006 // Free Software Foundation, Inc. // // This file is part of the GNU ISO C++ Library. This library is free @@ -228,37 +228,10 @@ _GLIBCXX_BEGIN_NAMESPACE(std) ios_base::openmode __mode = ios_base::in | ios_base::out); // Internal function for correctly updating the internal buffer - // for a particular _M_string, due to initialization or - // re-sizing of an existing _M_string. - // Assumes: contents of _M_string and internal buffer match exactly. - // __i == _M_in_cur - _M_in_beg - // __o == _M_out_cur - _M_out_beg + // for a particular _M_string, due to initialization or re-sizing + // of an existing _M_string. void - _M_sync(char_type* __base, __size_type __i, __size_type __o) - { - const bool __testin = _M_mode & ios_base::in; - const bool __testout = _M_mode & ios_base::out; - char_type* __end = __base + _M_string.size(); - - if (__testin) - this->setg(__base, __base + __i, __end); - if (__testout) - { - // If __base comes from setbuf we cannot trust capacity() - // to match the size of the buffer area: in general, after - // Step 1 above, _M_string.capacity() >= __n. - if (__base == _M_string.data()) - this->setp(__base, __base + _M_string.capacity()); - else - this->setp(__base, __end); - this->pbump(__o); - // egptr() always tracks the string end. When !__testin, - // for the correct functioning of the streambuf inlines - // the other get area pointers are identical. - if (!__testin) - this->setg(__end, __end, __end); - } - } + _M_sync(char_type* __base, __size_type __i, __size_type __o); // Internal function for correctly updating egptr() to the actual // string end. diff --git a/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/char/26250.cc b/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/char/26250.cc new file mode 100644 index 00000000000..bf7dcde7d03 --- /dev/null +++ b/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/char/26250.cc @@ -0,0 +1,58 @@ +// Copyright (C) 2006 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. + +// 27.8.1.4 Overridden virtual functions + +#include <sstream> +#include <testsuite_hooks.h> + +struct pubbuf +: std::stringbuf +{ + using std::stringbuf::eback; + using std::stringbuf::egptr; + using std::stringbuf::pbase; + using std::stringbuf::pptr; + using std::stringbuf::epptr; + using std::stringbuf::overflow; +}; + +// libstdc++/26250 +void test01() +{ + bool test __attribute__((unused)) = true; + + pubbuf buf; + + VERIFY( buf.overflow('x') == 'x' ); + VERIFY( buf.pptr() - buf.pbase() == 1 ); + + // not required but good for efficiency + // NB: we are implementing DR 169 and DR 432 + const int write_positions = buf.epptr() - buf.pbase(); + VERIFY( write_positions > 1 ); + + // 27.7.1.3, p8: + VERIFY( buf.egptr() - buf.eback() == 1 ); +} + +int main() +{ + test01(); + return 0; +} diff --git a/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc b/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc new file mode 100644 index 00000000000..c835ea95145 --- /dev/null +++ b/libstdc++-v3/testsuite/27_io/basic_stringbuf/overflow/wchar_t/26250.cc @@ -0,0 +1,58 @@ +// Copyright (C) 2006 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. + +// 27.8.1.4 Overridden virtual functions + +#include <sstream> +#include <testsuite_hooks.h> + +struct pubbuf +: std::wstringbuf +{ + using std::wstringbuf::eback; + using std::wstringbuf::egptr; + using std::wstringbuf::pbase; + using std::wstringbuf::pptr; + using std::wstringbuf::epptr; + using std::wstringbuf::overflow; +}; + +// libstdc++/26250 +void test01() +{ + bool test __attribute__((unused)) = true; + + pubbuf buf; + + VERIFY( buf.overflow(L'x') == L'x' ); + VERIFY( buf.pptr() - buf.pbase() == 1 ); + + // not required but good for efficiency + // NB: we are implementing DR 169 and DR 432 + const int write_positions = buf.epptr() - buf.pbase(); + VERIFY( write_positions > 1 ); + + // 27.7.1.3, p8: + VERIFY( buf.egptr() - buf.eback() == 1 ); +} + +int main() +{ + test01(); + return 0; +} |