1 // Copyright 2016 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/http2/test_tools/hpack_example.h"
6
7 #include <ctype.h>
8
9 #include <string>
10
11 #include "absl/strings/escaping.h"
12 #include "absl/strings/str_cat.h"
13 #include "quiche/common/platform/api/quiche_bug_tracker.h"
14 #include "quiche/common/platform/api/quiche_logging.h"
15
16 namespace http2 {
17 namespace test {
18 namespace {
19
HpackExampleToStringOrDie(absl::string_view example,std::string * output)20 void HpackExampleToStringOrDie(absl::string_view example, std::string* output) {
21 while (!example.empty()) {
22 const char c0 = example[0];
23 if (isxdigit(c0)) {
24 QUICHE_CHECK_GT(example.size(), 1u) << "Truncated hex byte?";
25 const char c1 = example[1];
26 QUICHE_CHECK(isxdigit(c1)) << "Found half a byte?";
27 std::string byte;
28 QUICHE_CHECK(absl::HexStringToBytes(example.substr(0, 2), &byte))
29 << "Can't parse hex byte";
30 absl::StrAppend(output, byte);
31 example.remove_prefix(2);
32 continue;
33 }
34 if (isspace(c0)) {
35 example.remove_prefix(1);
36 continue;
37 }
38 if (!example.empty() && example[0] == '|') {
39 // Start of a comment. Skip to end of line or of input.
40 auto pos = example.find('\n');
41 if (pos == absl::string_view::npos) {
42 // End of input.
43 break;
44 }
45 example.remove_prefix(pos + 1);
46 continue;
47 }
48 QUICHE_BUG(http2_bug_107_1)
49 << "Can't parse byte " << static_cast<int>(c0)
50 << absl::StrCat(" (0x", absl::Hex(c0), ")") << "\nExample: " << example;
51 }
52 QUICHE_CHECK_LT(0u, output->size()) << "Example is empty.";
53 }
54
55 } // namespace
56
HpackExampleToStringOrDie(absl::string_view example)57 std::string HpackExampleToStringOrDie(absl::string_view example) {
58 std::string output;
59 HpackExampleToStringOrDie(example, &output);
60 return output;
61 }
62
63 } // namespace test
64 } // namespace http2
65