This is the mail archive of the libstdc++@gcc.gnu.org mailing list for the libstdc++ project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Patch] libstdc++/9548 and DR 231


Hi,

the below, for trunk, fixes the bug and implements the resolution of
DR 231 (Ready): both _S_format_float and its call in _M_convert_float
become cleaner.

If the patch gets accepted I would like to apply something similar
to 3_3, keeping intact _S_format_float prototype for ABI-sake.

Tested x86-linux. Ok?

Paolo.

////////////
2003-02-05  Paolo Carlini  <pcarlini@unitus.it>

	PR libstdc++/9548
	Implement resolution of DR 231 (Ready)
	* include/bits/locale_facets.h (__num_base::_S_format_float):
	Change declaration: return void, remove __prec parameter.
	* src/locale.cc (__num_base::_S_format_float): Implement
	resolution of DR 231.
	* include/bits/locale_facets.tcc (num_put::_M_convert_float):
	Tweak uses. Check for negative precision.
	* testsuite/22_locale/num_put/put/char/6.cc: Add
	* testsuite/22_locale/num_put/put/wchar_t/6.cc: Likewise.
diff -prN libstdc++-v3-orig/include/bits/locale_facets.h libstdc++-v3/include/bits/locale_facets.h
*** libstdc++-v3-orig/include/bits/locale_facets.h	Wed Jan 22 17:51:51 2003
--- libstdc++-v3/include/bits/locale_facets.h	Wed Feb  5 13:59:04 2003
*************** namespace std
*** 509,517 ****
  
      // num_put
      // Construct and return valid scanf format for floating point types.
!     static bool
!     _S_format_float(const ios_base& __io, char* __fptr, char __mod, 
! 		    streamsize __prec);
      
      // Construct and return valid scanf format for integer types.
      static void
--- 509,516 ----
  
      // num_put
      // Construct and return valid scanf format for floating point types.
!     static void
!     _S_format_float(const ios_base& __io, char* __fptr, char __mod);
      
      // Construct and return valid scanf format for integer types.
      static void
diff -prN libstdc++-v3-orig/include/bits/locale_facets.tcc libstdc++-v3/include/bits/locale_facets.tcc
*** libstdc++-v3-orig/include/bits/locale_facets.tcc	Sat Feb  1 13:57:21 2003
--- libstdc++-v3/include/bits/locale_facets.tcc	Thu Feb  6 01:37:58 2003
*************** namespace std
*** 635,640 ****
--- 635,644 ----
  	if (__prec > static_cast<streamsize>(__max_digits))
  	  __prec = static_cast<streamsize>(__max_digits);
  
+ 	// Default precision.
+ 	if (__prec < static_cast<streamsize>(0))
+ 	  __prec = static_cast<streamsize>(6);
+ 
  	// Long enough for the max format spec.
  	char __fbuf[16];
  
*************** namespace std
*** 646,669 ****
  	int __cs_size = __max_digits * 3;
  	char* __cs = static_cast<char*>(__builtin_alloca(__cs_size));
  
! 	const bool __fp = _S_format_float(__io, __fbuf, __mod, __prec);
! 	if (__fp)
! 	  __len = __convert_from_v(__cs, __cs_size, __fbuf, __v, 
! 				   _S_c_locale, __prec);
! 	else
! 	  __len = __convert_from_v(__cs, __cs_size, __fbuf, __v, _S_c_locale);
  
  	// If the buffer was not large enough, try again with the correct size.
  	if (__len >= __cs_size)
  	  {
  	    __cs_size = __len + 1; 
  	    __cs = static_cast<char*>(__builtin_alloca(__cs_size));
! 	    if (__fp)
! 	      __len = __convert_from_v(__cs, __cs_size, __fbuf, __v, 
  				       _S_c_locale, __prec);
- 	    else
- 	      __len = __convert_from_v(__cs, __cs_size, __fbuf, __v, 
- 				       _S_c_locale);
  	  }
  #else
  	// Consider the possibility of long ios_base::fixed outputs
--- 650,666 ----
  	int __cs_size = __max_digits * 3;
  	char* __cs = static_cast<char*>(__builtin_alloca(__cs_size));
  
