aboutsummaryrefslogtreecommitdiff
path: root/thirdparty/utfcpp/tests
diff options
context:
space:
mode:
authorPer Larsson <[email protected]>2021-11-11 15:10:08 +0100
committerPer Larsson <[email protected]>2021-11-11 15:10:08 +0100
commitb15b04b55ecfa0335c168561c61a7568538fccb8 (patch)
tree40f68a324f081746c74c423d8c478d3da6b1b4cc /thirdparty/utfcpp/tests
parentHandle batch requests asynchronously. (diff)
parentFormat fix. (diff)
downloadzen-b15b04b55ecfa0335c168561c61a7568538fccb8.tar.xz
zen-b15b04b55ecfa0335c168561c61a7568538fccb8.zip
Merge branch 'main' into zcache-batch
Diffstat (limited to 'thirdparty/utfcpp/tests')
-rw-r--r--thirdparty/utfcpp/tests/CMakeLists.txt41
-rw-r--r--thirdparty/utfcpp/tests/docker/Dockerfile5
-rw-r--r--thirdparty/utfcpp/tests/negative.cpp59
-rw-r--r--thirdparty/utfcpp/tests/test_checked_api.cpp188
-rw-r--r--thirdparty/utfcpp/tests/test_checked_iterator.cpp31
-rw-r--r--thirdparty/utfcpp/tests/test_cpp11.cpp106
-rw-r--r--thirdparty/utfcpp/tests/test_data/utf8_invalid.txtbin0 -> 20010 bytes
-rw-r--r--thirdparty/utfcpp/tests/test_unchecked_api.cpp161
-rw-r--r--thirdparty/utfcpp/tests/test_unchecked_iterator.cpp32
9 files changed, 623 insertions, 0 deletions
diff --git a/thirdparty/utfcpp/tests/CMakeLists.txt b/thirdparty/utfcpp/tests/CMakeLists.txt
new file mode 100644
index 000000000..06e0d7e9c
--- /dev/null
+++ b/thirdparty/utfcpp/tests/CMakeLists.txt
@@ -0,0 +1,41 @@
+add_executable(negative ${PROJECT_SOURCE_DIR}/tests/negative.cpp)
+add_executable(cpp11 ${PROJECT_SOURCE_DIR}/tests/test_cpp11.cpp)
+add_executable(apitests
+ ${PROJECT_SOURCE_DIR}/tests/test_checked_api.cpp
+ ${PROJECT_SOURCE_DIR}/tests/test_unchecked_api.cpp
+ ${PROJECT_SOURCE_DIR}/tests/test_checked_iterator.cpp
+ ${PROJECT_SOURCE_DIR}/tests/test_unchecked_iterator.cpp
+)
+
+add_executable(noexceptionstests
+ ${PROJECT_SOURCE_DIR}/tests/test_unchecked_api.cpp
+ ${PROJECT_SOURCE_DIR}/tests/test_unchecked_iterator.cpp
+)
+
+target_link_libraries(negative PRIVATE utf8::cpp)
+target_link_libraries(cpp11 PRIVATE
+ utf8::cpp
+ gtest_main
+ )
+target_link_libraries(apitests PRIVATE
+ utf8::cpp
+ gtest_main
+)
+
+target_link_libraries(noexceptionstests PRIVATE
+ utf8::cpp
+ gtest_main
+)
+target_compile_options(noexceptionstests PUBLIC -fno-exceptions)
+
+set_target_properties(negative
+ PROPERTIES
+ CXX_STANDARD 98
+ CXX_STANDARD_REQUIRED YES
+ CXX_EXTENSIONS NO)
+
+add_test(negative_test negative ${PROJECT_SOURCE_DIR}/tests/test_data/utf8_invalid.txt)
+add_test(cpp11_test cpp11)
+add_test(api_test apitests)
+add_test(noexceptions_test noexceptionstests)
+
diff --git a/thirdparty/utfcpp/tests/docker/Dockerfile b/thirdparty/utfcpp/tests/docker/Dockerfile
new file mode 100644
index 000000000..125a26936
--- /dev/null
+++ b/thirdparty/utfcpp/tests/docker/Dockerfile
@@ -0,0 +1,5 @@
+FROM debian:stretch-slim
+
+RUN apt-get update \
+ && apt-get install -y make g++ cmake git \
+ && rm -rf /var/lib/apt/lists/*
diff --git a/thirdparty/utfcpp/tests/negative.cpp b/thirdparty/utfcpp/tests/negative.cpp
new file mode 100644
index 000000000..f1bcc993e
--- /dev/null
+++ b/thirdparty/utfcpp/tests/negative.cpp
@@ -0,0 +1,59 @@
+#include "utf8.h"
+using namespace utf8;
+
+#include <string>
+#include <iostream>
+#include <fstream>
+#include <algorithm>
+using namespace std;
+
+const unsigned INVALID_LINES[] = { 75, 76, 83, 84, 85, 93, 102, 103, 105, 106, 107, 108, 109, 110, 114, 115, 116, 117, 124, 125, 130, 135, 140, 145, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 169, 175, 176, 177, 207, 208, 209, 210, 211, 220, 221, 222, 223, 224, 232, 233, 234, 235, 236, 247, 248, 249, 250, 251, 252, 253, 257, 258, 259, 260, 261, 262, 263, 264};
+const unsigned* INVALID_LINES_END = INVALID_LINES + sizeof(INVALID_LINES)/sizeof(unsigned);
+
+int main(int argc, char** argv)
+{
+ string test_file_path;
+ if (argc == 2)
+ test_file_path = argv[1];
+ else {
+ cout << "Wrong number of arguments" << endl;
+ return 1;
+ }
+ // Open the test file
+ ifstream fs8(test_file_path.c_str());
+ if (!fs8.is_open()) {
+ cout << "Could not open " << test_file_path << endl;
+ return 1;
+ }
+
+ // Read it line by line
+ unsigned int line_count = 0;
+ char byte;
+ while (!fs8.eof()) {
+ string line;
+ while ((byte = static_cast<char>(fs8.get())) != '\n' && !fs8.eof())
+ line.push_back(byte);
+
+ line_count++;
+ bool expected_valid = (find(INVALID_LINES, INVALID_LINES_END, line_count) == INVALID_LINES_END);
+ // Print out lines that contain unexpected invalid UTF-8
+ if (!is_valid(line.begin(), line.end())) {
+ if (expected_valid) {
+ cout << "Unexpected invalid utf-8 at line " << line_count << '\n';
+ return 1;
+ }
+
+ // try fixing it:
+ string fixed_line;
+ replace_invalid(line.begin(), line.end(), back_inserter(fixed_line));
+ if (!is_valid(fixed_line.begin(), fixed_line.end())) {
+ cout << "replace_invalid() resulted in an invalid utf-8 at line " << line_count << '\n';
+ return 1;
+ }
+ }
+ else if (!expected_valid) {
+ cout << "Invalid utf-8 NOT detected at line " << line_count << '\n';
+ return 1;
+ }
+ }
+}
diff --git a/thirdparty/utfcpp/tests/test_checked_api.cpp b/thirdparty/utfcpp/tests/test_checked_api.cpp
new file mode 100644
index 000000000..6787da62e
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_checked_api.cpp
@@ -0,0 +1,188 @@
+#include "gtest/gtest.h"
+#include "utf8.h"
+
+#include <string>
+#include <vector>
+using namespace utf8;
+using namespace std;
+
+
+TEST(CheckedAPITests, test_append)
+{
+ unsigned char u[5] = {0,0,0,0,0};
+ append(0x0448, u);
+ EXPECT_EQ (u[0], 0xd1);
+ EXPECT_EQ (u[1], 0x88);
+ EXPECT_EQ (u[2], 0);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x65e5, u);
+ EXPECT_EQ (u[0], 0xe6);
+ EXPECT_EQ (u[1], 0x97);
+ EXPECT_EQ (u[2], 0xa5);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x3044, u);
+ EXPECT_EQ (u[0], 0xe3);
+ EXPECT_EQ (u[1], 0x81);
+ EXPECT_EQ (u[2], 0x84);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x10346, u);
+ EXPECT_EQ (u[0], 0xf0);
+ EXPECT_EQ (u[1], 0x90);
+ EXPECT_EQ (u[2], 0x8d);
+ EXPECT_EQ (u[3], 0x86);
+ EXPECT_EQ (u[4], 0);
+}
+
+TEST(CheckedAPITests, test_next)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ const char* w = twochars;
+ int cp = next(w, twochars + 6);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, twochars + 3);
+
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ w = threechars;
+
+ cp = next(w, threechars + 9);
+ EXPECT_EQ (cp, 0x10346);
+ EXPECT_EQ (w, threechars + 4);
+
+ cp = next(w, threechars + 9);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, threechars + 7);
+
+ cp = next(w, threechars + 9);
+ EXPECT_EQ (cp, 0x0448);
+ EXPECT_EQ (w, threechars + 9);
+}
+
+TEST(CheckedAPITests, test_peek_next)
+{
+ const char* const cw = "\xe6\x97\xa5\xd1\x88";
+ int cp = peek_next(cw, cw + 6);
+ EXPECT_EQ (cp, 0x65e5);
+}
+
+TEST(CheckedAPITests, test_prior)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ const char* w = twochars + 3;
+ int cp = prior (w, twochars);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, twochars);
+
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ w = threechars + 9;
+ cp = prior(w, threechars);
+ EXPECT_EQ (cp, 0x0448);
+ EXPECT_EQ (w, threechars + 7);
+ cp = prior(w, threechars);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, threechars + 4);
+ cp = prior(w, threechars);
+ EXPECT_EQ (cp, 0x10346);
+ EXPECT_EQ (w, threechars);
+}
+
+TEST(CheckedAPITests, test_advance)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ const char* w = threechars;
+ advance(w, 2, threechars + 9);
+ EXPECT_EQ(w, threechars + 7);
+ advance(w, -2, threechars);
+ EXPECT_EQ(w, threechars);
+ advance(w, 3, threechars + 9);
+ EXPECT_EQ(w, threechars + 9);
+ advance(w, -2, threechars);
+ EXPECT_EQ(w, threechars + 4);
+ advance(w, -1, threechars);
+ EXPECT_EQ(w, threechars);
+}
+
+TEST(CheckedAPITests, test_distance)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ size_t dist = utf8::distance(twochars, twochars + 5);
+ EXPECT_EQ (dist, 2);
+}
+
+TEST(CheckedAPITests, test_utf32to8)
+{
+ int utf32string[] = {0x448, 0x65E5, 0x10346, 0};
+ string utf8result;
+ utf32to8(utf32string, utf32string + 3, back_inserter(utf8result));
+ EXPECT_EQ (utf8result.size(), 9);
+}
+
+TEST(CheckedAPITests, test_utf8to32)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ vector<int> utf32result;
+ utf8to32(twochars, twochars + 5, back_inserter(utf32result));
+ EXPECT_EQ (utf32result.size(), 2);
+}
+
+TEST(CheckedAPITests, test_utf16to8)
+{
+ unsigned short utf16string[] = {0x41, 0x0448, 0x65e5, 0xd834, 0xdd1e};
+ string utf8result;
+ utf16to8(utf16string, utf16string + 5, back_inserter(utf8result));
+ EXPECT_EQ (utf8result.size(), 10);
+}
+
+TEST(CheckedAPITests, test_utf8to16)
+{
+ char utf8_with_surrogates[] = "\xe6\x97\xa5\xd1\x88\xf0\x9d\x84\x9e";
+ vector <unsigned short> utf16result;
+ utf8to16(utf8_with_surrogates, utf8_with_surrogates + 9, back_inserter(utf16result));
+ EXPECT_EQ (utf16result.size(), 4);
+ EXPECT_EQ (utf16result[2], 0xd834);
+ EXPECT_EQ (utf16result[3], 0xdd1e);
+}
+
+TEST(CheckedAPITests, test_replace_invalid)
+{
+ char invalid_sequence[] = "a\x80\xe0\xa0\xc0\xaf\xed\xa0\x80z";
+ vector<char> replace_invalid_result;
+ replace_invalid (invalid_sequence, invalid_sequence + sizeof(invalid_sequence), std::back_inserter(replace_invalid_result), '?');
+ bool bvalid = is_valid(replace_invalid_result.begin(), replace_invalid_result.end());
+ EXPECT_TRUE (bvalid);
+ const char fixed_invalid_sequence[] = "a????z";
+ EXPECT_EQ (sizeof(fixed_invalid_sequence), replace_invalid_result.size());
+ EXPECT_TRUE (std::equal(replace_invalid_result.begin(), replace_invalid_result.begin() + sizeof(fixed_invalid_sequence), fixed_invalid_sequence));
+}
+
+TEST(CheckedAPITests, test_find_invalid)
+{
+ char utf_invalid[] = "\xe6\x97\xa5\xd1\x88\xfa";
+ char* invalid = find_invalid(utf_invalid, utf_invalid + 6);
+ EXPECT_EQ (invalid, utf_invalid + 5);
+}
+
+TEST(CheckedAPITests, test_is_valid)
+{
+ char utf_invalid[] = "\xe6\x97\xa5\xd1\x88\xfa";
+ bool bvalid = is_valid(utf_invalid, utf_invalid + 6);
+ EXPECT_FALSE (bvalid);
+ char utf8_with_surrogates[] = "\xe6\x97\xa5\xd1\x88\xf0\x9d\x84\x9e";
+ bvalid = is_valid(utf8_with_surrogates, utf8_with_surrogates + 9);
+ EXPECT_TRUE (bvalid);
+}
+
+TEST(CheckedAPITests, test_starts_with_bom)
+{
+ unsigned char byte_order_mark[] = {0xef, 0xbb, 0xbf};
+ bool bbom = starts_with_bom(byte_order_mark, byte_order_mark + sizeof(byte_order_mark));
+ EXPECT_TRUE (bbom);
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ bool no_bbom = starts_with_bom(threechars, threechars + sizeof(threechars));
+ EXPECT_FALSE (no_bbom);
+}
diff --git a/thirdparty/utfcpp/tests/test_checked_iterator.cpp b/thirdparty/utfcpp/tests/test_checked_iterator.cpp
new file mode 100644
index 000000000..4c44834fd
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_checked_iterator.cpp
@@ -0,0 +1,31 @@
+#include "gtest/gtest.h"
+#include "utf8.h"
+
+using namespace utf8;
+
+
+TEST(CheckedIteratrTests, test_increment)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ utf8::iterator<const char*> it(threechars, threechars, threechars + 9);
+ utf8::iterator<const char*> it2 = it;
+ EXPECT_EQ (it2, it);
+ EXPECT_EQ (*it, 0x10346);
+ EXPECT_EQ (*(++it), 0x65e5);
+ EXPECT_EQ ((*it++), 0x65e5);
+ EXPECT_EQ (*it, 0x0448);
+ EXPECT_NE (it, it2);
+ utf8::iterator<const char*> endit (threechars + 9, threechars, threechars + 9);
+ EXPECT_EQ (++it, endit);
+}
+
+TEST(CheckedIteratrTests, test_decrement)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ utf8::iterator<const char*> it(threechars+9, threechars, threechars + 9);
+ EXPECT_EQ (*(--it), 0x0448);
+ EXPECT_EQ ((*it--), 0x0448);
+ EXPECT_EQ (*it, 0x65e5);
+ EXPECT_EQ (--it, utf8::iterator<const char*>(threechars, threechars, threechars + 9));
+ EXPECT_EQ (*it, 0x10346);
+}
diff --git a/thirdparty/utfcpp/tests/test_cpp11.cpp b/thirdparty/utfcpp/tests/test_cpp11.cpp
new file mode 100644
index 000000000..edcff9d31
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_cpp11.cpp
@@ -0,0 +1,106 @@
+#include "gtest/gtest.h"
+#include "utf8.h"
+#include <string>
+using namespace utf8;
+using namespace std;
+
+#if __cplusplus >= 201103L // C++ 11 or later
+
+TEST(CPP11APITests, test_append)
+{
+ string u;
+ append(0x0448, u);
+ EXPECT_EQ (u[0], char(0xd1));
+ EXPECT_EQ (u[1], char(0x88));
+ EXPECT_EQ (u.length(), 2);
+
+ u.clear();
+ append(0x65e5, u);
+ EXPECT_EQ (u[0], char(0xe6));
+ EXPECT_EQ (u[1], char(0x97));
+ EXPECT_EQ (u[2], char(0xa5));
+ EXPECT_EQ (u.length(), 3);
+
+ u.clear();
+ append(0x3044, u);
+ EXPECT_EQ (u[0], char(0xe3));
+ EXPECT_EQ (u[1], char(0x81));
+ EXPECT_EQ (u[2], char(0x84));
+ EXPECT_EQ (u.length(), 3);
+
+ u.clear();
+ append(0x10346, u);
+ EXPECT_EQ (u[0], char(0xf0));
+ EXPECT_EQ (u[1], char(0x90));
+ EXPECT_EQ (u[2], char(0x8d));
+ EXPECT_EQ (u[3], char(0x86));
+ EXPECT_EQ (u.length(), 4);
+}
+
+TEST(CPP11APITests, test_utf16to8)
+{
+ u16string utf16string = {0x41, 0x0448, 0x65e5, 0xd834, 0xdd1e};
+ string u = utf16to8(utf16string);
+ EXPECT_EQ (u.size(), 10);
+}
+
+TEST(CPP11APITests, test_utf8to16)
+{
+ string utf8_with_surrogates = "\xe6\x97\xa5\xd1\x88\xf0\x9d\x84\x9e";
+ u16string utf16result = utf8to16(utf8_with_surrogates);
+ EXPECT_EQ (utf16result.size(), 4);
+ EXPECT_EQ (utf16result[2], 0xd834);
+ EXPECT_EQ (utf16result[3], 0xdd1e);
+}
+
+TEST(CPP11APITests, test_utf32to8)
+{
+ u32string utf32string = {0x448, 0x65E5, 0x10346};
+ string utf8result = utf32to8(utf32string);
+ EXPECT_EQ (utf8result.size(), 9);
+}
+
+TEST(CPP11APITests, test_utf8to32)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ u32string utf32result = utf8to32(twochars);
+ EXPECT_EQ (utf32result.size(), 2);
+}
+
+TEST(CPP11APITests, test_find_invalid)
+{
+ string utf_invalid = "\xe6\x97\xa5\xd1\x88\xfa";
+ auto invalid = find_invalid(utf_invalid);
+ EXPECT_EQ (invalid, 5);
+}
+
+TEST(CPP11APITests, test_is_valid)
+{
+ string utf_invalid = "\xe6\x97\xa5\xd1\x88\xfa";
+ bool bvalid = is_valid(utf_invalid);
+ EXPECT_FALSE (bvalid);
+ string utf8_with_surrogates = "\xe6\x97\xa5\xd1\x88\xf0\x9d\x84\x9e";
+ bvalid = is_valid(utf8_with_surrogates);
+ EXPECT_TRUE (bvalid);
+}
+
+TEST(CPP11APITests, test_replace_invalid)
+{
+ string invalid_sequence = "a\x80\xe0\xa0\xc0\xaf\xed\xa0\x80z";
+ string replace_invalid_result = replace_invalid(invalid_sequence, '?');
+ bool bvalid = is_valid(replace_invalid_result);
+ EXPECT_TRUE (bvalid);
+ const string fixed_invalid_sequence = "a????z";
+ EXPECT_EQ(fixed_invalid_sequence, replace_invalid_result);
+}
+
+TEST(CPP11APITests, test_starts_with_bom)
+{
+ string byte_order_mark = {char(0xef), char(0xbb), char(0xbf)};
+ bool bbom = starts_with_bom(byte_order_mark);
+ EXPECT_TRUE (bbom);
+ string threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ bool no_bbom = starts_with_bom(threechars);
+ EXPECT_FALSE (no_bbom);
+}
+#endif // C++ 11 or later
diff --git a/thirdparty/utfcpp/tests/test_data/utf8_invalid.txt b/thirdparty/utfcpp/tests/test_data/utf8_invalid.txt
new file mode 100644
index 000000000..ae8315932
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_data/utf8_invalid.txt
Binary files differ
diff --git a/thirdparty/utfcpp/tests/test_unchecked_api.cpp b/thirdparty/utfcpp/tests/test_unchecked_api.cpp
new file mode 100644
index 000000000..e9f19ca6c
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_unchecked_api.cpp
@@ -0,0 +1,161 @@
+#include "gtest/gtest.h"
+#include "utf8/unchecked.h"
+
+#include <string>
+#include <vector>
+using namespace utf8::unchecked;
+using namespace std;
+
+TEST(UnCheckedAPITests, test_append)
+{
+ unsigned char u[5] = {0,0,0,0,0};
+ append(0x0448, u);
+ EXPECT_EQ (u[0], 0xd1);
+ EXPECT_EQ (u[1], 0x88);
+ EXPECT_EQ (u[2], 0);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x65e5, u);
+ EXPECT_EQ (u[0], 0xe6);
+ EXPECT_EQ (u[1], 0x97);
+ EXPECT_EQ (u[2], 0xa5);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x3044, u);
+ EXPECT_EQ (u[0], 0xe3);
+ EXPECT_EQ (u[1], 0x81);
+ EXPECT_EQ (u[2], 0x84);
+ EXPECT_EQ (u[3], 0);
+ EXPECT_EQ (u[4], 0);
+
+ append(0x10346, u);
+ EXPECT_EQ (u[0], 0xf0);
+ EXPECT_EQ (u[1], 0x90);
+ EXPECT_EQ (u[2], 0x8d);
+ EXPECT_EQ (u[3], 0x86);
+ EXPECT_EQ (u[4], 0);
+}
+
+TEST(UnCheckedAPITests, test_next)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ const char* w = twochars;
+ int cp = utf8::unchecked::next(w);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, twochars + 3);
+
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ w = threechars;
+
+ cp = utf8::unchecked::next(w);
+ EXPECT_EQ (cp, 0x10346);
+ EXPECT_EQ (w, threechars + 4);
+
+ cp = utf8::unchecked::next(w);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, threechars + 7);
+
+ cp = utf8::unchecked::next(w);
+ EXPECT_EQ (cp, 0x0448);
+ EXPECT_EQ (w, threechars + 9);
+}
+
+TEST(UnCheckedAPITests, test_peek_next)
+{
+ const char* const cw = "\xe6\x97\xa5\xd1\x88";
+ int cp = peek_next(cw);
+ EXPECT_EQ (cp, 0x65e5);
+}
+
+TEST(UnCheckedAPITests, test_prior)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ const char* w = twochars + 3;
+ int cp = prior (w);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, twochars);
+
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ w = threechars + 9;
+ cp = prior(w);
+ EXPECT_EQ (cp, 0x0448);
+ EXPECT_EQ (w, threechars + 7);
+ cp = prior(w);
+ EXPECT_EQ (cp, 0x65e5);
+ EXPECT_EQ (w, threechars + 4);
+ cp = prior(w);
+ EXPECT_EQ (cp, 0x10346);
+ EXPECT_EQ (w, threechars);
+}
+
+TEST(UnCheckedAPITests, test_advance)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ const char* w = threechars;
+ utf8::unchecked::advance(w, 2);
+ EXPECT_EQ(w, threechars + 7);
+ utf8::unchecked::advance(w, -2);
+ EXPECT_EQ(w, threechars);
+ utf8::unchecked::advance(w, 3);
+ EXPECT_EQ(w, threechars + 9);
+ utf8::unchecked::advance(w, -2);
+ EXPECT_EQ(w, threechars + 4);
+ utf8::unchecked::advance(w, -1);
+ EXPECT_EQ(w, threechars);
+}
+
+TEST(UnCheckedAPITests, test_distance)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ size_t dist = utf8::unchecked::distance(twochars, twochars + 5);
+ EXPECT_EQ (dist, 2);
+}
+
+TEST(UnCheckedAPITests, test_utf32to8)
+{
+ int utf32string[] = {0x448, 0x65E5, 0x10346, 0};
+ string utf8result;
+ utf32to8(utf32string, utf32string + 3, back_inserter(utf8result));
+ EXPECT_EQ (utf8result.size(), 9);
+}
+
+TEST(UnCheckedAPITests, test_utf8to32)
+{
+ const char* twochars = "\xe6\x97\xa5\xd1\x88";
+ vector<int> utf32result;
+ utf8to32(twochars, twochars + 5, back_inserter(utf32result));
+ EXPECT_EQ (utf32result.size(), 2);
+}
+
+TEST(UnCheckedAPITests, test_utf16to8)
+{
+ unsigned short utf16string[] = {0x41, 0x0448, 0x65e5, 0xd834, 0xdd1e};
+ string utf8result;
+ utf16to8(utf16string, utf16string + 5, back_inserter(utf8result));
+ EXPECT_EQ (utf8result.size(), 10);
+}
+
+TEST(UnCheckedAPITests, test_utf8to16)
+{
+ char utf8_with_surrogates[] = "\xe6\x97\xa5\xd1\x88\xf0\x9d\x84\x9e";
+ vector <unsigned short> utf16result;
+ utf8to16(utf8_with_surrogates, utf8_with_surrogates + 9, back_inserter(utf16result));
+ EXPECT_EQ (utf16result.size(), 4);
+ EXPECT_EQ (utf16result[2], 0xd834);
+ EXPECT_EQ (utf16result[3], 0xdd1e);
+}
+
+TEST(UnCheckedAPITests, test_replace_invalid)
+{
+ char invalid_sequence[] = "a\x80\xe0\xa0\xc0\xaf\xed\xa0\x80z";
+ vector<char> replace_invalid_result;
+ replace_invalid (invalid_sequence, invalid_sequence + sizeof(invalid_sequence), std::back_inserter(replace_invalid_result), '?');
+ bool bvalid = utf8::is_valid(replace_invalid_result.begin(), replace_invalid_result.end());
+ EXPECT_TRUE (bvalid);
+ const char fixed_invalid_sequence[] = "a????z";
+ EXPECT_EQ (sizeof(fixed_invalid_sequence), replace_invalid_result.size());
+ EXPECT_TRUE (std::equal(replace_invalid_result.begin(), replace_invalid_result.begin() + sizeof(fixed_invalid_sequence), fixed_invalid_sequence));
+}
+
diff --git a/thirdparty/utfcpp/tests/test_unchecked_iterator.cpp b/thirdparty/utfcpp/tests/test_unchecked_iterator.cpp
new file mode 100644
index 000000000..103e8e28a
--- /dev/null
+++ b/thirdparty/utfcpp/tests/test_unchecked_iterator.cpp
@@ -0,0 +1,32 @@
+#include "gtest/gtest.h"
+#include "utf8/unchecked.h"
+
+using namespace utf8::unchecked;
+
+
+TEST(UnCheckedIteratrTests, test_increment)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ utf8::unchecked::iterator<const char*> it(threechars);
+ utf8::unchecked::iterator<const char*> it2 = it;
+ EXPECT_EQ (it2, it);
+ EXPECT_EQ (*it, 0x10346);
+ EXPECT_EQ (*(++it), 0x65e5);
+ EXPECT_EQ ((*it++), 0x65e5);
+ EXPECT_EQ (*it, 0x0448);
+ EXPECT_NE (it, it2);
+ utf8::unchecked::iterator<const char*> endit (threechars + 9);
+ EXPECT_EQ (++it, endit);
+}
+
+TEST(UnCheckedIteratrTests, test_decrement)
+{
+ const char* threechars = "\xf0\x90\x8d\x86\xe6\x97\xa5\xd1\x88";
+ utf8::unchecked::iterator<const char*> it(threechars+9);
+ EXPECT_EQ (*(--it), 0x0448);
+ EXPECT_EQ ((*it--), 0x0448);
+ EXPECT_EQ (*it, 0x65e5);
+ EXPECT_EQ (--it, utf8::unchecked::iterator<const char*>(threechars));
+ EXPECT_EQ (*it, 0x10346);
+
+}