1 /*
2 *
3 * Copyright 2015 gRPC authors.
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 */
18
19 /* With the addition of a libuv endpoint, sockaddr.h now includes uv.h when
20 using that endpoint. Because of various transitive includes in uv.h,
21 including windows.h on Windows, uv.h must be included before other system
22 headers. Therefore, sockaddr.h must always be included first */
23 #include "src/core/lib/iomgr/sockaddr_utils.h"
24 #include "src/core/lib/iomgr/sockaddr.h"
25 #include "src/core/lib/iomgr/socket_utils.h"
26
27 #include <errno.h>
28 #include <string.h>
29
30 #include <grpc/support/alloc.h>
31 #include <grpc/support/log.h>
32 #include <grpc/support/port_platform.h>
33 #include "test/core/util/test_config.h"
34
make_addr4(const uint8_t * data,size_t data_len)35 static grpc_resolved_address make_addr4(const uint8_t* data, size_t data_len) {
36 grpc_resolved_address resolved_addr4;
37 grpc_sockaddr_in* addr4 =
38 reinterpret_cast<grpc_sockaddr_in*>(resolved_addr4.addr);
39 memset(&resolved_addr4, 0, sizeof(resolved_addr4));
40 addr4->sin_family = GRPC_AF_INET;
41 GPR_ASSERT(data_len == sizeof(addr4->sin_addr.s_addr));
42 memcpy(&addr4->sin_addr.s_addr, data, data_len);
43 addr4->sin_port = grpc_htons(12345);
44 resolved_addr4.len = static_cast<socklen_t>(sizeof(grpc_sockaddr_in));
45 return resolved_addr4;
46 }
47
make_addr6(const uint8_t * data,size_t data_len)48 static grpc_resolved_address make_addr6(const uint8_t* data, size_t data_len) {
49 grpc_resolved_address resolved_addr6;
50 grpc_sockaddr_in6* addr6 =
51 reinterpret_cast<grpc_sockaddr_in6*>(resolved_addr6.addr);
52 memset(&resolved_addr6, 0, sizeof(resolved_addr6));
53 addr6->sin6_family = GRPC_AF_INET6;
54 GPR_ASSERT(data_len == sizeof(addr6->sin6_addr.s6_addr));
55 memcpy(&addr6->sin6_addr.s6_addr, data, data_len);
56 addr6->sin6_port = grpc_htons(12345);
57 resolved_addr6.len = static_cast<socklen_t>(sizeof(grpc_sockaddr_in6));
58 return resolved_addr6;
59 }
60
set_addr6_scope_id(grpc_resolved_address * addr,uint32_t scope_id)61 static void set_addr6_scope_id(grpc_resolved_address* addr, uint32_t scope_id) {
62 grpc_sockaddr_in6* addr6 = reinterpret_cast<grpc_sockaddr_in6*>(addr->addr);
63 GPR_ASSERT(addr6->sin6_family == GRPC_AF_INET6);
64 addr6->sin6_scope_id = scope_id;
65 }
66
67 static const uint8_t kMapped[] = {0, 0, 0, 0, 0, 0, 0, 0,
68 0, 0, 0xff, 0xff, 192, 0, 2, 1};
69
70 static const uint8_t kNotQuiteMapped[] = {0, 0, 0, 0, 0, 0, 0, 0,
71 0, 0, 0xff, 0xfe, 192, 0, 2, 99};
72 static const uint8_t kIPv4[] = {192, 0, 2, 1};
73
74 static const uint8_t kIPv6[] = {0x20, 0x01, 0x0d, 0xb8, 0, 0, 0, 0,
75 0, 0, 0, 0, 0, 0, 0, 1};
76
test_sockaddr_is_v4mapped(void)77 static void test_sockaddr_is_v4mapped(void) {
78 grpc_resolved_address input4;
79 grpc_resolved_address input6;
80 grpc_resolved_address output4;
81 grpc_resolved_address expect4;
82
83 gpr_log(GPR_INFO, "%s", "test_sockaddr_is_v4mapped");
84
85 /* v4mapped input should succeed. */
86 input6 = make_addr6(kMapped, sizeof(kMapped));
87 GPR_ASSERT(grpc_sockaddr_is_v4mapped(&input6, nullptr));
88 GPR_ASSERT(grpc_sockaddr_is_v4mapped(&input6, &output4));
89 expect4 = make_addr4(kIPv4, sizeof(kIPv4));
90 GPR_ASSERT(memcmp(&expect4, &output4, sizeof(expect4)) == 0);
91
92 /* Non-v4mapped input should fail. */
93 input6 = make_addr6(kNotQuiteMapped, sizeof(kNotQuiteMapped));
94 GPR_ASSERT(!grpc_sockaddr_is_v4mapped(&input6, nullptr));
95 GPR_ASSERT(!grpc_sockaddr_is_v4mapped(&input6, &output4));
96 /* Output is unchanged. */
97 GPR_ASSERT(memcmp(&expect4, &output4, sizeof(expect4)) == 0);
98
99 /* Plain IPv4 input should also fail. */
100 input4 = make_addr4(kIPv4, sizeof(kIPv4));
101 GPR_ASSERT(!grpc_sockaddr_is_v4mapped(&input4, nullptr));
102 }
103
test_sockaddr_to_v4mapped(void)104 static void test_sockaddr_to_v4mapped(void) {
105 grpc_resolved_address input4;
106 grpc_resolved_address input6;
107 grpc_resolved_address output6;
108 grpc_resolved_address expect6;
109
110 gpr_log(GPR_INFO, "%s", "test_sockaddr_to_v4mapped");
111
112 /* IPv4 input should succeed. */
113 input4 = make_addr4(kIPv4, sizeof(kIPv4));
114 GPR_ASSERT(grpc_sockaddr_to_v4mapped(&input4, &output6));
115 expect6 = make_addr6(kMapped, sizeof(kMapped));
116 GPR_ASSERT(memcmp(&expect6, &output6, sizeof(output6)) == 0);
117
118 /* IPv6 input should fail. */
119 input6 = make_addr6(kIPv6, sizeof(kIPv6));
120 GPR_ASSERT(!grpc_sockaddr_to_v4mapped(&input6, &output6));
121 /* Output is unchanged. */
122 GPR_ASSERT(memcmp(&expect6, &output6, sizeof(output6)) == 0);
123
124 /* Already-v4mapped input should also fail. */
125 input6 = make_addr6(kMapped, sizeof(kMapped));
126 GPR_ASSERT(!grpc_sockaddr_to_v4mapped(&input6, &output6));
127 }
128
test_sockaddr_is_wildcard(void)129 static void test_sockaddr_is_wildcard(void) {
130 grpc_resolved_address wild4;
131 grpc_resolved_address wild6;
132 grpc_resolved_address wild_mapped;
133 grpc_resolved_address dummy;
134 grpc_sockaddr_in* wild4_addr;
135 grpc_sockaddr_in6* wild6_addr;
136 grpc_sockaddr_in6* wild_mapped_addr;
137 int port;
138
139 gpr_log(GPR_INFO, "%s", "test_sockaddr_is_wildcard");
140
141 /* Generate wildcards. */
142 grpc_sockaddr_make_wildcards(555, &wild4, &wild6);
143 GPR_ASSERT(grpc_sockaddr_to_v4mapped(&wild4, &wild_mapped));
144
145 /* Test 0.0.0.0:555 */
146 port = -1;
147 GPR_ASSERT(grpc_sockaddr_is_wildcard(&wild4, &port));
148 GPR_ASSERT(port == 555);
149 wild4_addr = reinterpret_cast<grpc_sockaddr_in*>(&wild4.addr);
150 memset(&wild4_addr->sin_addr.s_addr, 0xbd, 1);
151 GPR_ASSERT(!grpc_sockaddr_is_wildcard(&wild4, &port));
152
153 /* Test [::]:555 */
154 port = -1;
155 GPR_ASSERT(grpc_sockaddr_is_wildcard(&wild6, &port));
156 GPR_ASSERT(port == 555);
157 wild6_addr = reinterpret_cast<grpc_sockaddr_in6*>(&wild6.addr);
158 memset(&wild6_addr->sin6_addr.s6_addr, 0xbd, 1);
159 GPR_ASSERT(!grpc_sockaddr_is_wildcard(&wild6, &port));
160
161 /* Test [::ffff:0.0.0.0]:555 */
162 port = -1;
163 GPR_ASSERT(grpc_sockaddr_is_wildcard(&wild_mapped, &port));
164 GPR_ASSERT(port == 555);
165 wild_mapped_addr = reinterpret_cast<grpc_sockaddr_in6*>(&wild_mapped.addr);
166 memset(&wild_mapped_addr->sin6_addr.s6_addr, 0xbd, 1);
167 GPR_ASSERT(!grpc_sockaddr_is_wildcard(&wild_mapped, &port));
168
169 /* Test AF_UNSPEC. */
170 port = -1;
171 memset(&dummy, 0, sizeof(dummy));
172 GPR_ASSERT(!grpc_sockaddr_is_wildcard(&dummy, &port));
173 GPR_ASSERT(port == -1);
174 }
175
expect_sockaddr_str(const char * expected,grpc_resolved_address * addr,int normalize)176 static void expect_sockaddr_str(const char* expected,
177 grpc_resolved_address* addr, int normalize) {
178 gpr_log(GPR_INFO, " expect_sockaddr_str(%s)", expected);
179 std::string actual = grpc_sockaddr_to_string(addr, normalize);
180 GPR_ASSERT(actual == expected);
181 }
182
expect_sockaddr_uri(const char * expected,grpc_resolved_address * addr)183 static void expect_sockaddr_uri(const char* expected,
184 grpc_resolved_address* addr) {
185 gpr_log(GPR_INFO, " expect_sockaddr_uri(%s)", expected);
186 std::string actual = grpc_sockaddr_to_uri(addr);
187 GPR_ASSERT(actual == expected);
188 }
189
test_sockaddr_to_string(void)190 static void test_sockaddr_to_string(void) {
191 grpc_resolved_address input4;
192 grpc_resolved_address input6;
193 grpc_resolved_address dummy;
194 grpc_sockaddr* dummy_addr;
195
196 gpr_log(GPR_INFO, "%s", "test_sockaddr_to_string");
197
198 errno = 0x7EADBEEF;
199
200 input4 = make_addr4(kIPv4, sizeof(kIPv4));
201 expect_sockaddr_str("192.0.2.1:12345", &input4, 0);
202 expect_sockaddr_str("192.0.2.1:12345", &input4, 1);
203 expect_sockaddr_uri("ipv4:192.0.2.1:12345", &input4);
204
205 input6 = make_addr6(kIPv6, sizeof(kIPv6));
206 expect_sockaddr_str("[2001:db8::1]:12345", &input6, 0);
207 expect_sockaddr_str("[2001:db8::1]:12345", &input6, 1);
208 expect_sockaddr_uri("ipv6:[2001:db8::1]:12345", &input6);
209
210 set_addr6_scope_id(&input6, 2);
211 expect_sockaddr_str("[2001:db8::1%252]:12345", &input6, 0);
212 expect_sockaddr_str("[2001:db8::1%252]:12345", &input6, 1);
213 expect_sockaddr_uri("ipv6:[2001:db8::1%252]:12345", &input6);
214
215 set_addr6_scope_id(&input6, 101);
216 expect_sockaddr_str("[2001:db8::1%25101]:12345", &input6, 0);
217 expect_sockaddr_str("[2001:db8::1%25101]:12345", &input6, 1);
218 expect_sockaddr_uri("ipv6:[2001:db8::1%25101]:12345", &input6);
219
220 input6 = make_addr6(kMapped, sizeof(kMapped));
221 expect_sockaddr_str("[::ffff:192.0.2.1]:12345", &input6, 0);
222 expect_sockaddr_str("192.0.2.1:12345", &input6, 1);
223 expect_sockaddr_uri("ipv4:192.0.2.1:12345", &input6);
224
225 input6 = make_addr6(kNotQuiteMapped, sizeof(kNotQuiteMapped));
226 expect_sockaddr_str("[::fffe:c000:263]:12345", &input6, 0);
227 expect_sockaddr_str("[::fffe:c000:263]:12345", &input6, 1);
228 expect_sockaddr_uri("ipv6:[::fffe:c000:263]:12345", &input6);
229
230 memset(&dummy, 0, sizeof(dummy));
231 dummy_addr = reinterpret_cast<grpc_sockaddr*>(dummy.addr);
232 dummy_addr->sa_family = 123;
233 expect_sockaddr_str("(sockaddr family=123)", &dummy, 0);
234 expect_sockaddr_str("(sockaddr family=123)", &dummy, 1);
235 GPR_ASSERT(grpc_sockaddr_to_uri(&dummy).empty());
236 }
237
test_sockaddr_set_get_port(void)238 static void test_sockaddr_set_get_port(void) {
239 grpc_resolved_address input4;
240 grpc_resolved_address input6;
241 grpc_resolved_address dummy;
242 grpc_sockaddr* dummy_addr;
243
244 gpr_log(GPR_DEBUG, "test_sockaddr_set_get_port");
245
246 input4 = make_addr4(kIPv4, sizeof(kIPv4));
247 GPR_ASSERT(grpc_sockaddr_get_port(&input4) == 12345);
248 GPR_ASSERT(grpc_sockaddr_set_port(&input4, 54321));
249 GPR_ASSERT(grpc_sockaddr_get_port(&input4) == 54321);
250
251 input6 = make_addr6(kIPv6, sizeof(kIPv6));
252 GPR_ASSERT(grpc_sockaddr_get_port(&input6) == 12345);
253 GPR_ASSERT(grpc_sockaddr_set_port(&input6, 54321));
254 GPR_ASSERT(grpc_sockaddr_get_port(&input6) == 54321);
255
256 memset(&dummy, 0, sizeof(dummy));
257 dummy_addr = reinterpret_cast<grpc_sockaddr*>(dummy.addr);
258 dummy_addr->sa_family = 123;
259 GPR_ASSERT(grpc_sockaddr_get_port(&dummy) == 0);
260 GPR_ASSERT(grpc_sockaddr_set_port(&dummy, 1234) == 0);
261 }
262
main(int argc,char ** argv)263 int main(int argc, char** argv) {
264 grpc::testing::TestEnvironment env(argc, argv);
265
266 test_sockaddr_is_v4mapped();
267 test_sockaddr_to_v4mapped();
268 test_sockaddr_is_wildcard();
269 test_sockaddr_to_string();
270 test_sockaddr_set_get_port();
271
272 return 0;
273 }
274