1 //
2 //  Copyright (c) 2009-2011 Artyom Beilis (Tonkikh)
3 //
4 //  Distributed under the Boost Software License, Version 1.0. (See
5 //  accompanying file LICENSE_1_0.txt or copy at
6 //  http://www.boost.org/LICENSE_1_0.txt)
7 //
8 #define BOOST_LOCALE_SOURCE
9 #include <boost/config.hpp>
10 
11 #if defined(BOOST_WINDOWS) || defined(__CYGWIN__)
12 #define BOOST_LOCALE_WITH_WCONV
13 #endif
14 
15 #ifdef BOOST_LOCALE_WITH_ICONV
16 #include "iconv_codepage.ipp"
17 #endif
18 #ifdef BOOST_LOCALE_WITH_ICU
19 #include "uconv_codepage.ipp"
20 #endif
21 #ifdef BOOST_LOCALE_WITH_WCONV
22 #include "wconv_codepage.ipp"
23 #endif
24 
25 #include <boost/locale/encoding.hpp>
26 
27 #include <string>
28 #include <cstring>
29 #include <memory>
30 
31 namespace boost {
32     namespace locale {
33         namespace conv {
34             namespace impl {
35 
convert_between(char const * begin,char const * end,char const * to_charset,char const * from_charset,method_type how)36                 std::string convert_between(char const *begin,
37                                             char const *end,
38                                             char const *to_charset,
39                                             char const *from_charset,
40                                             method_type how)
41                 {
42                     std::auto_ptr<converter_between> cvt;
43                     #ifdef BOOST_LOCALE_WITH_ICONV
44                     cvt.reset(new iconv_between());
45                     if(cvt->open(to_charset,from_charset,how))
46                         return cvt->convert(begin,end);
47                     #endif
48                     #ifdef BOOST_LOCALE_WITH_ICU
49                     cvt.reset(new uconv_between());
50                     if(cvt->open(to_charset,from_charset,how))
51                         return cvt->convert(begin,end);
52                     #endif
53                     #ifdef BOOST_LOCALE_WITH_WCONV
54                     cvt.reset(new wconv_between());
55                     if(cvt->open(to_charset,from_charset,how))
56                         return cvt->convert(begin,end);
57                     #endif
58                     throw invalid_charset_error(std::string(to_charset) + " or " + from_charset);
59                 }
60 
61                 template<typename CharType>
convert_to(char const * begin,char const * end,char const * charset,method_type how)62                 std::basic_string<CharType> convert_to(
63                                         char const *begin,
64                                         char const *end,
65                                         char const *charset,
66                                         method_type how)
67                 {
68                     std::auto_ptr<converter_to_utf<CharType> > cvt;
69                     #ifdef BOOST_LOCALE_WITH_ICONV
70                     cvt.reset(new iconv_to_utf<CharType>());
71                     if(cvt->open(charset,how))
72                         return cvt->convert(begin,end);
73                     #endif
74                     #ifdef BOOST_LOCALE_WITH_ICU
75                     cvt.reset(new uconv_to_utf<CharType>());
76                     if(cvt->open(charset,how))
77                         return cvt->convert(begin,end);
78                     #endif
79                     #ifdef BOOST_LOCALE_WITH_WCONV
80                     cvt.reset(new wconv_to_utf<CharType>());
81                     if(cvt->open(charset,how))
82                         return cvt->convert(begin,end);
83                     #endif
84                     throw invalid_charset_error(charset);
85                 }
86 
87                 template<typename CharType>
convert_from(CharType const * begin,CharType const * end,char const * charset,method_type how)88                 std::string convert_from(
89                                         CharType const *begin,
90                                         CharType const *end,
91                                         char const *charset,
92                                         method_type how)
93                 {
94                     std::auto_ptr<converter_from_utf<CharType> > cvt;
95                     #ifdef BOOST_LOCALE_WITH_ICONV
96                     cvt.reset(new iconv_from_utf<CharType>());
97                     if(cvt->open(charset,how))
98                         return cvt->convert(begin,end);
99                     #endif
100                     #ifdef BOOST_LOCALE_WITH_ICU
101                     cvt.reset(new uconv_from_utf<CharType>());
102                     if(cvt->open(charset,how))
103                         return cvt->convert(begin,end);
104                     #endif
105                     #ifdef BOOST_LOCALE_WITH_WCONV
106                     cvt.reset(new wconv_from_utf<CharType>());
107                     if(cvt->open(charset,how))
108                         return cvt->convert(begin,end);
109                     #endif
110                     throw invalid_charset_error(charset);
111                 }
112 
normalize_encoding(char const * ccharset)113                 std::string normalize_encoding(char const *ccharset)
114                 {
115                     std::string charset;
116                     charset.reserve(std::strlen(ccharset));
117                     while(*ccharset!=0) {
118                         char c=*ccharset++;
119                         if('0' <= c && c<= '9')
120                             charset+=c;
121                         else if('a' <=c && c <='z')
122                             charset+=c;
123                         else if('A' <=c && c <='Z')
124                             charset+=char(c-'A'+'a');
125                     }
126                     return charset;
127                 }
128 
129 
130             } // impl
131 
132             using namespace impl;
133 
between(char const * begin,char const * end,std::string const & to_charset,std::string const & from_charset,method_type how)134             std::string between(char const *begin,char const *end,
135                                 std::string const &to_charset,std::string const &from_charset,method_type how)
136             {
137                 return convert_between(begin,end,to_charset.c_str(),from_charset.c_str(),how);
138             }
139 
140             template<>
to_utf(char const * begin,char const * end,std::string const & charset,method_type how)141             std::basic_string<char> to_utf(char const *begin,char const *end,std::string const &charset,method_type how)
142             {
143                 return convert_to<char>(begin,end,charset.c_str(),how);
144             }
145 
146             template<>
from_utf(char const * begin,char const * end,std::string const & charset,method_type how)147             std::string from_utf(char const *begin,char const *end,std::string const &charset,method_type how)
148             {
149                 return convert_from<char>(begin,end,charset.c_str(),how);
150             }
151 
152             template<>
to_utf(char const * begin,char const * end,std::string const & charset,method_type how)153             std::basic_string<wchar_t> to_utf(char const *begin,char const *end,std::string const &charset,method_type how)
154             {
155                 return convert_to<wchar_t>(begin,end,charset.c_str(),how);
156             }
157 
158             template<>
from_utf(wchar_t const * begin,wchar_t const * end,std::string const & charset,method_type how)159             std::string from_utf(wchar_t const *begin,wchar_t const *end,std::string const &charset,method_type how)
160             {
161                 return convert_from<wchar_t>(begin,end,charset.c_str(),how);
162             }
163 
164             #ifdef BOOST_HAS_CHAR16_T
165             template<>
to_utf(char const * begin,char const * end,std::string const & charset,method_type how)166             std::basic_string<char16_t> to_utf(char const *begin,char const *end,std::string const &charset,method_type how)
167             {
168                 return convert_to<char16_t>(begin,end,charset.c_str(),how);
169             }
170 
171             template<>
from_utf(char16_t const * begin,char16_t const * end,std::string const & charset,method_type how)172             std::string from_utf(char16_t const *begin,char16_t const *end,std::string const &charset,method_type how)
173             {
174                 return convert_from<char16_t>(begin,end,charset.c_str(),how);
175             }
176             #endif
177 
178             #ifdef BOOST_HAS_CHAR32_T
179             template<>
to_utf(char const * begin,char const * end,std::string const & charset,method_type how)180             std::basic_string<char32_t> to_utf(char const *begin,char const *end,std::string const &charset,method_type how)
181             {
182                 return convert_to<char32_t>(begin,end,charset.c_str(),how);
183             }
184 
185             template<>
from_utf(char32_t const * begin,char32_t const * end,std::string const & charset,method_type how)186             std::string from_utf(char32_t const *begin,char32_t const *end,std::string const &charset,method_type how)
187             {
188                 return convert_from<char32_t>(begin,end,charset.c_str(),how);
189             }
190             #endif
191 
192 
193         }
194     }
195 }
196 
197 
198 
199 // vim: tabstop=4 expandtab shiftwidth=4 softtabstop=4
200 
201