Commit 3a9ebf3c by Benjamin Kosnik Committed by Benjamin Kosnik

ostream_inserter_char.cc (test07): New.


2002-01-24  Benjamin Kosnik  <bkoz@redhat.com>

	* testsuite/27_io/ostream_inserter_char.cc (test07): New.

2002-01-24  Benjamin Kosnik  <bkoz@redhat.com>

	* include/bits/basic_ios.h (basic_ios::_M_check_facet): Make
	const, tweak.
	(basic_ios::fill(char_type)): Use fill().
	* include/bits/basic_ios.tcc (basic_ios::widen): Use _M_check_facet.
	(basic_ios::narrow): Same.
	(basic_ios::_M_cache_facets): Explicitly set cached facets to zero
	if they are invalid.
	(basic_ios::init): Comment.
	* testsuite/27_io/ios_init.cc (test02): New.

From-SVN: r49205
parent c4df4ceb
2002-01-24 Benjamin Kosnik <bkoz@redhat.com>
* testsuite/27_io/ostream_inserter_char.cc (test07): New.
2002-01-24 Benjamin Kosnik <bkoz@redhat.com>
* include/bits/basic_ios.h (basic_ios::_M_check_facet): Make
const, tweak.
(basic_ios::fill(char_type)): Use fill().
* include/bits/basic_ios.tcc (basic_ios::widen): Use _M_check_facet.
(basic_ios::narrow): Same.
(basic_ios::_M_cache_facets): Explicitly set cached facets to zero
if they are invalid.
(basic_ios::init): Comment.
* testsuite/27_io/ios_init.cc (test02): New.
2002-01-24 Phil Edwards <pme@gcc.gnu.org> 2002-01-24 Phil Edwards <pme@gcc.gnu.org>
* include/bits/stl_tempbuf.h (_Temporary_buffer): Add doxygen hook. * include/bits/stl_tempbuf.h (_Temporary_buffer): Add doxygen hook.
......
// Iostreams base classes -*- C++ -*- // Iostreams base classes -*- C++ -*-
// Copyright (C) 1997, 1998, 1999, 2001 Free Software Foundation, Inc. // Copyright (C) 1997, 1998, 1999, 2001, 2002 Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // 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 // software; you can redistribute it and/or modify it under the
...@@ -62,12 +62,11 @@ namespace std ...@@ -62,12 +62,11 @@ namespace std
typedef num_get<_CharT, __istreambuf_iter> __numget_type; typedef num_get<_CharT, __istreambuf_iter> __numget_type;
// Data members: // Data members:
private: protected:
basic_ostream<_CharT, _Traits>* _M_tie; basic_ostream<_CharT, _Traits>* _M_tie;
char_type _M_fill; char_type _M_fill;
iostate _M_exception; iostate _M_exception;
protected:
basic_streambuf<_CharT, _Traits>* _M_streambuf; basic_streambuf<_CharT, _Traits>* _M_streambuf;
iostate _M_streambuf_state; iostate _M_streambuf_state;
...@@ -174,7 +173,7 @@ namespace std ...@@ -174,7 +173,7 @@ namespace std
inline char_type inline char_type
fill(char_type __ch) fill(char_type __ch)
{ {
char_type __old = _M_fill; char_type __old = this->fill();
_M_fill = __ch; _M_fill = __ch;
return __old; return __old;
} }
...@@ -198,14 +197,11 @@ namespace std ...@@ -198,14 +197,11 @@ namespace std
init(basic_streambuf<_CharT, _Traits>* __sb); init(basic_streambuf<_CharT, _Traits>* __sb);
bool bool
_M_check_facet(const locale::facet* __f) _M_check_facet(const locale::facet* __f) const
{ {
bool __ret = false; if (!__f)
if (__f)
__ret = true;
else
__throw_bad_cast(); __throw_bad_cast();
return __ret; return true;
} }
void void
......
// basic_ios locale and locale-related member functions -*- C++ -*- // basic_ios locale and locale-related member functions -*- C++ -*-
// Copyright (C) 1999, 2001 Free Software Foundation, Inc. // Copyright (C) 1999, 2001, 2002 Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // 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 // software; you can redistribute it and/or modify it under the
...@@ -91,12 +91,22 @@ namespace std ...@@ -91,12 +91,22 @@ namespace std
template<typename _CharT, typename _Traits> template<typename _CharT, typename _Traits>
char char
basic_ios<_CharT, _Traits>::narrow(char_type __c, char __dfault) const basic_ios<_CharT, _Traits>::narrow(char_type __c, char __dfault) const
{ return _M_ios_fctype->narrow(__c, __dfault); } {
char __ret;
if (_M_check_facet(_M_ios_fctype))
__ret = _M_ios_fctype->narrow(__c, __dfault);
return __ret;
}
template<typename _CharT, typename _Traits> template<typename _CharT, typename _Traits>
_CharT _CharT
basic_ios<_CharT, _Traits>::widen(char __c) const basic_ios<_CharT, _Traits>::widen(char __c) const
{ return _M_ios_fctype->widen(__c); } {
char_type __ret;
if (_M_check_facet(_M_ios_fctype))
__ret = _M_ios_fctype->widen(__c);
return __ret;
}
// Locales: // Locales:
template<typename _CharT, typename _Traits> template<typename _CharT, typename _Traits>
...@@ -119,7 +129,19 @@ namespace std ...@@ -119,7 +129,19 @@ namespace std
ios_base::_M_init(); ios_base::_M_init();
_M_cache_facets(_M_ios_locale); _M_cache_facets(_M_ios_locale);
_M_tie = 0; _M_tie = 0;
// NB: The 27.4.4.1 Postconditions Table only specifies
// requirements after basic_ios::init() has been called. As part
// of this, fill() must return widen(' '), which needs an imbued
// ctype facet of char_type to return without throwing an
// exception. This is not a required facet, so streams with
// char_type != [char, wchar_t] will not have it by
// default. However, because fill()'s signature is const, this
// data member cannot be lazily initialized. Thus, thoughts of
// using a non-const helper function in ostream inserters is
// really besides the point.
_M_fill = this->widen(' '); _M_fill = this->widen(' ');
_M_exception = goodbit; _M_exception = goodbit;
_M_streambuf = __sb; _M_streambuf = __sb;
_M_streambuf_state = __sb ? goodbit : badbit; _M_streambuf_state = __sb ? goodbit : badbit;
...@@ -131,15 +153,18 @@ namespace std ...@@ -131,15 +153,18 @@ namespace std
{ {
if (has_facet<__ctype_type>(__loc)) if (has_facet<__ctype_type>(__loc))
_M_ios_fctype = &use_facet<__ctype_type>(__loc); _M_ios_fctype = &use_facet<__ctype_type>(__loc);
else
_M_ios_fctype = 0;
// Should be filled in by ostream and istream, respectively. // Should be filled in by ostream and istream, respectively.
if (has_facet<__numput_type>(__loc)) if (has_facet<__numput_type>(__loc))
_M_fnumput = &use_facet<__numput_type>(__loc); _M_fnumput = &use_facet<__numput_type>(__loc);
else
_M_fnumput = 0;
if (has_facet<__numget_type>(__loc)) if (has_facet<__numget_type>(__loc))
_M_fnumget = &use_facet<__numget_type>(__loc); _M_fnumget = &use_facet<__numget_type>(__loc);
else
_M_fnumget = 0;
} }
} // namespace std } // namespace std
#endif // _CPP_BITS_BASICIOS_TCC #endif
// 2001-06-05 Benjamin Kosnik <bkoz@redhat.com> // 2001-06-05 Benjamin Kosnik <bkoz@redhat.com>
// Copyright (C) 2001 Free Software Foundation, Inc. // Copyright (C) 2001, 2002 Free Software Foundation, Inc.
// //
// This file is part of the GNU ISO C++ Library. This library is free // 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 // software; you can redistribute it and/or modify it under the
...@@ -30,6 +30,7 @@ ...@@ -30,6 +30,7 @@
// 27.4.2.1.6 class ios_base::init // 27.4.2.1.6 class ios_base::init
#include <fstream> #include <fstream>
#include <sstream>
#include <iostream> #include <iostream>
#include <testsuite_hooks.h> #include <testsuite_hooks.h>
...@@ -81,8 +82,58 @@ void test01() ...@@ -81,8 +82,58 @@ void test01()
VERIFY( k1 == initial ); VERIFY( k1 == initial );
} }
// Non-required instantiations don't have the required facets inbued,
// by default, into the locale object. As such, basic_ios::init is
// required to return a bad_cast for the first use of fill() call.
// See 27.4.4.1
void test02()
{
bool test = true;
// 01: Doesn't call basic_ios::init, which uses ctype<char_type>..
try
{
std::basic_ostringstream<unsigned short> oss;
}
catch(...)
{
test = false;
}
// 02: Calls basic_ios::init, which uses ctype<char_type>..
try
{
std::basic_string<unsigned short> str;
std::basic_ostringstream<unsigned short> oss(str);
// Shouldn't get this far.
test = false;
// Try each member functions for unformatted io.
// put
oss.put(324);
// write
const unsigned short us[4] = {1246, 433, 520, 0};
oss.write(us, 4);
// flush
oss.flush();
}
catch(const std::bad_cast& obj)
{
test = true;
}
catch(...)
{
test = false;
}
VERIFY( test );
}
int main() int main()
{ {
test01(); test01();
test02();
return 0; return 0;
} }
// 1999-08-16 bkoz // 1999-08-16 bkoz
// Copyright (C) 2000, 1999 Free Software Foundation // Copyright (C) 1999, 2000, 2002 Free Software Foundation
// //
// This file is part of the GNU ISO C++ Library. This library is free // 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 // software; you can redistribute it and/or modify it under the
...@@ -52,10 +52,7 @@ bool test01() ...@@ -52,10 +52,7 @@ bool test01()
f << str01; f << str01;
f.close(); f.close();
#ifdef DEBUG_ASSERT VERIFY( test );
assert(test);
#endif
return test; return test;
} }
...@@ -92,11 +89,6 @@ bool test02(void) ...@@ -92,11 +89,6 @@ bool test02(void)
oss03 << str03; oss03 << str03;
tmp = oss03.str(); tmp = oss03.str();
VERIFY( tmp == "909909" ); VERIFY( tmp == "909909" );
#ifdef DEBUG_ASSERT
assert(test);
#endif
return test; return test;
} }
...@@ -133,17 +125,12 @@ bool test03(void) ...@@ -133,17 +125,12 @@ bool test03(void)
oss03 << str03; oss03 << str03;
tmp = oss03.str(); tmp = oss03.str();
VERIFY( tmp == "909909" ); VERIFY( tmp == "909909" );
#ifdef DEBUG_ASSERT
assert(test);
#endif
return test; return test;
} }
// stringstream and large strings // stringstream and large strings
bool test04() { bool test04()
{
bool test = true; bool test = true;
std::string str_01; std::string str_01;
const std::string str_02("coltrane playing 'softly as a morning sunrise'"); const std::string str_02("coltrane playing 'softly as a morning sunrise'");
...@@ -166,11 +153,6 @@ bool test04() { ...@@ -166,11 +153,6 @@ bool test04() {
VERIFY( oss_02.good() ); VERIFY( oss_02.good() );
VERIFY( str_tmp != str_01 ); VERIFY( str_tmp != str_01 );
VERIFY( str_tmp.size() == 2390 ); VERIFY( str_tmp.size() == 2390 );
#ifdef DEBUG_ASSERT
assert(test);
#endif
return test; return test;
} }
...@@ -216,11 +198,6 @@ bool test05() ...@@ -216,11 +198,6 @@ bool test05()
str10 = sstr05.str(); str10 = sstr05.str();
VERIFY( str05 == str01 ); VERIFY( str05 == str01 );
VERIFY( str10 == str01 ); VERIFY( str10 == str01 );
#ifdef DEBUG_ASSERT
assert(test);
#endif
return test; return test;
} }
...@@ -249,13 +226,69 @@ void test06() ...@@ -249,13 +226,69 @@ void test06()
VERIFY( ostr2.str() == "blackalicious NIA " ); VERIFY( ostr2.str() == "blackalicious NIA " );
ostr2 << "4: deception (5:19)"; // should append to full string from above ostr2 << "4: deception (5:19)"; // should append to full string from above
VERIFY( ostr2.str() == "blackalicious NIA 4: deception (5:19)" ); VERIFY( ostr2.str() == "blackalicious NIA 4: deception (5:19)" );
}
// Global counter, needs to be reset after use.
bool used;
class gnu_ctype : public std::ctype<wchar_t>
{
protected:
char_type
do_widen(char c) const
{
used = true;
return std::ctype<wchar_t>::do_widen(c);
}
const char*
do_widen(const char* low, const char* high, char_type* dest) const
{
used = true;
return std::ctype<wchar_t>::do_widen(low, high, dest);
}
};
#ifdef DEBUG_ASSERT // 27.6.2.5.4 - Character inserter template functions
assert(test); // [lib.ostream.inserters.character]
void test07()
{
#if _GLIBCPP_USE_WCHAR_T
using namespace std;
bool test = true;
const char* buffer = "SFPL 5th floor, outside carrol, the Asian side";
wostringstream oss;
oss.imbue(locale(locale::classic(), new gnu_ctype));
// 1
// template<class charT, class traits>
// basic_ostream<charT,traits>& operator<<(basic_ostream<charT,traits>& out,
// const char* s);
used = false;
oss << buffer;
VERIFY( used ); // Only required for char_type != char
wstring str = oss.str();
wchar_t c1 = oss.widen(buffer[0]);
VERIFY( str[0] == c1 );
wchar_t c2 = oss.widen(buffer[1]);
VERIFY( str[1] == c2 );
// 2
// template<class charT, class traits>
// basic_ostream<charT,traits>& operator<<(basic_ostream<charT,traits>& out,
// char c);
used = false;
oss.str(wstring());
oss << 'b';
VERIFY( used ); // Only required for char_type != char
str = oss.str();
wchar_t c3 = oss.widen('b');
VERIFY( str[0] == c3 );
#endif #endif
} }
int main() int main()
{ {
test01(); test01();
...@@ -264,5 +297,6 @@ int main() ...@@ -264,5 +297,6 @@ int main()
test04(); test04();
test05(); test05();
test06(); test06();
test07();
return 0; return 0;
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment