xref: /aosp_15_r20/external/cronet/net/third_party/quiche/src/quiche/common/test_tools/quiche_test_utils.cc (revision 6777b5387eb2ff775bb5750e3f5d96f37fb7352b)
1 // Copyright (c) 2020 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 "quiche/common/test_tools/quiche_test_utils.h"
6 
7 #include <string>
8 
9 #include "quiche/common/platform/api/quiche_googleurl.h"
10 #include "quiche/common/platform/api/quiche_logging.h"
11 #include "quiche/common/platform/api/quiche_test.h"
12 
13 namespace {
14 
HexDumpWithMarks(const char * data,int length,const bool * marks,int mark_length)15 std::string HexDumpWithMarks(const char* data, int length, const bool* marks,
16                              int mark_length) {
17   static const char kHexChars[] = "0123456789abcdef";
18   static const int kColumns = 4;
19 
20   const int kSizeLimit = 1024;
21   if (length > kSizeLimit || mark_length > kSizeLimit) {
22     QUICHE_LOG(ERROR) << "Only dumping first " << kSizeLimit << " bytes.";
23     length = std::min(length, kSizeLimit);
24     mark_length = std::min(mark_length, kSizeLimit);
25   }
26 
27   std::string hex;
28   for (const char* row = data; length > 0;
29        row += kColumns, length -= kColumns) {
30     for (const char* p = row; p < row + 4; ++p) {
31       if (p < row + length) {
32         const bool mark =
33             (marks && (p - data) < mark_length && marks[p - data]);
34         hex += mark ? '*' : ' ';
35         hex += kHexChars[(*p & 0xf0) >> 4];
36         hex += kHexChars[*p & 0x0f];
37         hex += mark ? '*' : ' ';
38       } else {
39         hex += "    ";
40       }
41     }
42     hex = hex + "  ";
43 
44     for (const char* p = row; p < row + 4 && p < row + length; ++p) {
45       hex += (*p >= 0x20 && *p < 0x7f) ? (*p) : '.';
46     }
47 
48     hex = hex + '\n';
49   }
50   return hex;
51 }
52 
53 }  // namespace
54 
55 namespace quiche {
56 namespace test {
57 
CompareCharArraysWithHexError(const std::string & description,const char * actual,const int actual_len,const char * expected,const int expected_len)58 void CompareCharArraysWithHexError(const std::string& description,
59                                    const char* actual, const int actual_len,
60                                    const char* expected,
61                                    const int expected_len) {
62   EXPECT_EQ(actual_len, expected_len);
63   const int min_len = std::min(actual_len, expected_len);
64   const int max_len = std::max(actual_len, expected_len);
65   std::unique_ptr<bool[]> marks(new bool[max_len]);
66   bool identical = (actual_len == expected_len);
67   for (int i = 0; i < min_len; ++i) {
68     if (actual[i] != expected[i]) {
69       marks[i] = true;
70       identical = false;
71     } else {
72       marks[i] = false;
73     }
74   }
75   for (int i = min_len; i < max_len; ++i) {
76     marks[i] = true;
77   }
78   if (identical) return;
79   ADD_FAILURE() << "Description:\n"
80                 << description << "\n\nExpected:\n"
81                 << HexDumpWithMarks(expected, expected_len, marks.get(),
82                                     max_len)
83                 << "\nActual:\n"
84                 << HexDumpWithMarks(actual, actual_len, marks.get(), max_len);
85 }
86 
MakeIOVector(absl::string_view str)87 iovec MakeIOVector(absl::string_view str) {
88   return iovec{const_cast<char*>(str.data()), static_cast<size_t>(str.size())};
89 }
90 
GoogleUrlSupportsIdnaForTest()91 bool GoogleUrlSupportsIdnaForTest() {
92   const std::string kTestInput = "https://\xe5\x85\x89.example.org/";
93   const std::string kExpectedOutput = "https://xn--54q.example.org/";
94 
95   GURL url(kTestInput);
96   bool valid = url.is_valid() && url.spec() == kExpectedOutput;
97   QUICHE_CHECK(valid || !url.is_valid()) << url.spec();
98   return valid;
99 }
100 
101 }  // namespace test
102 }  // namespace quiche
103