locale.cc: Fix comments, move ctors together.

2002-10-09  Benjamin Kosnik  <bkoz@redhat.com>

	* src/locale.cc: Fix comments, move ctors together.
	* testsuite/22_locale/static_members.cc (test03): Add.

From-SVN: r58001
This commit is contained in:
Benjamin Kosnik 2002-10-10 05:15:29 +00:00 committed by Benjamin Kosnik
parent 7db40b5f9b
commit 402a402cab
3 changed files with 119 additions and 32 deletions

View File

@ -1,3 +1,8 @@
2002-10-09 Benjamin Kosnik <bkoz@redhat.com>
* src/locale.cc: Fix comments, move ctors together.
* testsuite/22_locale/static_members.cc (test03): Add.
2002-10-08 Jonathan Lennox <lennox@cs.columbia.edu>
PR libstdc++/8071, libstdc++/8127, libstdc++/6745

View File

@ -148,25 +148,6 @@ namespace std
0
};
locale::~locale() throw()
{ _M_impl->_M_remove_reference(); }
void
locale::_M_coalesce(const locale& __base, const locale& __add,
category __cat)
{
__cat = _S_normalize_category(__cat);
_M_impl = new _Impl(*__base._M_impl, 1);
try
{ _M_impl->_M_replace_categories(__add._M_impl, __cat); }
catch (...)
{
_M_impl->_M_remove_reference();
__throw_exception_again;
}
}
locale::locale() throw()
{
_S_initialize();
@ -178,6 +159,7 @@ namespace std
// This is used to initialize global and classic locales, and
// assumes that the _Impl objects are constructed correctly.
// The lack of a reference increment is intentional.
locale::locale(_Impl* __ip) throw() : _M_impl(__ip)
{ }
@ -309,6 +291,9 @@ namespace std
locale::locale(const locale& __base, const locale& __add, category __cat)
{ _M_coalesce(__base, __add, __cat); }
locale::~locale() throw()
{ _M_impl->_M_remove_reference(); }
bool
locale::operator==(const locale& __rhs) const throw()
{
@ -381,7 +366,7 @@ namespace std
try
{
// 26 Standard facets, 2 references.
// One reference for _M_classic, one for _M_global
// One reference for _S_classic, one for _S_global
_S_classic = new (&c_locale_impl) _Impl(0, 2, true);
_S_global = _S_classic;
new (&c_locale) locale(_S_classic);
@ -399,6 +384,22 @@ namespace std
return c_locale;
}
void
locale::_M_coalesce(const locale& __base, const locale& __add,
category __cat)
{
__cat = _S_normalize_category(__cat);
_M_impl = new _Impl(*__base._M_impl, 1);
try
{ _M_impl->_M_replace_categories(__add._M_impl, __cat); }
catch (...)
{
_M_impl->_M_remove_reference();
__throw_exception_again;
}
}
locale::category
locale::_S_normalize_category(category __cat)
{

View File

@ -23,8 +23,7 @@
#include <cwchar> // for mbstate_t
#include <locale>
#include <iostream>
//#include <testsuite_hooks.h>
#define VERIFY(x) test &= x
#include <testsuite_hooks.h>
typedef std::codecvt<char, char, std::mbstate_t> ccodecvt;
class gnu_codecvt: public ccodecvt { };
@ -32,12 +31,11 @@ class gnu_codecvt: public ccodecvt { };
void test01()
{
using namespace std;
bool test = true;
string str1, str2;
// Construct a locale object with the C facet.
const locale loc_env("");
const locale loc01 = locale::classic();
// Construct a locale object with the specialized facet.
@ -54,13 +52,13 @@ void test01()
// global
locale loc03;
VERIFY ( loc03 == loc01);
locale loc04 = locale::global(loc02);
locale global_orig = locale::global(loc02);
locale loc05;
VERIFY (loc05 != loc03);
VERIFY (loc05 == loc02);
// Reset global locale.
locale::global(loc_env);
// Reset global settings.
locale::global(global_orig);
}
// Sanity check locale::global(loc) and setlocale.
@ -77,20 +75,102 @@ void test02()
// Get underlying current locale and environment settings.
const string lc_all_orig = std::setlocale(LC_ALL, NULL);
const locale loc_orig("");
const locale env_orig("");
// setlocale to en_PH
string lc_all_ph = std::setlocale(LC_ALL, ph.c_str());
const locale loc_env("");
VERIFY( loc_env == loc_orig );
VERIFY( loc_env == env_orig );
locale::global(loc_mx);
locale global_orig = locale::global(loc_mx);
string lc_all_mx = std::setlocale(LC_ALL, NULL);
VERIFY( lc_all_mx == mx.c_str() );
// Restore global info.
locale::global(loc_orig);
// Restore global settings.
locale::global(global_orig);
}
// Static counter for use in checking ctors/dtors.
static std::size_t counter;
class surf : public std::locale::facet
{
public:
static std::locale::id id;
surf(size_t refs = 0): std::locale::facet(refs) { ++counter; }
~surf() { --counter; }
};
std::locale::id surf::id;
typedef surf facet_type;
// Verify lifetimes of global objects.
void test03()
{
using namespace std;
bool test = true;
string name;
locale global_orig;
// 1: Destroyed when out of scope.
{
{
{
VERIFY( counter == 0 );
{
locale loc01(locale::classic(), new facet_type);
VERIFY( counter == 1 );
global_orig = locale::global(loc01);
name = loc01.name();
}
VERIFY( counter == 1 );
locale loc02 = locale();
// Weak, but it's something...
VERIFY( loc02.name() == name );
}
VERIFY( counter == 1 );
// NB: loc03 should be a copy of the previous global locale.
locale loc03 = locale::global(global_orig);
VERIFY( counter == 1 );
VERIFY( loc03.name() == name );
}
VERIFY( counter == 0 );
locale loc04 = locale();
VERIFY( loc04 == global_orig );
}
// 2: Not destroyed when out of scope, deliberately leaked.
{
{
{
VERIFY( counter == 0 );
{
locale loc01(locale::classic(), new facet_type(1));
VERIFY( counter == 1 );
global_orig = locale::global(loc01);
name = loc01.name();
}
VERIFY( counter == 1 );
locale loc02 = locale();
// Weak, but it's something...
VERIFY( loc02.name() == name );
}
VERIFY( counter == 1 );
// NB: loc03 should be a copy of the previous global locale.
locale loc03 = locale::global(global_orig);
VERIFY( counter == 1 );
VERIFY( loc03.name() == name );
}
VERIFY( counter == 1 );
locale loc04 = locale();
VERIFY( loc04 == global_orig );
}
VERIFY( counter == 1 );
// Restore global settings.
locale::global(global_orig);
}
int main ()
@ -98,5 +178,6 @@ int main ()
test01();
test02();
test03();
return 0;
}