1 // Copyright 2017 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "third_party/blink/public/common/messaging/string_message_codec.h"
6
7 #include "base/strings/utf_string_conversions.h"
8 #include "base/test/task_environment.h"
9 #include "testing/gtest/include/gtest/gtest.h"
10 #include "v8/include/v8.h"
11
12 namespace blink {
13 namespace {
14
DecodeWithV8(const std::vector<uint8_t> & encoded)15 base::string16 DecodeWithV8(const std::vector<uint8_t>& encoded) {
16 base::test::TaskEnvironment task_environment;
17 base::string16 result;
18
19 v8::Isolate::CreateParams params;
20 params.array_buffer_allocator =
21 v8::ArrayBuffer::Allocator::NewDefaultAllocator();
22 v8::Isolate* isolate = v8::Isolate::New(params);
23 {
24 v8::HandleScope scope(isolate);
25 v8::TryCatch try_catch(isolate);
26
27 v8::Local<v8::Context> context = v8::Context::New(isolate);
28
29 v8::ValueDeserializer deserializer(isolate, encoded.data(), encoded.size());
30 deserializer.SetSupportsLegacyWireFormat(true);
31
32 EXPECT_TRUE(deserializer.ReadHeader(context).ToChecked());
33
34 v8::Local<v8::Value> value =
35 deserializer.ReadValue(context).ToLocalChecked();
36 v8::Local<v8::String> str = value->ToString(context).ToLocalChecked();
37
38 result.resize(str->Length());
39 str->Write(isolate, reinterpret_cast<uint16_t*>(&result[0]), 0,
40 result.size());
41 }
42 isolate->Dispose();
43 delete params.array_buffer_allocator;
44
45 return result;
46 }
47
EncodeWithV8(const base::string16 & message)48 std::vector<uint8_t> EncodeWithV8(const base::string16& message) {
49 base::test::TaskEnvironment task_environment;
50 std::vector<uint8_t> result;
51
52 v8::Isolate::CreateParams params;
53 params.array_buffer_allocator =
54 v8::ArrayBuffer::Allocator::NewDefaultAllocator();
55 v8::Isolate* isolate = v8::Isolate::New(params);
56 {
57 v8::HandleScope scope(isolate);
58 v8::TryCatch try_catch(isolate);
59
60 v8::Local<v8::Context> context = v8::Context::New(isolate);
61
62 v8::Local<v8::String> message_as_value =
63 v8::String::NewFromTwoByte(
64 isolate, reinterpret_cast<const uint16_t*>(message.data()),
65 v8::NewStringType::kNormal, message.size())
66 .ToLocalChecked();
67
68 v8::ValueSerializer serializer(isolate);
69 serializer.WriteHeader();
70 EXPECT_TRUE(serializer.WriteValue(context, message_as_value).ToChecked());
71
72 std::pair<uint8_t*, size_t> buffer = serializer.Release();
73 result = std::vector<uint8_t>(buffer.first, buffer.first + buffer.second);
74 free(buffer.first);
75 }
76 isolate->Dispose();
77 delete params.array_buffer_allocator;
78
79 return result;
80 }
81
TEST(StringMessageCodecTest,SelfTest_ASCII)82 TEST(StringMessageCodecTest, SelfTest_ASCII) {
83 base::string16 message = base::ASCIIToUTF16("hello");
84 base::string16 decoded;
85 EXPECT_TRUE(DecodeStringMessage(EncodeStringMessage(message), &decoded));
86 EXPECT_EQ(message, decoded);
87 }
88
TEST(StringMessageCodecTest,SelfTest_NonASCII)89 TEST(StringMessageCodecTest, SelfTest_NonASCII) {
90 base::string16 message = base::WideToUTF16(L"hello \u263A");
91 base::string16 decoded;
92 EXPECT_TRUE(DecodeStringMessage(EncodeStringMessage(message), &decoded));
93 EXPECT_EQ(message, decoded);
94 }
95
TEST(StringMessageCodecTest,SelfTest_NonASCIILongEnoughToForcePadding)96 TEST(StringMessageCodecTest, SelfTest_NonASCIILongEnoughToForcePadding) {
97 base::string16 message(200, 0x263A);
98 base::string16 decoded;
99 EXPECT_TRUE(DecodeStringMessage(EncodeStringMessage(message), &decoded));
100 EXPECT_EQ(message, decoded);
101 }
102
TEST(StringMessageCodecTest,SelfToV8Test_ASCII)103 TEST(StringMessageCodecTest, SelfToV8Test_ASCII) {
104 base::string16 message = base::ASCIIToUTF16("hello");
105 EXPECT_EQ(message, DecodeWithV8(EncodeStringMessage(message)));
106 }
107
TEST(StringMessageCodecTest,SelfToV8Test_NonASCII)108 TEST(StringMessageCodecTest, SelfToV8Test_NonASCII) {
109 base::string16 message = base::WideToUTF16(L"hello \u263A");
110 EXPECT_EQ(message, DecodeWithV8(EncodeStringMessage(message)));
111 }
112
TEST(StringMessageCodecTest,SelfToV8Test_NonASCIILongEnoughToForcePadding)113 TEST(StringMessageCodecTest, SelfToV8Test_NonASCIILongEnoughToForcePadding) {
114 base::string16 message(200, 0x263A);
115 EXPECT_EQ(message, DecodeWithV8(EncodeStringMessage(message)));
116 }
117
TEST(StringMessageCodecTest,V8ToSelfTest_ASCII)118 TEST(StringMessageCodecTest, V8ToSelfTest_ASCII) {
119 base::string16 message = base::ASCIIToUTF16("hello");
120 base::string16 decoded;
121 EXPECT_TRUE(DecodeStringMessage(EncodeWithV8(message), &decoded));
122 EXPECT_EQ(message, decoded);
123 }
124
TEST(StringMessageCodecTest,V8ToSelfTest_NonASCII)125 TEST(StringMessageCodecTest, V8ToSelfTest_NonASCII) {
126 base::string16 message = base::WideToUTF16(L"hello \u263A");
127 base::string16 decoded;
128 EXPECT_TRUE(DecodeStringMessage(EncodeWithV8(message), &decoded));
129 EXPECT_EQ(message, decoded);
130 }
131
TEST(StringMessageCodecTest,V8ToSelfTest_NonASCIILongEnoughToForcePadding)132 TEST(StringMessageCodecTest, V8ToSelfTest_NonASCIILongEnoughToForcePadding) {
133 base::string16 message(200, 0x263A);
134 base::string16 decoded;
135 EXPECT_TRUE(DecodeStringMessage(EncodeWithV8(message), &decoded));
136 EXPECT_EQ(message, decoded);
137 }
138
139 } // namespace
140 } // namespace blink
141