1 /*
2 * nghttp2 - HTTP/2 C Library
3 *
4 * Copyright (c) 2016 Tatsuhiro Tsujikawa
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining
7 * a copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sublicense, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be
15 * included in all copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 */
25 #include "base64_test.h"
26
27 #include <cstring>
28 #include <iostream>
29
30 #include "munitxx.h"
31
32 #include <nghttp2/nghttp2.h>
33
34 #include "base64.h"
35
36 using namespace std::literals;
37
38 namespace nghttp2 {
39
40 namespace {
41 const MunitTest tests[]{
42 munit_void_test(test_base64_encode),
43 munit_void_test(test_base64_decode),
44 munit_test_end(),
45 };
46 } // namespace
47
48 const MunitSuite base64_suite{
49 "/base64", tests, NULL, 1, MUNIT_SUITE_OPTION_NONE,
50 };
51
test_base64_encode(void)52 void test_base64_encode(void) {
53 {
54 std::string in = "\xff";
55 auto out = base64::encode(std::begin(in), std::end(in));
56 assert_stdstring_equal("/w==", out);
57 }
58 {
59 std::string in = "\xff\xfe";
60 auto out = base64::encode(std::begin(in), std::end(in));
61 assert_stdstring_equal("//4=", out);
62 }
63 {
64 std::string in = "\xff\xfe\xfd";
65 auto out = base64::encode(std::begin(in), std::end(in));
66 assert_stdstring_equal("//79", out);
67 }
68 {
69 std::string in = "\xff\xfe\xfd\xfc";
70 auto out = base64::encode(std::begin(in), std::end(in));
71 assert_stdstring_equal("//79/A==", out);
72 }
73 }
74
test_base64_decode(void)75 void test_base64_decode(void) {
76 BlockAllocator balloc(4096, 4096);
77 {
78 auto in = "/w=="sv;
79 auto out = base64::decode(std::begin(in), std::end(in));
80 assert_stdsv_equal("\xff"sv, out);
81 assert_stdsv_equal("\xff"sv, StringRef{base64::decode(
82 balloc, std::begin(in), std::end(in))});
83 }
84 {
85 auto in = "//4="sv;
86 auto out = base64::decode(std::begin(in), std::end(in));
87 assert_stdsv_equal("\xff\xfe"sv, out);
88 assert_stdsv_equal(
89 "\xff\xfe"sv,
90 StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
91 }
92 {
93 auto in = "//79"sv;
94 auto out = base64::decode(std::begin(in), std::end(in));
95 assert_stdsv_equal("\xff\xfe\xfd"sv, out);
96 assert_stdsv_equal(
97 "\xff\xfe\xfd"sv,
98 StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
99 }
100 {
101 auto in = "//79/A=="sv;
102 auto out = base64::decode(std::begin(in), std::end(in));
103 assert_stdsv_equal("\xff\xfe\xfd\xfc"sv, out);
104 assert_stdsv_equal(
105 "\xff\xfe\xfd\xfc"sv,
106 StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
107 }
108 {
109 // we check the number of valid input must be multiples of 4
110 auto in = "//79="sv;
111 auto out = base64::decode(std::begin(in), std::end(in));
112 assert_stdsv_equal(""sv, out);
113 assert_stdsv_equal(
114 ""sv, StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
115 }
116 {
117 // ending invalid character at the boundary of multiples of 4 is
118 // bad
119 auto in = "bmdodHRw\n"sv;
120 auto out = base64::decode(std::begin(in), std::end(in));
121 assert_stdsv_equal("", out);
122 assert_stdsv_equal(
123 ""sv, StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
124 }
125 {
126 // after seeing '=', subsequent input must be also '='.
127 auto in = "//79/A=A"sv;
128 auto out = base64::decode(std::begin(in), std::end(in));
129 assert_stdsv_equal(""sv, out);
130 assert_stdsv_equal(
131 ""sv, StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
132 }
133 {
134 // additional '=' at the end is bad
135 auto in = "//79/A======"sv;
136 auto out = base64::decode(std::begin(in), std::end(in));
137 assert_stdsv_equal(""sv, out);
138 assert_stdsv_equal(
139 ""sv, StringRef{base64::decode(balloc, std::begin(in), std::end(in))});
140 }
141 }
142
143 } // namespace nghttp2
144