]> gitweb.ps.run Git - toc/blob - antlr4-cpp-runtime-4.9.2-source/runtime/src/support/StringUtils.h
add antlr source code and ReadMe
[toc] / antlr4-cpp-runtime-4.9.2-source / runtime / src / support / StringUtils.h
1 /* Copyright (c) 2012-2017 The ANTLR Project. All rights reserved.
2  * Use of this file is governed by the BSD 3-clause license that
3  * can be found in the LICENSE.txt file in the project root.
4  */
5
6 #pragma once
7
8 #include "antlr4-common.h"
9
10 #ifdef USE_UTF8_INSTEAD_OF_CODECVT
11 #include "utf8.h"
12 #endif
13
14 namespace antlrcpp {
15
16   // For all conversions utf8 <-> utf32.
17   // I wouldn't prefer wstring_convert because: according to
18   // https://en.cppreference.com/w/cpp/locale/wstring_convert,
19   // wstring_convert is deprecated in C++17.
20   // utfcpp (https://github.com/nemtrif/utfcpp) is a substitution.
21 #ifndef USE_UTF8_INSTEAD_OF_CODECVT
22   // VS 2015 and VS 2017 have different bugs in std::codecvt_utf8<char32_t> (VS 2013 works fine).
23   #if defined(_MSC_VER) && _MSC_VER >= 1900 && _MSC_VER < 2000
24     typedef std::wstring_convert<std::codecvt_utf8<__int32>, __int32> UTF32Converter;
25   #else
26     typedef std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> UTF32Converter;
27   #endif
28 #endif
29
30   // The conversion functions fails in VS2017, so we explicitly use a workaround.
31   template<typename T>
32   inline std::string utf32_to_utf8(T const& data)
33   {
34     #ifndef USE_UTF8_INSTEAD_OF_CODECVT
35       // Don't make the converter static or we have to serialize access to it.
36       thread_local UTF32Converter converter;
37
38       #if defined(_MSC_VER) && _MSC_VER >= 1900 && _MSC_VER < 2000
39         const auto p = reinterpret_cast<const int32_t *>(data.data());
40         return converter.to_bytes(p, p + data.size());
41       #else
42         return converter.to_bytes(data);
43       #endif
44     #else
45       std::string narrow;
46       utf8::utf32to8(data.begin(), data.end(), std::back_inserter(narrow));
47       return narrow;
48     #endif
49   }
50
51   inline UTF32String utf8_to_utf32(const char* first, const char* last)
52   {
53     #ifndef USE_UTF8_INSTEAD_OF_CODECVT
54       thread_local UTF32Converter converter;
55
56       #if defined(_MSC_VER) && _MSC_VER >= 1900 && _MSC_VER < 2000
57         auto r = converter.from_bytes(first, last);
58         i32string s = reinterpret_cast<const int32_t *>(r.data());
59         return s;
60       #else
61         std::u32string s = converter.from_bytes(first, last);
62         return s;
63       #endif
64     #else
65       UTF32String wide;
66       utf8::utf8to32(first, last, std::back_inserter(wide));
67       return wide;
68     #endif
69   }
70
71   void replaceAll(std::string &str, std::string const& from, std::string const& to);
72
73   // string <-> wstring conversion (UTF-16), e.g. for use with Window's wide APIs.
74   ANTLR4CPP_PUBLIC std::string ws2s(std::wstring const& wstr);
75   ANTLR4CPP_PUBLIC std::wstring s2ws(std::string const& str);
76 }