|
|
1.1 root 1: /*
2: Copyright (c) 2008 TrueCrypt Foundation. All rights reserved.
3:
1.1.1.3 ! root 4: Governed by the TrueCrypt License 2.5 the full text of which is contained
1.1 root 5: in the file License.txt included in TrueCrypt binary and source code
6: distribution packages.
7: */
8:
9: #ifdef __GNUC__
10: # include <cxxabi.h>
11: #endif
1.1.1.3 ! root 12: #include <locale>
1.1 root 13: #include <typeinfo>
14: #include "Buffer.h"
15: #include "Exception.h"
16: #include "ForEach.h"
17: #include "StringConverter.h"
18: #include "SystemException.h"
19:
20: namespace TrueCrypt
21: {
22: wstring StringConverter::FromNumber (double number)
23: {
24: wstringstream s;
25: s << number;
26: return s.str();
27: }
28:
1.1.1.2 root 29: wstring StringConverter::FromNumber (int32 number)
1.1 root 30: {
31: wstringstream s;
32: s << number;
33: return s.str();
34: }
35:
1.1.1.2 root 36: wstring StringConverter::FromNumber (uint32 number)
1.1 root 37: {
38: wstringstream s;
39: s << number;
40: return s.str();
41: }
42:
1.1.1.2 root 43: wstring StringConverter::FromNumber (int64 number)
1.1 root 44: {
45: wstringstream s;
46: s << number;
47: return s.str();
48: }
49:
50: wstring StringConverter::FromNumber (uint64 number)
51: {
52: wstringstream s;
53: s << number;
54: return s.str();
55: }
56:
57: string StringConverter::GetTrailingNumber (const string &str)
58: {
59: size_t start = str.find_last_not_of ("0123456789");
60: if (start == string::npos)
61: return str;
62:
63: string s = str.substr (start + 1);
64: if (s.empty ())
65: throw ParameterIncorrect (SRC_POS);
66:
67: return s;
68: }
69:
70: string StringConverter::GetTypeName (const type_info &typeInfo)
71: {
72: try
73: {
74: #ifdef _MSC_VER
75: // type_info::name() leaks memory as of MS VC++ 8.0
76: string rawName (typeInfo.raw_name());
77:
78: int cut1 = (rawName.find (".?A") != string::npos) ? 4 : string::npos;
79: int cut2 = rawName.find ("@");
80: int cut3 = rawName.find ("@@");
81:
82: if (cut1 == string::npos || cut2 == string::npos || cut3 == string::npos)
83: return typeInfo.name();
84:
85: return rawName.substr (cut2 + 1, cut3 - cut2 - 1) + "::" + rawName.substr (cut1, cut2 - cut1);
86:
87: #elif defined (__GNUC__)
88: int status;
89: char *name = abi::__cxa_demangle (typeInfo.name(), nullptr, nullptr, &status);
90:
91: if (name)
92: {
93: string s (name);
94: free (name);
95: return s;
96: }
97: #endif
98: }
99: catch (...) { }
100:
101: return typeInfo.name();
102: }
103:
104: wstring StringConverter::QuoteSpaces (const wstring &str)
105: {
106: if (str.find (L' ') == string::npos)
107: return str;
108:
109: wstring escaped (L"'");
110: foreach (wchar_t c, str)
111: {
112: if (c == L'\'')
113: escaped += L'\'';
114: escaped += c;
115: }
116: return escaped + L'\'';
117: }
118:
119: vector <string> StringConverter::Split (const string &str, const string &separators, bool returnEmptyFields)
120: {
121: vector <string> elements;
122:
123: if (!returnEmptyFields)
124: {
125: size_t p = 0;
126: while ((p = str.find_first_not_of (separators, p)) != string::npos)
127: {
128: size_t end = str.find_first_of (separators, p);
129: if (end == string::npos)
130: {
131: elements.push_back (str.substr (p));
132: break;
133: }
134:
135: elements.push_back (str.substr (p, end - p));
136: p = end;
137: }
138: }
139: else
140: {
141: string element;
142: elements.push_back (element);
143: foreach (char c, str)
144: {
145: if (separators.find (c) != string::npos)
146: {
147: element.erase();
148: elements.push_back (element);
149: }
150: else
151: {
152: elements.back() += c;
153: }
154: }
155: }
156:
157: return elements;
158: }
159:
160: wstring StringConverter::ToExceptionString (const exception &ex)
161: {
162: const SystemException *sysEx = dynamic_cast <const SystemException *> (&ex);
163: if (sysEx)
164: return ToWide (sysEx->what()) + L": " + sysEx->SystemText() + L": " + sysEx->GetSubject();
165:
166: if (ex.what() && !string (ex.what()).empty())
167: return ToWide (GetTypeName (typeid (ex)) + ": " + ex.what());
168:
169: return ToWide (GetTypeName (typeid (ex)));
170: }
171:
1.1.1.3 ! root 172: string StringConverter::ToLower (const string &str)
! 173: {
! 174: string s;
! 175: foreach (char c, str)
! 176: s += tolower (c, locale());
! 177: return s;
! 178: }
! 179:
1.1 root 180: string StringConverter::ToSingle (const wstring &str, bool noThrow)
181: {
182: try
183: {
184: mbstate_t mbState;
185: Memory::Zero (&mbState, sizeof (mbState));
186: const wchar_t *src = str.c_str();
187:
188: size_t size = wcsrtombs (nullptr, &src, 0, &mbState);
189: if (size == -1)
190: throw StringConversionFailed (SRC_POS, str);
191:
192: vector <char> buf (size + 1);
193: Memory::Zero (&mbState, sizeof (mbState));
194:
195: if ((size = wcsrtombs (&buf[0], &src, buf.size(), &mbState)) == -1)
196: throw StringConversionFailed (SRC_POS, str);
197:
198: string s;
199: s.insert (s.begin(), buf.begin(), buf.begin() + size);
200: return s;
201: }
202: catch (...)
203: {
204: if (noThrow)
205: return "";
206: throw;
207: }
208: }
209:
210: uint32 StringConverter::ToUInt32 (const string &str)
211: {
212: uint32 n;
213: stringstream ss (str);
214:
215: ss >> n;
216: if (ss.fail() || n == 0xffffFFFFU)
217: throw ParameterIncorrect (SRC_POS);
218:
219: return n;
220: }
221:
222: uint32 StringConverter::ToUInt32 (const wstring &str)
223: {
224: uint32 n;
225: wstringstream ss (str);
226:
227: ss >> n;
228: if (ss.fail() || n == 0xffffFFFFU)
229: throw ParameterIncorrect (SRC_POS);
230:
231: return n;
232: }
233:
234: uint64 StringConverter::ToUInt64 (const string &str)
235: {
236: uint64 n;
237: stringstream ss (str);
238:
239: ss >> n;
240: if (ss.fail() || n == 0xffffFFFFffffFFFFULL)
241: throw ParameterIncorrect (SRC_POS);
242:
243: return n;
244: }
245:
246: uint64 StringConverter::ToUInt64 (const wstring &str)
247: {
248: uint64 n;
249: wstringstream ss (str);
250:
251: ss >> n;
252: if (ss.fail() || n == 0xffffFFFFffffFFFFULL)
253: throw ParameterIncorrect (SRC_POS);
254:
255: return n;
256: }
1.1.1.3 ! root 257:
! 258: string StringConverter::ToUpper (const string &str)
! 259: {
! 260: string s;
! 261: foreach (char c, str)
! 262: s += toupper (c, locale());
! 263: return s;
! 264: }
1.1 root 265:
266: wstring StringConverter::ToWide (const string &str, bool noThrow)
267: {
268: try
269: {
270: mbstate_t mbState;
271: Memory::Zero (&mbState, sizeof (mbState));
272: const char *src = str.c_str();
273:
274: size_t size = mbsrtowcs (nullptr, &src, 0, &mbState);
275: if (size == -1)
276: throw StringConversionFailed (SRC_POS);
277:
278: vector <wchar_t> buf (size + 1);
279: Memory::Zero (&mbState, sizeof (mbState));
280:
281: if ((size = mbsrtowcs (&buf[0], &src, buf.size(), &mbState)) == -1)
282: throw StringConversionFailed (SRC_POS);
283:
284: wstring s;
285: s.insert (s.begin(), buf.begin(), buf.begin() + size);
286: return s;
287: }
288: catch (...)
289: {
290: if (noThrow)
291: return L"";
292: throw;
293: }
294: }
295:
296: void StringConverter::ToWideBuffer (const wstring &str, wchar_t *buffer, size_t bufferSize)
297: {
298: if (str.length() < 1)
299: {
300: buffer[0] = 0;
301: return;
302: }
303:
304: BufferPtr (
305: (byte *) buffer,
306: bufferSize).CopyFrom (
307: ConstBufferPtr ((byte *) (wstring (str).c_str()),
308: (str.length() + 1) * sizeof (wchar_t)
309: )
310: );
311: }
312:
313: string StringConverter::Trim (const string &str)
314: {
315: size_t start = 0;
316: size_t end = str.size();
317: if (end < 1)
318: return str;
319:
320: foreach (char c, str)
321: {
322: if (c > ' ')
323: break;
324: ++start;
325: }
326:
327: foreach_reverse (char c, str)
328: {
329: if (c > ' ')
330: break;
331: --end;
332: }
333:
334: return str.substr (start, end - start);
335: }
336: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.