]> git.ipfire.org Git - thirdparty/gcc.git/blob - libstdc++-v3/config/locale/gnu/numeric_members.cc
Update Copyright years for files modified in 2011 and/or 2012.
[thirdparty/gcc.git] / libstdc++-v3 / config / locale / gnu / numeric_members.cc
1 // std::numpunct implementation details, GNU version -*- C++ -*-
2
3 // Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2011
4 // Free Software Foundation, Inc.
5 //
6 // This file is part of the GNU ISO C++ Library. This library is free
7 // software; you can redistribute it and/or modify it under the
8 // terms of the GNU General Public License as published by the
9 // Free Software Foundation; either version 3, or (at your option)
10 // any later version.
11
12 // This library is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU General Public License for more details.
16
17 // Under Section 7 of GPL version 3, you are granted additional
18 // permissions described in the GCC Runtime Library Exception, version
19 // 3.1, as published by the Free Software Foundation.
20
21 // You should have received a copy of the GNU General Public License and
22 // a copy of the GCC Runtime Library Exception along with this program;
23 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
24 // <http://www.gnu.org/licenses/>.
25
26 //
27 // ISO C++ 14882: 22.2.3.1.2 numpunct virtual functions
28 //
29
30 // Written by Benjamin Kosnik <bkoz@redhat.com>
31
32 #include <locale>
33 #include <bits/c++locale_internal.h>
34
35 namespace std _GLIBCXX_VISIBILITY(default)
36 {
37 _GLIBCXX_BEGIN_NAMESPACE_VERSION
38
39 template<>
40 void
41 numpunct<char>::_M_initialize_numpunct(__c_locale __cloc)
42 {
43 if (!_M_data)
44 _M_data = new __numpunct_cache<char>;
45
46 if (!__cloc)
47 {
48 // "C" locale
49 _M_data->_M_grouping = "";
50 _M_data->_M_grouping_size = 0;
51 _M_data->_M_use_grouping = false;
52
53 _M_data->_M_decimal_point = '.';
54 _M_data->_M_thousands_sep = ',';
55
56 for (size_t __i = 0; __i < __num_base::_S_oend; ++__i)
57 _M_data->_M_atoms_out[__i] = __num_base::_S_atoms_out[__i];
58
59 for (size_t __j = 0; __j < __num_base::_S_iend; ++__j)
60 _M_data->_M_atoms_in[__j] = __num_base::_S_atoms_in[__j];
61 }
62 else
63 {
64 // Named locale.
65 _M_data->_M_decimal_point = *(__nl_langinfo_l(DECIMAL_POINT,
66 __cloc));
67 _M_data->_M_thousands_sep = *(__nl_langinfo_l(THOUSANDS_SEP,
68 __cloc));
69
70 // Check for NULL, which implies no grouping.
71 if (_M_data->_M_thousands_sep == '\0')
72 {
73 // Like in "C" locale.
74 _M_data->_M_grouping = "";
75 _M_data->_M_grouping_size = 0;
76 _M_data->_M_use_grouping = false;
77 _M_data->_M_thousands_sep = ',';
78 }
79 else
80 {
81 const char* __src = __nl_langinfo_l(GROUPING, __cloc);
82 const size_t __len = strlen(__src);
83 if (__len)
84 {
85 __try
86 {
87 char* __dst = new char[__len + 1];
88 memcpy(__dst, __src, __len + 1);
89 _M_data->_M_grouping = __dst;
90 }
91 __catch(...)
92 {
93 delete _M_data;
94 _M_data = 0;
95 __throw_exception_again;
96 }
97 }
98 else
99 {
100 _M_data->_M_grouping = "";
101 _M_data->_M_use_grouping = false;
102 }
103 _M_data->_M_grouping_size = __len;
104 }
105 }
106
107 // NB: There is no way to extact this info from posix locales.
108 // _M_truename = __nl_langinfo_l(YESSTR, __cloc);
109 _M_data->_M_truename = "true";
110 _M_data->_M_truename_size = 4;
111 // _M_falsename = __nl_langinfo_l(NOSTR, __cloc);
112 _M_data->_M_falsename = "false";
113 _M_data->_M_falsename_size = 5;
114 }
115
116 template<>
117 numpunct<char>::~numpunct()
118 {
119 if (_M_data->_M_grouping_size)
120 delete [] _M_data->_M_grouping;
121 delete _M_data;
122 }
123
124 #ifdef _GLIBCXX_USE_WCHAR_T
125 template<>
126 void
127 numpunct<wchar_t>::_M_initialize_numpunct(__c_locale __cloc)
128 {
129 if (!_M_data)
130 _M_data = new __numpunct_cache<wchar_t>;
131
132 if (!__cloc)
133 {
134 // "C" locale
135 _M_data->_M_grouping = "";
136 _M_data->_M_grouping_size = 0;
137 _M_data->_M_use_grouping = false;
138
139 _M_data->_M_decimal_point = L'.';
140 _M_data->_M_thousands_sep = L',';
141
142 // Use ctype::widen code without the facet...
143 for (size_t __i = 0; __i < __num_base::_S_oend; ++__i)
144 _M_data->_M_atoms_out[__i] =
145 static_cast<wchar_t>(__num_base::_S_atoms_out[__i]);
146
147 for (size_t __j = 0; __j < __num_base::_S_iend; ++__j)
148 _M_data->_M_atoms_in[__j] =
149 static_cast<wchar_t>(__num_base::_S_atoms_in[__j]);
150 }
151 else
152 {
153 // Named locale.
154 // NB: In the GNU model wchar_t is always 32 bit wide.
155 union { char *__s; wchar_t __w; } __u;
156 __u.__s = __nl_langinfo_l(_NL_NUMERIC_DECIMAL_POINT_WC, __cloc);
157 _M_data->_M_decimal_point = __u.__w;
158
159 __u.__s = __nl_langinfo_l(_NL_NUMERIC_THOUSANDS_SEP_WC, __cloc);
160 _M_data->_M_thousands_sep = __u.__w;
161
162 // Check for NULL, which implies no grouping.
163 if (_M_data->_M_thousands_sep == L'\0')
164 {
165 // Like in "C" locale.
166 _M_data->_M_grouping = "";
167 _M_data->_M_grouping_size = 0;
168 _M_data->_M_use_grouping = false;
169 _M_data->_M_thousands_sep = L',';
170 }
171 else
172 {
173 const char* __src = __nl_langinfo_l(GROUPING, __cloc);
174 const size_t __len = strlen(__src);
175 if (__len)
176 {
177 __try
178 {
179 char* __dst = new char[__len + 1];
180 memcpy(__dst, __src, __len + 1);
181 _M_data->_M_grouping = __dst;
182 }
183 __catch(...)
184 {
185 delete _M_data;
186 _M_data = 0;
187 __throw_exception_again;
188 }
189 }
190 else
191 {
192 _M_data->_M_grouping = "";
193 _M_data->_M_use_grouping = false;
194 }
195 _M_data->_M_grouping_size = __len;
196 }
197 }
198
199 // NB: There is no way to extact this info from posix locales.
200 // _M_truename = __nl_langinfo_l(YESSTR, __cloc);
201 _M_data->_M_truename = L"true";
202 _M_data->_M_truename_size = 4;
203 // _M_falsename = __nl_langinfo_l(NOSTR, __cloc);
204 _M_data->_M_falsename = L"false";
205 _M_data->_M_falsename_size = 5;
206 }
207
208 template<>
209 numpunct<wchar_t>::~numpunct()
210 {
211 if (_M_data->_M_grouping_size)
212 delete [] _M_data->_M_grouping;
213 delete _M_data;
214 }
215 #endif
216
217 _GLIBCXX_END_NAMESPACE_VERSION
218 } // namespace