! 	_S_format_float(__io, __fbuf, __mod);
! 	__len = __convert_from_v(__cs, __cs_size, __fbuf, __v, _S_c_locale,
! 				 __prec);
  
  	// If the buffer was not large enough, try again with the correct size.
  	if (__len >= __cs_size)
  	  {
  	    __cs_size = __len + 1; 
  	    __cs = static_cast<char*>(__builtin_alloca(__cs_size));
! 	    __len = __convert_from_v(__cs, __cs_size, __fbuf, __v, 
  				       _S_c_locale, __prec);
  	  }
  #else
  	// Consider the possibility of long ios_base::fixed outputs
*************** namespace std
*** 678,687 ****
  	                              : __max_digits * 3;
  	char* __cs = static_cast<char*>(__builtin_alloca(__cs_size));
  
! 	if (_S_format_float(__io, __fbuf, __mod, __prec))
! 	  __len = __convert_from_v(__cs, 0, __fbuf, __v, _S_c_locale, __prec);
! 	else
! 	  __len = __convert_from_v(__cs, 0, __fbuf, __v, _S_c_locale);
  #endif
  	return _M_widen_float(__s, __io, __fill, __cs, __len);
        }
--- 675,682 ----
  	                              : __max_digits * 3;
  	char* __cs = static_cast<char*>(__builtin_alloca(__cs_size));
  
! 	_S_format_float(__io, __fbuf, __mod);
! 	__len = __convert_from_v(__cs, 0, __fbuf, __v, _S_c_locale, __prec);
  #endif
  	return _M_widen_float(__s, __io, __fill, __cs, __len);
        }
diff -prN libstdc++-v3-orig/src/locale.cc libstdc++-v3/src/locale.cc
*** libstdc++-v3-orig/src/locale.cc	Sat Feb  1 13:57:21 2003
--- libstdc++-v3/src/locale.cc	Wed Feb  5 13:55:50 2003
*************** namespace std 
*** 505,515 ****
  
    const char __num_base::_S_atoms[] = "0123456789eEabcdfABCDF";
  
!   bool
!   __num_base::_S_format_float(const ios_base& __io, char* __fptr, char __mod,
! 			      streamsize __prec)
    {
-     bool __incl_prec = false;
      ios_base::fmtflags __flags = __io.flags();
      *__fptr++ = '%';
      // [22.2.2.2.2] Table 60
--- 505,516 ----
  
    const char __num_base::_S_atoms[] = "0123456789eEabcdfABCDF";
  
!   // _GLIBCPP_RESOLVE_LIB_DEFECTS
!   // According to the resolution of DR 231, about 22.2.2.2.2, p11,
!   // "str.precision() is specified in the conversion specification".
!   void
!   __num_base::_S_format_float(const ios_base& __io, char* __fptr, char __mod)
    {
      ios_base::fmtflags __flags = __io.flags();
      *__fptr++ = '%';
      // [22.2.2.2.2] Table 60
*************** namespace std 
*** 517,529 ****
        *__fptr++ = '+';
      if (__flags & ios_base::showpoint)
        *__fptr++ = '#';
!     // As per [22.2.2.2.2.11]
!     if (__flags & ios_base::fixed || __prec > 0)
!       {
! 	*__fptr++ = '.';
! 	*__fptr++ = '*';
! 	__incl_prec = true;
!       }
      if (__mod)
        *__fptr++ = __mod;
      ios_base::fmtflags __fltfield = __flags & ios_base::floatfield;
--- 518,529 ----
        *__fptr++ = '+';
      if (__flags & ios_base::showpoint)
        *__fptr++ = '#';
! 
!     // As per DR 231: _always_, not only when 
!     // __flags & ios_base::fixed || __prec > 0
!     *__fptr++ = '.';
!     *__fptr++ = '*';
! 
      if (__mod)
        *__fptr++ = __mod;
      ios_base::fmtflags __fltfield = __flags & ios_base::floatfield;
*************** namespace std 
*** 535,541 ****
      else
        *__fptr++ = (__flags & ios_base::uppercase) ? 'G' : 'g';
      *__fptr = '\0';
-     return __incl_prec;
    }
    
    void
--- 535,540 ----
diff -prN libstdc++-v3-orig/testsuite/22_locale/num_put/put/char/6.cc libstdc++-v3/testsuite/22_locale/num_put/put/char/6.cc
*** libstdc++-v3-orig/testsuite/22_locale/num_put/put/char/6.cc	Thu Jan  1 01:00:00 1970
--- libstdc++-v3/testsuite/22_locale/num_put/put/char/6.cc	Wed Feb  5 19:24:09 2003
***************
*** 0 ****
--- 1,68 ----
+ // 2003-02-05 Paolo Carlini <pcarlini@unitus.it>
+ 
+ // Copyright (C) 2003 Free Software Foundation
+ //
+ // 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, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ // USA.
+ 
+ // 22.2.2.2.1  num_put members
+ 
+ #include <locale>
+ #include <sstream>
+ #include <testsuite_hooks.h>
+ 
+ // libstdc++/9548
+ void test01()
+ {
+   using namespace std;
+   bool test = true;
+ 
+   ostringstream oss;
+   const num_put<char>& np = use_facet<num_put<char> >(oss.getloc()); 
+ 
+   oss.clear();
+   oss.precision(-1);
+   oss.setf(ios_base::fixed, ios_base::floatfield);
+   np.put(oss.rdbuf(), oss, '+', 30.5);
+   string result = oss.str();
+   VERIFY( result == "30.500000" );
+ }
+ 
+ // DR 231
+ void test02()
+ {
+   using namespace std;
+   bool test = true;
+ 
+   ostringstream oss;
+   const num_put<char>& np = use_facet<num_put<char> >(oss.getloc()); 
+ 
+   oss.clear();
+   oss.precision(0);
+   oss.setf(ios_base::scientific, ios_base::floatfield);
+   np.put(oss.rdbuf(), oss, '+', 1.0);
+   string result = oss.str();
+   VERIFY( result == "1e+00" );
+ }
+ 
+ int main()
+ {
+   test01();
+   test02();
+   return 0;
+ }
+ 
+ 
diff -prN libstdc++-v3-orig/testsuite/22_locale/num_put/put/wchar_t/6.cc libstdc++-v3/testsuite/22_locale/num_put/put/wchar_t/6.cc
*** libstdc++-v3-orig/testsuite/22_locale/num_put/put/wchar_t/6.cc	Thu Jan  1 01:00:00 1970
--- libstdc++-v3/testsuite/22_locale/num_put/put/wchar_t/6.cc	Wed Feb  5 19:25:51 2003
***************
*** 0 ****
--- 1,68 ----
+ // 2003-02-05 Paolo Carlini <pcarlini@unitus.it>
+ 
+ // Copyright (C) 2003 Free Software Foundation
+ //
+ // 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, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ // USA.
+ 
+ // 22.2.2.2.1  num_put members
+ 
+ #include <locale>
+ #include <sstream>
+ #include <testsuite_hooks.h>
+ 
+ // libstdc++/9548
+ void test01()
+ {
+   using namespace std;
+   bool test = true;
+ 
+   wostringstream oss;
+   const num_put<wchar_t>& np = use_facet<num_put<wchar_t> >(oss.getloc()); 
+ 
+   oss.clear();
+   oss.precision(-1);
+   oss.setf(ios_base::fixed, ios_base::floatfield);
+   np.put(oss.rdbuf(), oss, '+', 30.5);
+   wstring result = oss.str();
+   VERIFY( result == L"30.500000" );
+ }
+ 
+ // DR 231
+ void test02()
+ {
+   using namespace std;
+   bool test = true;
+ 
+   wostringstream oss;
+   const num_put<wchar_t>& np = use_facet<num_put<wchar_t> >(oss.getloc()); 
+ 
+   oss.clear();
+   oss.precision(0);
+   oss.setf(ios_base::scientific, ios_base::floatfield);
+   np.put(oss.rdbuf(), oss, '+', 1.0);
+   wstring result = oss.str();
+   VERIFY( result == L"1e+00" );
+ }
+ 
+ int main()
+ {
+   test01();
+   test02();
+   return 0;
+ }
+ 
+ 

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]