blob: 13bf505a1dd1664c140c65af9292a5d5c08ff607 [file] [log] [blame]
Garrick Evansf0ab7132019-06-18 14:50:42 +09001// Copyright 2019 The Chromium OS 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
Garrick Evans3388a032020-03-24 11:25:55 +09005#include "patchpanel/datapath.h"
Garrick Evansf0ab7132019-06-18 14:50:42 +09006
Garrick Evansc7ae82c2019-09-04 16:25:10 +09007#include <linux/if_tun.h>
Taoyu Li90c13912019-11-26 17:56:54 +09008#include <net/if.h>
Garrick Evansc7ae82c2019-09-04 16:25:10 +09009#include <sys/ioctl.h>
10
Garrick Evansf0ab7132019-06-18 14:50:42 +090011#include <utility>
12#include <vector>
13
Garrick Evansc7ae82c2019-09-04 16:25:10 +090014#include <base/bind.h>
Qijiang Fane90b8792020-03-09 16:15:41 +090015#include <base/bind_helpers.h>
Garrick Evansf0ab7132019-06-18 14:50:42 +090016#include <base/strings/string_util.h>
Garrick Evans8e8e3472020-01-23 14:03:50 +090017#include <gmock/gmock.h>
Garrick Evansf0ab7132019-06-18 14:50:42 +090018#include <gtest/gtest.h>
19
Jason Jeremy Imana7273a32020-08-04 11:25:31 +090020#include "patchpanel/mock_firewall.h"
Garrick Evans3388a032020-03-24 11:25:55 +090021#include "patchpanel/net_util.h"
Garrick Evansf0ab7132019-06-18 14:50:42 +090022
Garrick Evans8e8e3472020-01-23 14:03:50 +090023using testing::_;
24using testing::ElementsAre;
25using testing::Return;
26using testing::StrEq;
27
Garrick Evans3388a032020-03-24 11:25:55 +090028namespace patchpanel {
Garrick Evansc7ae82c2019-09-04 16:25:10 +090029namespace {
30
Hugo Benichi76675592020-04-08 14:29:57 +090031// TODO(hugobenichi) Centralize this constant definition
32constexpr pid_t kTestPID = -2;
33
Hugo Benichie8758b52020-04-03 14:49:01 +090034std::vector<ioctl_req_t> ioctl_reqs;
35std::vector<std::pair<std::string, struct rtentry>> ioctl_rtentry_args;
Garrick Evansc7ae82c2019-09-04 16:25:10 +090036
37// Capture all ioctls and succeed.
Taoyu Li90c13912019-11-26 17:56:54 +090038int ioctl_req_cap(int fd, ioctl_req_t req, ...) {
Hugo Benichie8758b52020-04-03 14:49:01 +090039 ioctl_reqs.push_back(req);
40 return 0;
41}
42
43// Capture ioctls for SIOCADDRT and SIOCDELRT and succeed.
44int ioctl_rtentry_cap(int fd, ioctl_req_t req, struct rtentry* arg) {
45 ioctl_reqs.push_back(req);
46 ioctl_rtentry_args.push_back({"", *arg});
47 // Copy the string poited by rtentry.rt_dev because Add/DeleteIPv4Route pass
48 // this value to ioctl() on the stack.
49 if (arg->rt_dev) {
50 auto& cap = ioctl_rtentry_args.back();
51 cap.first = std::string(arg->rt_dev);
52 cap.second.rt_dev = (char*)cap.first.c_str();
53 }
Garrick Evansc7ae82c2019-09-04 16:25:10 +090054 return 0;
55}
56
57} // namespace
58
Garrick Evans8e8e3472020-01-23 14:03:50 +090059class MockProcessRunner : public MinijailedProcessRunner {
60 public:
61 MockProcessRunner() = default;
62 ~MockProcessRunner() = default;
63
Garrick Evans2470caa2020-03-04 14:15:41 +090064 MOCK_METHOD1(WriteSentinelToContainer, int(pid_t pid));
Garrick Evans8e8e3472020-01-23 14:03:50 +090065 MOCK_METHOD3(brctl,
66 int(const std::string& cmd,
67 const std::vector<std::string>& argv,
68 bool log_failures));
69 MOCK_METHOD4(chown,
70 int(const std::string& uid,
71 const std::string& gid,
72 const std::string& file,
73 bool log_failures));
Garrick Evans8e8e3472020-01-23 14:03:50 +090074 MOCK_METHOD4(ip,
75 int(const std::string& obj,
76 const std::string& cmd,
77 const std::vector<std::string>& args,
78 bool log_failures));
79 MOCK_METHOD4(ip6,
80 int(const std::string& obj,
81 const std::string& cmd,
82 const std::vector<std::string>& args,
83 bool log_failures));
Jie Jiangcf5ce9c2020-07-14 17:22:03 +090084 MOCK_METHOD4(iptables,
Garrick Evans8e8e3472020-01-23 14:03:50 +090085 int(const std::string& table,
86 const std::vector<std::string>& argv,
Jie Jiangcf5ce9c2020-07-14 17:22:03 +090087 bool log_failures,
88 std::string* output));
89 MOCK_METHOD4(ip6tables,
Garrick Evans8e8e3472020-01-23 14:03:50 +090090 int(const std::string& table,
91 const std::vector<std::string>& argv,
Jie Jiangcf5ce9c2020-07-14 17:22:03 +090092 bool log_failures,
93 std::string* output));
Garrick Evans8e8e3472020-01-23 14:03:50 +090094 MOCK_METHOD2(modprobe_all,
95 int(const std::vector<std::string>& modules, bool log_failures));
96 MOCK_METHOD3(sysctl_w,
97 int(const std::string& key,
98 const std::string& value,
99 bool log_failures));
Hugo Benichi33860d72020-07-09 16:34:01 +0900100 MOCK_METHOD3(ip_netns_attach,
101 int(const std::string& netns_name,
102 pid_t netns_pid,
103 bool log_failures));
104 MOCK_METHOD2(ip_netns_delete,
105 int(const std::string& netns_name, bool log_failures));
Garrick Evans8e8e3472020-01-23 14:03:50 +0900106};
107
Hugo Benichid82d8832020-08-14 10:05:03 +0900108TEST(DatapathTest, IpFamily) {
109 EXPECT_EQ(IpFamily::Dual, IpFamily::IPv4 | IpFamily::IPv6);
110 EXPECT_EQ(IpFamily::Dual & IpFamily::IPv4, IpFamily::IPv4);
111 EXPECT_EQ(IpFamily::Dual & IpFamily::IPv6, IpFamily::IPv6);
112 EXPECT_NE(IpFamily::Dual, IpFamily::IPv4);
113 EXPECT_NE(IpFamily::Dual, IpFamily::IPv6);
114 EXPECT_NE(IpFamily::IPv4, IpFamily::IPv6);
115}
116
Hugo Benichibf811c62020-09-07 17:30:45 +0900117TEST(DatapathTest, Start) {
118 MockProcessRunner runner;
119 MockFirewall firewall;
120 // Asserts for sysctl modifications
121 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv4.ip_forward"), StrEq("1"), true));
122 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv4.ip_local_port_range"),
123 StrEq("32768 47103"), true));
124 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv6.conf.all.forwarding"),
125 StrEq("1"), true));
126 // Asserts for AddSNATMarkRules
127 EXPECT_CALL(
128 runner,
129 iptables(StrEq("filter"),
130 ElementsAre("-A", "FORWARD", "-m", "mark", "--mark", "1/1", "-m",
131 "state", "--state", "INVALID", "-j", "DROP", "-w"),
132 true, nullptr));
133 EXPECT_CALL(runner,
134 iptables(StrEq("filter"),
135 ElementsAre("-A", "FORWARD", "-m", "mark", "--mark",
136 "1/1", "-j", "ACCEPT", "-w"),
137 true, nullptr));
138 EXPECT_CALL(runner,
139 iptables(StrEq("nat"),
140 ElementsAre("-A", "POSTROUTING", "-m", "mark", "--mark",
141 "1/1", "-j", "MASQUERADE", "-w"),
142 true, nullptr));
143 // Asserts for AddForwardEstablishedRule
144 EXPECT_CALL(runner,
145 iptables(StrEq("filter"),
146 ElementsAre("-A", "FORWARD", "-m", "state", "--state",
147 "ESTABLISHED,RELATED", "-j", "ACCEPT", "-w"),
148 true, nullptr));
149 // Asserts for AddSourceIPv4DropRule() calls.
150 EXPECT_CALL(runner,
151 iptables(StrEq("filter"),
152 ElementsAre("-I", "OUTPUT", "-o", "eth+", "-s",
153 "100.115.92.0/23", "-j", "DROP", "-w"),
154 true, nullptr));
155 EXPECT_CALL(runner,
156 iptables(StrEq("filter"),
157 ElementsAre("-I", "OUTPUT", "-o", "wlan+", "-s",
158 "100.115.92.0/23", "-j", "DROP", "-w"),
159 true, nullptr));
160 EXPECT_CALL(runner,
161 iptables(StrEq("filter"),
162 ElementsAre("-I", "OUTPUT", "-o", "mlan+", "-s",
163 "100.115.92.0/23", "-j", "DROP", "-w"),
164 true, nullptr));
165 EXPECT_CALL(runner,
166 iptables(StrEq("filter"),
167 ElementsAre("-I", "OUTPUT", "-o", "usb+", "-s",
168 "100.115.92.0/23", "-j", "DROP", "-w"),
169 true, nullptr));
170 EXPECT_CALL(runner,
171 iptables(StrEq("filter"),
172 ElementsAre("-I", "OUTPUT", "-o", "wwan+", "-s",
173 "100.115.92.0/23", "-j", "DROP", "-w"),
174 true, nullptr));
175 EXPECT_CALL(runner,
176 iptables(StrEq("filter"),
177 ElementsAre("-I", "OUTPUT", "-o", "rmnet+", "-s",
178 "100.115.92.0/23", "-j", "DROP", "-w"),
179 true, nullptr));
180 // Asserts for AddOutboundIPv4SNATMark("vmtap+")
181 EXPECT_CALL(runner,
182 iptables(StrEq("mangle"),
183 ElementsAre("-A", "PREROUTING", "-i", "vmtap+", "-j",
184 "MARK", "--set-mark", "1/1", "-w"),
185 true, nullptr));
Taoyu Li78f0c9a2020-12-25 22:58:26 +0900186 // Asserts for OUTPUT ndp connmark bypass rule
187 EXPECT_CALL(
188 runner,
189 ip6tables(StrEq("mangle"),
190 ElementsAre("-A", "OUTPUT", "-p", "icmpv6", "--icmpv6-type",
191 "router-solicitation", "-j", "ACCEPT", "-w"),
192 true, nullptr));
193 EXPECT_CALL(
194 runner,
195 ip6tables(StrEq("mangle"),
196 ElementsAre("-A", "OUTPUT", "-p", "icmpv6", "--icmpv6-type",
197 "router-advertisement", "-j", "ACCEPT", "-w"),
198 true, nullptr));
199 EXPECT_CALL(
200 runner,
201 ip6tables(StrEq("mangle"),
202 ElementsAre("-A", "OUTPUT", "-p", "icmpv6", "--icmpv6-type",
203 "neighbour-solicitation", "-j", "ACCEPT", "-w"),
204 true, nullptr));
205 EXPECT_CALL(
206 runner,
207 ip6tables(StrEq("mangle"),
208 ElementsAre("-A", "OUTPUT", "-p", "icmpv6", "--icmpv6-type",
209 "neighbour-advertisement", "-j", "ACCEPT", "-w"),
210 true, nullptr));
Hugo Benichi2a940542020-10-26 18:50:49 +0900211 // Asserts for OUTPUT CONNMARK restore rule
212 EXPECT_CALL(runner, iptables(StrEq("mangle"),
213 ElementsAre("-A", "OUTPUT", "-j", "CONNMARK",
214 "--restore-mark", "--mask",
215 "0xffff0000", "-w"),
216 true, nullptr));
217 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
218 ElementsAre("-A", "OUTPUT", "-j", "CONNMARK",
219 "--restore-mark", "--mask",
220 "0xffff0000", "-w"),
221 true, nullptr));
Hugo Benichi3a9162b2020-09-09 15:47:40 +0900222 // Asserts for apply_local_source_mark chain
223 EXPECT_CALL(runner,
224 iptables(StrEq("mangle"),
225 ElementsAre("-N", "apply_local_source_mark", "-w"), true,
226 nullptr));
227 EXPECT_CALL(runner,
228 iptables(StrEq("mangle"),
229 ElementsAre("-F", "apply_local_source_mark", "-w"), true,
230 nullptr));
231 EXPECT_CALL(runner, iptables(StrEq("mangle"),
232 ElementsAre("-A", "OUTPUT", "-j",
233 "apply_local_source_mark", "-w"),
234 true, nullptr));
235 EXPECT_CALL(
236 runner,
237 iptables(StrEq("mangle"),
238 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
239 "--uid-owner", "chronos", "-j", "MARK", "--set-mark",
240 "0x00008100/0x0000ff00", "-w"),
241 true, nullptr));
242 EXPECT_CALL(runner, iptables(StrEq("mangle"),
243 ElementsAre("-A", "apply_local_source_mark",
244 "-m", "owner", "--uid-owner",
245 "debugd", "-j", "MARK", "--set-mark",
246 "0x00008200/0x0000ff00", "-w"),
247 true, nullptr));
248 EXPECT_CALL(runner,
249 iptables(StrEq("mangle"),
250 ElementsAre("-A", "apply_local_source_mark", "-m",
251 "owner", "--uid-owner", "cups", "-j", "MARK",
252 "--set-mark", "0x00008200/0x0000ff00", "-w"),
253 true, nullptr));
254 EXPECT_CALL(
255 runner,
256 iptables(StrEq("mangle"),
257 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
258 "--uid-owner", "kerberosd", "-j", "MARK",
259 "--set-mark", "0x00008400/0x0000ff00", "-w"),
260 true, nullptr));
261 EXPECT_CALL(
262 runner,
263 iptables(StrEq("mangle"),
264 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
265 "--uid-owner", "kerberosd-exec", "-j", "MARK",
266 "--set-mark", "0x00008400/0x0000ff00", "-w"),
267 true, nullptr));
268 EXPECT_CALL(
269 runner,
270 iptables(StrEq("mangle"),
271 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
272 "--uid-owner", "tlsdate", "-j", "MARK", "--set-mark",
273 "0x00008400/0x0000ff00", "-w"),
274 true, nullptr));
275 EXPECT_CALL(
276 runner,
277 iptables(StrEq("mangle"),
278 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
279 "--uid-owner", "pluginvm", "-j", "MARK",
280 "--set-mark", "0x00008200/0x0000ff00", "-w"),
281 true, nullptr));
282 EXPECT_CALL(
283 runner,
284 iptables(StrEq("mangle"),
285 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
286 "--uid-owner", "fuse-smbfs", "-j", "MARK",
287 "--set-mark", "0x00008400/0x0000ff00", "-w"),
288 true, nullptr));
289 EXPECT_CALL(
290 runner,
291 iptables(StrEq("mangle"),
Hugo Benichi7e3b1fc2020-11-19 15:47:05 +0900292 ElementsAre("-A", "apply_local_source_mark", "-m", "cgroup",
293 "--cgroup", "0x00010001", "-j", "MARK", "--set-mark",
294 "0x00000300/0x0000ff00", "-w"),
295 true, nullptr));
296 EXPECT_CALL(
297 runner,
298 iptables(StrEq("mangle"),
Hugo Benichi3a9162b2020-09-09 15:47:40 +0900299 ElementsAre("-A", "apply_local_source_mark", "-m", "mark",
300 "--mark", "0x0/0x00003f00", "-j", "MARK",
301 "--set-mark", "0x00000400/0x00003f00", "-w"),
302 true, nullptr));
303 EXPECT_CALL(runner,
304 ip6tables(StrEq("mangle"),
305 ElementsAre("-N", "apply_local_source_mark", "-w"),
306 true, nullptr));
307 EXPECT_CALL(runner,
308 ip6tables(StrEq("mangle"),
309 ElementsAre("-F", "apply_local_source_mark", "-w"),
310 true, nullptr));
311 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
312 ElementsAre("-A", "OUTPUT", "-j",
313 "apply_local_source_mark", "-w"),
314 true, nullptr));
315 EXPECT_CALL(
316 runner,
317 ip6tables(StrEq("mangle"),
318 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
319 "--uid-owner", "debugd", "-j", "MARK", "--set-mark",
320 "0x00008200/0x0000ff00", "-w"),
321 true, nullptr));
322 EXPECT_CALL(
323 runner,
324 ip6tables(StrEq("mangle"),
325 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
326 "--uid-owner", "chronos", "-j", "MARK",
327 "--set-mark", "0x00008100/0x0000ff00", "-w"),
328 true, nullptr));
329 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
330 ElementsAre("-A", "apply_local_source_mark",
331 "-m", "owner", "--uid-owner",
332 "cups", "-j", "MARK", "--set-mark",
333 "0x00008200/0x0000ff00", "-w"),
334 true, nullptr));
335 EXPECT_CALL(
336 runner,
337 ip6tables(StrEq("mangle"),
338 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
339 "--uid-owner", "kerberosd", "-j", "MARK",
340 "--set-mark", "0x00008400/0x0000ff00", "-w"),
341 true, nullptr));
342 EXPECT_CALL(
343 runner,
344 ip6tables(StrEq("mangle"),
345 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
346 "--uid-owner", "kerberosd-exec", "-j", "MARK",
347 "--set-mark", "0x00008400/0x0000ff00", "-w"),
348 true, nullptr));
349 EXPECT_CALL(
350 runner,
351 ip6tables(StrEq("mangle"),
352 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
353 "--uid-owner", "tlsdate", "-j", "MARK",
354 "--set-mark", "0x00008400/0x0000ff00", "-w"),
355 true, nullptr));
356 EXPECT_CALL(
357 runner,
358 ip6tables(StrEq("mangle"),
359 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
360 "--uid-owner", "pluginvm", "-j", "MARK",
361 "--set-mark", "0x00008200/0x0000ff00", "-w"),
362 true, nullptr));
363 EXPECT_CALL(
364 runner,
365 ip6tables(StrEq("mangle"),
366 ElementsAre("-A", "apply_local_source_mark", "-m", "owner",
367 "--uid-owner", "fuse-smbfs", "-j", "MARK",
368 "--set-mark", "0x00008400/0x0000ff00", "-w"),
369 true, nullptr));
370 EXPECT_CALL(
371 runner,
372 ip6tables(StrEq("mangle"),
Hugo Benichi7e3b1fc2020-11-19 15:47:05 +0900373 ElementsAre("-A", "apply_local_source_mark", "-m", "cgroup",
374 "--cgroup", "0x00010001", "-j", "MARK",
375 "--set-mark", "0x00000300/0x0000ff00", "-w"),
376 true, nullptr));
377 EXPECT_CALL(
378 runner,
379 ip6tables(StrEq("mangle"),
Hugo Benichi3a9162b2020-09-09 15:47:40 +0900380 ElementsAre("-A", "apply_local_source_mark", "-m", "mark",
381 "--mark", "0x0/0x00003f00", "-j", "MARK",
382 "--set-mark", "0x00000400/0x00003f00", "-w"),
383 true, nullptr));
Hugo Benichi3ef370b2020-11-16 19:07:17 +0900384 // Asserts for apply_vpn_mark chain
385 EXPECT_CALL(runner, iptables(StrEq("mangle"),
386 ElementsAre("-N", "apply_vpn_mark", "-w"), true,
387 nullptr));
388 EXPECT_CALL(runner, iptables(StrEq("mangle"),
389 ElementsAre("-F", "apply_vpn_mark", "-w"), true,
390 nullptr));
391 EXPECT_CALL(runner, iptables(StrEq("mangle"),
392 ElementsAre("-A", "OUTPUT", "-m", "mark",
393 "--mark", "0x00008000/0x0000c000",
394 "-j", "apply_vpn_mark", "-w"),
395 true, nullptr));
396 EXPECT_CALL(runner, iptables(StrEq("mangle"),
397 ElementsAre("-A", "apply_vpn_mark", "-m", "mark",
398 "!", "--mark", "0x0/0xffff0000",
399 "-j", "ACCEPT", "-w"),
400 true, nullptr));
401 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
402 ElementsAre("-N", "apply_vpn_mark", "-w"), true,
403 nullptr));
404 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
405 ElementsAre("-F", "apply_vpn_mark", "-w"), true,
406 nullptr));
407 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
408 ElementsAre("-A", "OUTPUT", "-m", "mark",
409 "--mark", "0x00008000/0x0000c000",
410 "-j", "apply_vpn_mark", "-w"),
411 true, nullptr));
412 EXPECT_CALL(
413 runner,
414 ip6tables(StrEq("mangle"),
415 ElementsAre("-A", "apply_vpn_mark", "-m", "mark", "!", "--mark",
416 "0x0/0xffff0000", "-j", "ACCEPT", "-w"),
417 true, nullptr));
Hugo Benichibf811c62020-09-07 17:30:45 +0900418
419 Datapath datapath(&runner, &firewall);
420 datapath.Start();
421}
422
423TEST(DatapathTest, Stop) {
424 MockProcessRunner runner;
425 MockFirewall firewall;
426 // Asserts for sysctl modifications
427 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv4.ip_local_port_range"),
428 StrEq("32768 61000"), true));
429 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv6.conf.all.forwarding"),
430 StrEq("0"), true));
431 EXPECT_CALL(runner, sysctl_w(StrEq("net.ipv4.ip_forward"), StrEq("0"), true));
432 // Asserts for RemoveOutboundIPv4SNATMark("vmtap+")
433 EXPECT_CALL(runner,
434 iptables(StrEq("mangle"),
435 ElementsAre("-D", "PREROUTING", "-i", "vmtap+", "-j",
436 "MARK", "--set-mark", "1/1", "-w"),
437 true, nullptr));
438 // Asserts for RemoveForwardEstablishedRule
439 EXPECT_CALL(runner,
440 iptables(StrEq("filter"),
441 ElementsAre("-D", "FORWARD", "-m", "state", "--state",
442 "ESTABLISHED,RELATED", "-j", "ACCEPT", "-w"),
443 true, nullptr));
444 // Asserts for RemoveSNATMarkRules
445 EXPECT_CALL(
446 runner,
447 iptables(StrEq("filter"),
448 ElementsAre("-D", "FORWARD", "-m", "mark", "--mark", "1/1", "-m",
449 "state", "--state", "INVALID", "-j", "DROP", "-w"),
450 true, nullptr));
451 EXPECT_CALL(runner,
452 iptables(StrEq("filter"),
453 ElementsAre("-D", "FORWARD", "-m", "mark", "--mark",
454 "1/1", "-j", "ACCEPT", "-w"),
455 true, nullptr));
456 EXPECT_CALL(runner,
457 iptables(StrEq("nat"),
458 ElementsAre("-D", "POSTROUTING", "-m", "mark", "--mark",
459 "1/1", "-j", "MASQUERADE", "-w"),
460 true, nullptr));
461 // Asserts for RemoveSourceIPv4DropRule() calls.
462 EXPECT_CALL(runner,
463 iptables(StrEq("filter"),
464 ElementsAre("-D", "OUTPUT", "-o", "eth+", "-s",
465 "100.115.92.0/23", "-j", "DROP", "-w"),
466 true, nullptr));
467 EXPECT_CALL(runner,
468 iptables(StrEq("filter"),
469 ElementsAre("-D", "OUTPUT", "-o", "wlan+", "-s",
470 "100.115.92.0/23", "-j", "DROP", "-w"),
471 true, nullptr));
472 EXPECT_CALL(runner,
473 iptables(StrEq("filter"),
474 ElementsAre("-D", "OUTPUT", "-o", "mlan+", "-s",
475 "100.115.92.0/23", "-j", "DROP", "-w"),
476 true, nullptr));
477 EXPECT_CALL(runner,
478 iptables(StrEq("filter"),
479 ElementsAre("-D", "OUTPUT", "-o", "usb+", "-s",
480 "100.115.92.0/23", "-j", "DROP", "-w"),
481 true, nullptr));
482 EXPECT_CALL(runner,
483 iptables(StrEq("filter"),
484 ElementsAre("-D", "OUTPUT", "-o", "wwan+", "-s",
485 "100.115.92.0/23", "-j", "DROP", "-w"),
486 true, nullptr));
487 EXPECT_CALL(runner,
488 iptables(StrEq("filter"),
489 ElementsAre("-D", "OUTPUT", "-o", "rmnet+", "-s",
490 "100.115.92.0/23", "-j", "DROP", "-w"),
491 true, nullptr));
Hugo Benichi3a9162b2020-09-09 15:47:40 +0900492 // Asserts for apply_local_source_mark chain
493 EXPECT_CALL(runner, iptables(StrEq("mangle"),
494 ElementsAre("-D", "OUTPUT", "-j",
495 "apply_local_source_mark", "-w"),
496 true, nullptr));
Hugo Benichi2a940542020-10-26 18:50:49 +0900497 // Asserts for OUTPUT CONNMARK restore rule
498 EXPECT_CALL(runner, iptables(StrEq("mangle"),
499 ElementsAre("-D", "OUTPUT", "-j", "CONNMARK",
500 "--restore-mark", "--mask",
501 "0xffff0000", "-w"),
502 true, nullptr));
503 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
504 ElementsAre("-D", "OUTPUT", "-j", "CONNMARK",
505 "--restore-mark", "--mask",
506 "0xffff0000", "-w"),
507 true, nullptr));
Hugo Benichi3a9162b2020-09-09 15:47:40 +0900508 EXPECT_CALL(runner,
509 iptables(StrEq("mangle"),
510 ElementsAre("-F", "apply_local_source_mark", "-w"), true,
511 nullptr));
512 EXPECT_CALL(runner,
513 iptables(StrEq("mangle"),
514 ElementsAre("-X", "apply_local_source_mark", "-w"), true,
515 nullptr));
516 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
517 ElementsAre("-D", "OUTPUT", "-j",
518 "apply_local_source_mark", "-w"),
519 true, nullptr));
520 EXPECT_CALL(runner,
521 ip6tables(StrEq("mangle"),
522 ElementsAre("-F", "apply_local_source_mark", "-w"),
523 true, nullptr));
524 EXPECT_CALL(runner,
525 ip6tables(StrEq("mangle"),
526 ElementsAre("-X", "apply_local_source_mark", "-w"),
527 true, nullptr));
Hugo Benichi3ef370b2020-11-16 19:07:17 +0900528 // Asserts for apply_vpn_mark chain
529 EXPECT_CALL(runner, iptables(StrEq("mangle"),
530 ElementsAre("-D", "OUTPUT", "-m", "mark",
531 "--mark", "0x00008000/0x0000c000",
532 "-j", "apply_vpn_mark", "-w"),
533 true, nullptr));
534 EXPECT_CALL(runner, iptables(StrEq("mangle"),
535 ElementsAre("-F", "apply_vpn_mark", "-w"), true,
536 nullptr));
537 EXPECT_CALL(runner, iptables(StrEq("mangle"),
538 ElementsAre("-X", "apply_vpn_mark", "-w"), true,
539 nullptr));
540 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
541 ElementsAre("-D", "OUTPUT", "-m", "mark",
542 "--mark", "0x00008000/0x0000c000",
543 "-j", "apply_vpn_mark", "-w"),
544 true, nullptr));
545 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
546 ElementsAre("-F", "apply_vpn_mark", "-w"), true,
547 nullptr));
548 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
549 ElementsAre("-X", "apply_vpn_mark", "-w"), true,
550 nullptr));
Hugo Benichibf811c62020-09-07 17:30:45 +0900551
552 Datapath datapath(&runner, &firewall);
553 datapath.Stop();
554}
555
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900556TEST(DatapathTest, AddTAP) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900557 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900558 MockFirewall firewall;
559 Datapath datapath(&runner, &firewall, ioctl_req_cap);
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900560 MacAddress mac = {1, 2, 3, 4, 5, 6};
Qijiang Fane90b8792020-03-09 16:15:41 +0900561 Subnet subnet(Ipv4Addr(100, 115, 92, 4), 30, base::DoNothing());
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900562 auto addr = subnet.AllocateAtOffset(0);
Garrick Evans4f9f5572019-11-26 10:25:16 +0900563 auto ifname = datapath.AddTAP("foo0", &mac, addr.get(), "");
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900564 EXPECT_EQ(ifname, "foo0");
Hugo Benichie8758b52020-04-03 14:49:01 +0900565 std::vector<ioctl_req_t> expected = {
566 TUNSETIFF, TUNSETPERSIST, SIOCSIFADDR, SIOCSIFNETMASK,
567 SIOCSIFHWADDR, SIOCGIFFLAGS, SIOCSIFFLAGS};
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900568 EXPECT_EQ(ioctl_reqs, expected);
569 ioctl_reqs.clear();
Hugo Benichi7c342672020-09-08 09:18:14 +0900570 ioctl_rtentry_args.clear();
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900571}
572
573TEST(DatapathTest, AddTAPWithOwner) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900574 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900575 MockFirewall firewall;
576 Datapath datapath(&runner, &firewall, ioctl_req_cap);
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900577 MacAddress mac = {1, 2, 3, 4, 5, 6};
Qijiang Fane90b8792020-03-09 16:15:41 +0900578 Subnet subnet(Ipv4Addr(100, 115, 92, 4), 30, base::DoNothing());
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900579 auto addr = subnet.AllocateAtOffset(0);
Garrick Evans4f9f5572019-11-26 10:25:16 +0900580 auto ifname = datapath.AddTAP("foo0", &mac, addr.get(), "root");
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900581 EXPECT_EQ(ifname, "foo0");
Hugo Benichie8758b52020-04-03 14:49:01 +0900582 std::vector<ioctl_req_t> expected = {
583 TUNSETIFF, TUNSETPERSIST, TUNSETOWNER, SIOCSIFADDR,
584 SIOCSIFNETMASK, SIOCSIFHWADDR, SIOCGIFFLAGS, SIOCSIFFLAGS};
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900585 EXPECT_EQ(ioctl_reqs, expected);
586 ioctl_reqs.clear();
Hugo Benichi7c342672020-09-08 09:18:14 +0900587 ioctl_rtentry_args.clear();
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900588}
589
Garrick Evans621ed262019-11-13 12:28:43 +0900590TEST(DatapathTest, AddTAPNoAddrs) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900591 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900592 MockFirewall firewall;
593 Datapath datapath(&runner, &firewall, ioctl_req_cap);
Garrick Evans4f9f5572019-11-26 10:25:16 +0900594 auto ifname = datapath.AddTAP("foo0", nullptr, nullptr, "");
Garrick Evans621ed262019-11-13 12:28:43 +0900595 EXPECT_EQ(ifname, "foo0");
Hugo Benichie8758b52020-04-03 14:49:01 +0900596 std::vector<ioctl_req_t> expected = {TUNSETIFF, TUNSETPERSIST, SIOCGIFFLAGS,
597 SIOCSIFFLAGS};
Garrick Evans621ed262019-11-13 12:28:43 +0900598 EXPECT_EQ(ioctl_reqs, expected);
599 ioctl_reqs.clear();
Hugo Benichi7c342672020-09-08 09:18:14 +0900600 ioctl_rtentry_args.clear();
Garrick Evans621ed262019-11-13 12:28:43 +0900601}
602
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900603TEST(DatapathTest, RemoveTAP) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900604 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900605 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +0900606 EXPECT_CALL(runner, ip(StrEq("tuntap"), StrEq("del"),
607 ElementsAre("foo0", "mode", "tap"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900608 Datapath datapath(&runner, &firewall);
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900609 datapath.RemoveTAP("foo0");
Garrick Evansc7ae82c2019-09-04 16:25:10 +0900610}
Garrick Evansf0ab7132019-06-18 14:50:42 +0900611
Hugo Benichi33860d72020-07-09 16:34:01 +0900612TEST(DatapathTest, NetnsAttachName) {
613 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900614 MockFirewall firewall;
Hugo Benichi33860d72020-07-09 16:34:01 +0900615 EXPECT_CALL(runner, ip_netns_delete(StrEq("netns_foo"), false));
616 EXPECT_CALL(runner, ip_netns_attach(StrEq("netns_foo"), 1234, true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900617 Datapath datapath(&runner, &firewall);
Hugo Benichi33860d72020-07-09 16:34:01 +0900618 EXPECT_TRUE(datapath.NetnsAttachName("netns_foo", 1234));
619}
620
621TEST(DatapathTest, NetnsDeleteName) {
622 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900623 MockFirewall firewall;
Hugo Benichi33860d72020-07-09 16:34:01 +0900624 EXPECT_CALL(runner, ip_netns_delete(StrEq("netns_foo"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900625 Datapath datapath(&runner, &firewall);
Hugo Benichi33860d72020-07-09 16:34:01 +0900626 EXPECT_TRUE(datapath.NetnsDeleteName("netns_foo"));
627}
628
Garrick Evans8a949dc2019-07-18 16:17:53 +0900629TEST(DatapathTest, AddBridge) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900630 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900631 MockFirewall firewall;
632 Datapath datapath(&runner, &firewall);
Garrick Evans8e8e3472020-01-23 14:03:50 +0900633 EXPECT_CALL(runner, brctl(StrEq("addbr"), ElementsAre("br"), true));
Garrick Evans6f4fa3a2020-02-10 16:15:09 +0900634 EXPECT_CALL(
635 runner,
636 ip(StrEq("addr"), StrEq("add"),
637 ElementsAre("1.1.1.1/30", "brd", "1.1.1.3", "dev", "br"), true));
Garrick Evans7a1a9ee2020-01-28 11:03:57 +0900638 EXPECT_CALL(runner,
639 ip(StrEq("link"), StrEq("set"), ElementsAre("br", "up"), true));
Garrick Evans8e8e3472020-01-23 14:03:50 +0900640 EXPECT_CALL(runner, iptables(StrEq("mangle"),
641 ElementsAre("-A", "PREROUTING", "-i", "br", "-j",
Hugo Benichi6c445322020-08-12 16:46:19 +0900642 "MARK", "--set-mark", "1/1", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +0900643 true, nullptr));
Garrick Evans7a1a9ee2020-01-28 11:03:57 +0900644 datapath.AddBridge("br", Ipv4Addr(1, 1, 1, 1), 30);
Garrick Evans8a949dc2019-07-18 16:17:53 +0900645}
646
Hugo Benichi76675592020-04-08 14:29:57 +0900647TEST(DatapathTest, ConnectVethPair) {
648 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900649 MockFirewall firewall;
Hugo Benichi76675592020-04-08 14:29:57 +0900650 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("add"),
651 ElementsAre("veth_foo", "type", "veth", "peer", "name",
Hugo Benichi33860d72020-07-09 16:34:01 +0900652 "peer_foo", "netns", "netns_foo"),
Hugo Benichi76675592020-04-08 14:29:57 +0900653 true));
654 EXPECT_CALL(runner, ip(StrEq("addr"), StrEq("add"),
655 ElementsAre("100.115.92.169/30", "brd",
656 "100.115.92.171", "dev", "peer_foo"),
657 true))
658 .WillOnce(Return(0));
659 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
660 ElementsAre("dev", "peer_foo", "up", "addr",
661 "01:02:03:04:05:06", "multicast", "on"),
662 true))
663 .WillOnce(Return(0));
Hugo Benichi76675592020-04-08 14:29:57 +0900664 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
665 ElementsAre("veth_foo", "up"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900666 Datapath datapath(&runner, &firewall);
Hugo Benichi33860d72020-07-09 16:34:01 +0900667 EXPECT_TRUE(datapath.ConnectVethPair(kTestPID, "netns_foo", "veth_foo",
668 "peer_foo", {1, 2, 3, 4, 5, 6},
Hugo Benichi76675592020-04-08 14:29:57 +0900669 Ipv4Addr(100, 115, 92, 169), 30, true));
670}
671
Garrick Evans2470caa2020-03-04 14:15:41 +0900672TEST(DatapathTest, AddVirtualInterfacePair) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900673 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900674 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +0900675 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("add"),
676 ElementsAre("veth_foo", "type", "veth", "peer", "name",
Hugo Benichi33860d72020-07-09 16:34:01 +0900677 "peer_foo", "netns", "netns_foo"),
Garrick Evans8e8e3472020-01-23 14:03:50 +0900678 true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900679 Datapath datapath(&runner, &firewall);
Hugo Benichi33860d72020-07-09 16:34:01 +0900680 EXPECT_TRUE(
681 datapath.AddVirtualInterfacePair("netns_foo", "veth_foo", "peer_foo"));
Garrick Evans2470caa2020-03-04 14:15:41 +0900682}
683
684TEST(DatapathTest, ToggleInterface) {
685 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900686 MockFirewall firewall;
Garrick Evans2470caa2020-03-04 14:15:41 +0900687 EXPECT_CALL(runner,
688 ip(StrEq("link"), StrEq("set"), ElementsAre("foo", "up"), true));
Garrick Evans7a1a9ee2020-01-28 11:03:57 +0900689 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
Garrick Evans2470caa2020-03-04 14:15:41 +0900690 ElementsAre("bar", "down"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900691 Datapath datapath(&runner, &firewall);
Garrick Evans2470caa2020-03-04 14:15:41 +0900692 EXPECT_TRUE(datapath.ToggleInterface("foo", true));
693 EXPECT_TRUE(datapath.ToggleInterface("bar", false));
694}
695
696TEST(DatapathTest, ConfigureInterface) {
697 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900698 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +0900699 EXPECT_CALL(
700 runner,
Garrick Evans2470caa2020-03-04 14:15:41 +0900701 ip(StrEq("addr"), StrEq("add"),
702 ElementsAre("1.1.1.1/30", "brd", "1.1.1.3", "dev", "foo"), true))
703 .WillOnce(Return(0));
704 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
705 ElementsAre("dev", "foo", "up", "addr",
706 "02:02:02:02:02:02", "multicast", "on"),
707 true))
708 .WillOnce(Return(0));
709
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900710 Datapath datapath(&runner, &firewall);
Garrick Evans2470caa2020-03-04 14:15:41 +0900711 MacAddress mac_addr = {2, 2, 2, 2, 2, 2};
712 EXPECT_TRUE(datapath.ConfigureInterface("foo", mac_addr, Ipv4Addr(1, 1, 1, 1),
713 30, true, true));
Garrick Evans54861622019-07-19 09:05:09 +0900714}
715
716TEST(DatapathTest, RemoveInterface) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900717 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900718 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +0900719 EXPECT_CALL(runner,
720 ip(StrEq("link"), StrEq("delete"), ElementsAre("foo"), false));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900721 Datapath datapath(&runner, &firewall);
Garrick Evans54861622019-07-19 09:05:09 +0900722 datapath.RemoveInterface("foo");
Garrick Evans54861622019-07-19 09:05:09 +0900723}
724
Garrick Evans8a949dc2019-07-18 16:17:53 +0900725TEST(DatapathTest, RemoveBridge) {
Garrick Evans8e8e3472020-01-23 14:03:50 +0900726 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900727 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +0900728 EXPECT_CALL(runner, iptables(StrEq("mangle"),
729 ElementsAre("-D", "PREROUTING", "-i", "br", "-j",
Hugo Benichi6c445322020-08-12 16:46:19 +0900730 "MARK", "--set-mark", "1/1", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +0900731 true, nullptr));
Garrick Evans7a1a9ee2020-01-28 11:03:57 +0900732 EXPECT_CALL(runner,
733 ip(StrEq("link"), StrEq("set"), ElementsAre("br", "down"), true));
Garrick Evans8e8e3472020-01-23 14:03:50 +0900734 EXPECT_CALL(runner, brctl(StrEq("delbr"), ElementsAre("br"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +0900735 Datapath datapath(&runner, &firewall);
Garrick Evans8a949dc2019-07-18 16:17:53 +0900736 datapath.RemoveBridge("br");
Garrick Evans8a949dc2019-07-18 16:17:53 +0900737}
738
Hugo Benichi321f23b2020-09-25 15:42:05 +0900739TEST(DatapathTest, AddRemoveSourceIPv4DropRule) {
740 MockProcessRunner runner;
741 MockFirewall firewall;
742 EXPECT_CALL(runner,
743 iptables(StrEq("filter"),
744 ElementsAre("-I", "OUTPUT", "-o", "eth+", "-s",
745 "100.115.92.0/24", "-j", "DROP", "-w"),
746 true, nullptr));
747 EXPECT_CALL(runner,
748 iptables(StrEq("filter"),
749 ElementsAre("-D", "OUTPUT", "-o", "eth+", "-s",
750 "100.115.92.0/24", "-j", "DROP", "-w"),
751 true, nullptr));
752 Datapath datapath(&runner, &firewall);
753 datapath.AddSourceIPv4DropRule("eth+", "100.115.92.0/24");
754 datapath.RemoveSourceIPv4DropRule("eth+", "100.115.92.0/24");
755}
756
Hugo Benichi7c342672020-09-08 09:18:14 +0900757TEST(DatapathTest, StartRoutingNamespace) {
758 MockProcessRunner runner;
759 MockFirewall firewall;
760 MacAddress mac = {1, 2, 3, 4, 5, 6};
761
762 EXPECT_CALL(runner, ip_netns_delete(StrEq("netns_foo"), false));
763 EXPECT_CALL(runner, ip_netns_attach(StrEq("netns_foo"), kTestPID, true));
764 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("add"),
765 ElementsAre("arc_ns0", "type", "veth", "peer", "name",
766 "veth0", "netns", "netns_foo"),
767 true));
768 EXPECT_CALL(runner, ip(StrEq("addr"), StrEq("add"),
769 ElementsAre("100.115.92.130/30", "brd",
770 "100.115.92.131", "dev", "veth0"),
771 true))
772 .WillOnce(Return(0));
773 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
774 ElementsAre("dev", "veth0", "up", "addr",
775 "01:02:03:04:05:06", "multicast", "off"),
776 true))
777 .WillOnce(Return(0));
778 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
779 ElementsAre("arc_ns0", "up"), true));
780 EXPECT_CALL(runner, ip(StrEq("addr"), StrEq("add"),
781 ElementsAre("100.115.92.129/30", "brd",
782 "100.115.92.131", "dev", "arc_ns0"),
783 true))
784 .WillOnce(Return(0));
785 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("set"),
786 ElementsAre("dev", "arc_ns0", "up", "addr",
787 "01:02:03:04:05:06", "multicast", "off"),
788 true))
789 .WillOnce(Return(0));
790 EXPECT_CALL(runner, iptables(StrEq("filter"),
791 ElementsAre("-A", "FORWARD", "-o", "arc_ns0",
792 "-j", "ACCEPT", "-w"),
793 true, nullptr));
Hugo Benichi93306e52020-12-04 16:08:00 +0900794 EXPECT_CALL(runner, iptables(StrEq("filter"),
795 ElementsAre("-A", "FORWARD", "-i", "arc_ns0",
796 "-j", "ACCEPT", "-w"),
797 true, nullptr));
Hugo Benichi7c342672020-09-08 09:18:14 +0900798 EXPECT_CALL(runner,
799 iptables(StrEq("mangle"),
800 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0", "-j",
801 "MARK", "--set-mark", "1/1", "-w"),
802 true, nullptr));
Hugo Benichi93306e52020-12-04 16:08:00 +0900803 EXPECT_CALL(runner, iptables(StrEq("mangle"),
804 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
805 "-j", "MARK", "--set-mark",
806 "0x00000200/0x00003f00", "-w"),
807 true, nullptr));
808 EXPECT_CALL(runner, iptables(StrEq("mangle"),
809 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
810 "-j", "CONNMARK", "--restore-mark",
811 "--mask", "0xffff0000", "-w"),
812 true, nullptr));
813 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
814 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
815 "-j", "MARK", "--set-mark",
816 "0x00000200/0x00003f00", "-w"),
817 true, nullptr));
818 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
819 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
820 "-j", "CONNMARK", "--restore-mark",
821 "--mask", "0xffff0000", "-w"),
822 true, nullptr));
823 EXPECT_CALL(runner, iptables(StrEq("mangle"),
824 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
825 "-j", "apply_vpn_mark", "-w"),
826 true, nullptr));
827 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
828 ElementsAre("-A", "PREROUTING", "-i", "arc_ns0",
829 "-j", "apply_vpn_mark", "-w"),
830 true, nullptr));
Hugo Benichi7c342672020-09-08 09:18:14 +0900831
Hugo Benichifcf81022020-12-04 11:01:37 +0900832 ConnectedNamespace nsinfo = {};
833 nsinfo.pid = kTestPID;
834 nsinfo.netns_name = "netns_foo";
Hugo Benichi93306e52020-12-04 16:08:00 +0900835 nsinfo.source = TrafficSource::USER;
Hugo Benichifcf81022020-12-04 11:01:37 +0900836 nsinfo.outbound_ifname = "";
Hugo Benichi93306e52020-12-04 16:08:00 +0900837 nsinfo.route_on_vpn = true;
Hugo Benichifcf81022020-12-04 11:01:37 +0900838 nsinfo.host_ifname = "arc_ns0";
839 nsinfo.peer_ifname = "veth0";
840 nsinfo.peer_subnet = std::make_unique<Subnet>(Ipv4Addr(100, 115, 92, 128), 30,
841 base::DoNothing());
842 nsinfo.peer_mac_addr = mac;
Hugo Benichi7c342672020-09-08 09:18:14 +0900843 Datapath datapath(&runner, &firewall, (ioctl_t)ioctl_rtentry_cap);
Hugo Benichifcf81022020-12-04 11:01:37 +0900844 datapath.StartRoutingNamespace(nsinfo);
Hugo Benichi7c342672020-09-08 09:18:14 +0900845 ioctl_reqs.clear();
846 ioctl_rtentry_args.clear();
847}
848
849TEST(DatapathTest, StopRoutingNamespace) {
850 MockProcessRunner runner;
851 MockFirewall firewall;
852
853 EXPECT_CALL(runner, iptables(StrEq("filter"),
854 ElementsAre("-D", "FORWARD", "-o", "arc_ns0",
855 "-j", "ACCEPT", "-w"),
856 true, nullptr));
Hugo Benichi93306e52020-12-04 16:08:00 +0900857 EXPECT_CALL(runner, iptables(StrEq("filter"),
858 ElementsAre("-D", "FORWARD", "-i", "arc_ns0",
859 "-j", "ACCEPT", "-w"),
860 true, nullptr));
Hugo Benichi7c342672020-09-08 09:18:14 +0900861 EXPECT_CALL(runner,
862 iptables(StrEq("mangle"),
863 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0", "-j",
864 "MARK", "--set-mark", "1/1", "-w"),
865 true, nullptr));
Hugo Benichi93306e52020-12-04 16:08:00 +0900866 EXPECT_CALL(runner, iptables(StrEq("mangle"),
867 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
868 "-j", "MARK", "--set-mark",
869 "0x00000200/0x00003f00", "-w"),
870 true, nullptr));
871 EXPECT_CALL(runner, iptables(StrEq("mangle"),
872 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
873 "-j", "CONNMARK", "--restore-mark",
874 "--mask", "0xffff0000", "-w"),
875 true, nullptr));
876 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
877 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
878 "-j", "MARK", "--set-mark",
879 "0x00000200/0x00003f00", "-w"),
880 true, nullptr));
881 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
882 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
883 "-j", "CONNMARK", "--restore-mark",
884 "--mask", "0xffff0000", "-w"),
885 true, nullptr));
886 EXPECT_CALL(runner, iptables(StrEq("mangle"),
887 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
888 "-j", "apply_vpn_mark", "-w"),
889 true, nullptr));
890 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
891 ElementsAre("-D", "PREROUTING", "-i", "arc_ns0",
892 "-j", "apply_vpn_mark", "-w"),
893 true, nullptr));
Hugo Benichi7c342672020-09-08 09:18:14 +0900894 EXPECT_CALL(runner, ip_netns_delete(StrEq("netns_foo"), true));
895 EXPECT_CALL(runner, ip(StrEq("link"), StrEq("delete"), ElementsAre("arc_ns0"),
896 false));
897
Hugo Benichifcf81022020-12-04 11:01:37 +0900898 ConnectedNamespace nsinfo = {};
899 nsinfo.pid = kTestPID;
900 nsinfo.netns_name = "netns_foo";
Hugo Benichi93306e52020-12-04 16:08:00 +0900901 nsinfo.source = TrafficSource::USER;
Hugo Benichifcf81022020-12-04 11:01:37 +0900902 nsinfo.outbound_ifname = "";
Hugo Benichi93306e52020-12-04 16:08:00 +0900903 nsinfo.route_on_vpn = true;
Hugo Benichifcf81022020-12-04 11:01:37 +0900904 nsinfo.host_ifname = "arc_ns0";
905 nsinfo.peer_ifname = "veth0";
906 nsinfo.peer_subnet = std::make_unique<Subnet>(Ipv4Addr(100, 115, 92, 128), 30,
907 base::DoNothing());
Hugo Benichi7c342672020-09-08 09:18:14 +0900908 Datapath datapath(&runner, &firewall);
Hugo Benichifcf81022020-12-04 11:01:37 +0900909 datapath.StopRoutingNamespace(nsinfo);
Hugo Benichi7c342672020-09-08 09:18:14 +0900910}
911
Hugo Benichi8d622b52020-08-13 15:24:12 +0900912TEST(DatapathTest, StartRoutingDevice_Arc) {
913 MockProcessRunner runner;
914 MockFirewall firewall;
915 EXPECT_CALL(runner, iptables(StrEq("nat"),
916 ElementsAre("-A", "PREROUTING", "-i", "eth0",
917 "-m", "socket", "--nowildcard", "-j",
918 "ACCEPT", "-w"),
919 true, nullptr));
920 EXPECT_CALL(runner, iptables(StrEq("nat"),
921 ElementsAre("-A", "PREROUTING", "-i", "eth0",
922 "-p", "tcp", "-j", "DNAT",
923 "--to-destination", "1.2.3.4", "-w"),
924 true, nullptr));
925 EXPECT_CALL(runner, iptables(StrEq("nat"),
926 ElementsAre("-A", "PREROUTING", "-i", "eth0",
927 "-p", "udp", "-j", "DNAT",
928 "--to-destination", "1.2.3.4", "-w"),
929 true, nullptr));
930 EXPECT_CALL(runner, iptables(StrEq("filter"),
Hugo Benichic6ae67c2020-08-14 15:02:13 +0900931 ElementsAre("-A", "FORWARD", "-i", "eth0", "-o",
932 "arc_eth0", "-j", "ACCEPT", "-w"),
933 true, nullptr));
934 EXPECT_CALL(runner, iptables(StrEq("filter"),
935 ElementsAre("-A", "FORWARD", "-i", "arc_eth0",
936 "-o", "eth0", "-j", "ACCEPT", "-w"),
Hugo Benichi8d622b52020-08-13 15:24:12 +0900937 true, nullptr));
Hugo Benichi9be19b12020-08-14 15:33:40 +0900938 EXPECT_CALL(runner, iptables(StrEq("mangle"),
939 ElementsAre("-A", "PREROUTING", "-i", "arc_eth0",
940 "-j", "MARK", "--set-mark",
941 "0x00002000/0x00003f00", "-w"),
942 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +0900943 EXPECT_CALL(runner, iptables(StrEq("mangle"),
944 ElementsAre("-A", "PREROUTING", "-i", "arc_eth0",
945 "-j", "MARK", "--set-mark",
946 "0x03ea0000/0xffff0000", "-w"),
947 true, nullptr));
Hugo Benichi5c9c11c2020-09-15 17:25:26 +0900948 EXPECT_CALL(
949 runner,
950 ip6tables(StrEq("mangle"),
951 ElementsAre("-A", "PREROUTING", "-i", "arc_eth0", "-j", "MARK",
952 "--set-mark", "0x00002000/0x00003f00", "-w"),
953 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +0900954 EXPECT_CALL(
955 runner,
956 ip6tables(StrEq("mangle"),
957 ElementsAre("-A", "PREROUTING", "-i", "arc_eth0", "-j", "MARK",
958 "--set-mark", "0x03ea0000/0xffff0000", "-w"),
959 true, nullptr));
Hugo Benichi8d622b52020-08-13 15:24:12 +0900960
961 Datapath datapath(&runner, &firewall);
Hugo Benichiaf9d8a72020-08-26 13:28:13 +0900962 datapath.SetIfnameIndex("eth0", 2);
Hugo Benichi8d622b52020-08-13 15:24:12 +0900963 datapath.StartRoutingDevice("eth0", "arc_eth0", Ipv4Addr(1, 2, 3, 4),
Hugo Benichi93306e52020-12-04 16:08:00 +0900964 TrafficSource::ARC, false);
Hugo Benichi8d622b52020-08-13 15:24:12 +0900965}
966
967TEST(DatapathTest, StartRoutingDevice_CrosVM) {
968 MockProcessRunner runner;
969 MockFirewall firewall;
970 EXPECT_CALL(runner, iptables(StrEq("filter"),
971 ElementsAre("-A", "FORWARD", "-o", "vmtap0",
972 "-j", "ACCEPT", "-w"),
973 true, nullptr));
Hugo Benichic6ae67c2020-08-14 15:02:13 +0900974 EXPECT_CALL(runner, iptables(StrEq("filter"),
975 ElementsAre("-A", "FORWARD", "-i", "vmtap0",
976 "-j", "ACCEPT", "-w"),
977 true, nullptr));
Hugo Benichi9be19b12020-08-14 15:33:40 +0900978 EXPECT_CALL(runner, iptables(StrEq("mangle"),
979 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
980 "-j", "MARK", "--set-mark",
981 "0x00002100/0x00003f00", "-w"),
982 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +0900983 EXPECT_CALL(runner, iptables(StrEq("mangle"),
984 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
985 "-j", "CONNMARK", "--restore-mark",
986 "--mask", "0xffff0000", "-w"),
987 true, nullptr));
Hugo Benichi5c9c11c2020-09-15 17:25:26 +0900988 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
989 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
990 "-j", "MARK", "--set-mark",
991 "0x00002100/0x00003f00", "-w"),
992 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +0900993 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
994 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
995 "-j", "CONNMARK", "--restore-mark",
996 "--mask", "0xffff0000", "-w"),
997 true, nullptr));
Hugo Benichi3ef370b2020-11-16 19:07:17 +0900998 EXPECT_CALL(runner, iptables(StrEq("mangle"),
999 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
1000 "-j", "apply_vpn_mark", "-w"),
1001 true, nullptr));
1002 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1003 ElementsAre("-A", "PREROUTING", "-i", "vmtap0",
1004 "-j", "apply_vpn_mark", "-w"),
1005 true, nullptr));
Hugo Benichi8d622b52020-08-13 15:24:12 +09001006
1007 Datapath datapath(&runner, &firewall);
1008 datapath.StartRoutingDevice("", "vmtap0", Ipv4Addr(1, 2, 3, 4),
Hugo Benichi93306e52020-12-04 16:08:00 +09001009 TrafficSource::CROSVM, true);
Hugo Benichi8d622b52020-08-13 15:24:12 +09001010}
1011
1012TEST(DatapathTest, StopRoutingDevice_Arc) {
1013 MockProcessRunner runner;
1014 MockFirewall firewall;
1015 EXPECT_CALL(runner, iptables(StrEq("nat"),
1016 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1017 "-m", "socket", "--nowildcard", "-j",
1018 "ACCEPT", "-w"),
1019 true, nullptr));
1020 EXPECT_CALL(runner, iptables(StrEq("nat"),
1021 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1022 "-p", "tcp", "-j", "DNAT",
1023 "--to-destination", "1.2.3.4", "-w"),
1024 true, nullptr));
1025 EXPECT_CALL(runner, iptables(StrEq("nat"),
1026 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1027 "-p", "udp", "-j", "DNAT",
1028 "--to-destination", "1.2.3.4", "-w"),
1029 true, nullptr));
1030 EXPECT_CALL(runner, iptables(StrEq("filter"),
Hugo Benichic6ae67c2020-08-14 15:02:13 +09001031 ElementsAre("-D", "FORWARD", "-i", "eth0", "-o",
1032 "arc_eth0", "-j", "ACCEPT", "-w"),
1033 true, nullptr));
1034 EXPECT_CALL(runner, iptables(StrEq("filter"),
1035 ElementsAre("-D", "FORWARD", "-i", "arc_eth0",
1036 "-o", "eth0", "-j", "ACCEPT", "-w"),
Hugo Benichi8d622b52020-08-13 15:24:12 +09001037 true, nullptr));
Hugo Benichi9be19b12020-08-14 15:33:40 +09001038 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1039 ElementsAre("-D", "PREROUTING", "-i", "arc_eth0",
1040 "-j", "MARK", "--set-mark",
1041 "0x00002000/0x00003f00", "-w"),
1042 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +09001043 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1044 ElementsAre("-D", "PREROUTING", "-i", "arc_eth0",
1045 "-j", "MARK", "--set-mark",
1046 "0x03ea0000/0xffff0000", "-w"),
1047 true, nullptr));
Hugo Benichi5c9c11c2020-09-15 17:25:26 +09001048 EXPECT_CALL(
1049 runner,
1050 ip6tables(StrEq("mangle"),
1051 ElementsAre("-D", "PREROUTING", "-i", "arc_eth0", "-j", "MARK",
1052 "--set-mark", "0x00002000/0x00003f00", "-w"),
1053 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +09001054 EXPECT_CALL(
1055 runner,
1056 ip6tables(StrEq("mangle"),
1057 ElementsAre("-D", "PREROUTING", "-i", "arc_eth0", "-j", "MARK",
1058 "--set-mark", "0x03ea0000/0xffff0000", "-w"),
1059 true, nullptr));
Hugo Benichi8d622b52020-08-13 15:24:12 +09001060
1061 Datapath datapath(&runner, &firewall);
Hugo Benichiaf9d8a72020-08-26 13:28:13 +09001062 datapath.SetIfnameIndex("eth0", 2);
Hugo Benichi8d622b52020-08-13 15:24:12 +09001063 datapath.StopRoutingDevice("eth0", "arc_eth0", Ipv4Addr(1, 2, 3, 4),
Hugo Benichi93306e52020-12-04 16:08:00 +09001064 TrafficSource::ARC, true);
Hugo Benichi8d622b52020-08-13 15:24:12 +09001065}
1066
1067TEST(DatapathTest, StopRoutingDevice_CrosVM) {
1068 MockProcessRunner runner;
1069 MockFirewall firewall;
1070 EXPECT_CALL(runner, iptables(StrEq("filter"),
1071 ElementsAre("-D", "FORWARD", "-o", "vmtap0",
1072 "-j", "ACCEPT", "-w"),
1073 true, nullptr));
Hugo Benichic6ae67c2020-08-14 15:02:13 +09001074 EXPECT_CALL(runner, iptables(StrEq("filter"),
1075 ElementsAre("-D", "FORWARD", "-i", "vmtap0",
1076 "-j", "ACCEPT", "-w"),
1077 true, nullptr));
Hugo Benichi9be19b12020-08-14 15:33:40 +09001078 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1079 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1080 "-j", "MARK", "--set-mark",
1081 "0x00002100/0x00003f00", "-w"),
1082 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +09001083 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1084 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1085 "-j", "CONNMARK", "--restore-mark",
1086 "--mask", "0xffff0000", "-w"),
1087 true, nullptr));
Hugo Benichi5c9c11c2020-09-15 17:25:26 +09001088 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1089 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1090 "-j", "MARK", "--set-mark",
1091 "0x00002100/0x00003f00", "-w"),
1092 true, nullptr));
Hugo Benichiaf9d8a72020-08-26 13:28:13 +09001093 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1094 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1095 "-j", "CONNMARK", "--restore-mark",
1096 "--mask", "0xffff0000", "-w"),
1097 true, nullptr));
Hugo Benichi3ef370b2020-11-16 19:07:17 +09001098 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1099 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1100 "-j", "apply_vpn_mark", "-w"),
1101 true, nullptr));
1102 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1103 ElementsAre("-D", "PREROUTING", "-i", "vmtap0",
1104 "-j", "apply_vpn_mark", "-w"),
1105 true, nullptr));
Hugo Benichi8d622b52020-08-13 15:24:12 +09001106
1107 Datapath datapath(&runner, &firewall);
1108 datapath.StopRoutingDevice("", "vmtap0", Ipv4Addr(1, 2, 3, 4),
Hugo Benichi93306e52020-12-04 16:08:00 +09001109 TrafficSource::CROSVM, true);
Hugo Benichi8d622b52020-08-13 15:24:12 +09001110}
1111
Hugo Benichid82d8832020-08-14 10:05:03 +09001112TEST(DatapathTest, StartStopIpForwarding) {
1113 struct {
1114 IpFamily family;
1115 std::string iif;
1116 std::string oif;
1117 std::vector<std::string> start_args;
1118 std::vector<std::string> stop_args;
1119 bool result;
1120 } testcases[] = {
1121 {IpFamily::IPv4, "", "", {}, {}, false},
1122 {IpFamily::NONE, "foo", "bar", {}, {}, false},
1123 {IpFamily::IPv4,
1124 "foo",
1125 "bar",
1126 {"-A", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1127 {"-D", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1128 true},
1129 {IpFamily::IPv4,
1130 "",
1131 "bar",
1132 {"-A", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1133 {"-D", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1134 true},
1135 {IpFamily::IPv4,
1136 "foo",
1137 "",
1138 {"-A", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1139 {"-D", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1140 true},
1141 {IpFamily::IPv6,
1142 "foo",
1143 "bar",
1144 {"-A", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1145 {"-D", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1146 true},
1147 {IpFamily::IPv6,
1148 "",
1149 "bar",
1150 {"-A", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1151 {"-D", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1152 true},
1153 {IpFamily::IPv6,
1154 "foo",
1155 "",
1156 {"-A", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1157 {"-D", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1158 true},
1159 {IpFamily::Dual,
1160 "foo",
1161 "bar",
1162 {"-A", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1163 {"-D", "FORWARD", "-i", "foo", "-o", "bar", "-j", "ACCEPT", "-w"},
1164 true},
1165 {IpFamily::Dual,
1166 "",
1167 "bar",
1168 {"-A", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1169 {"-D", "FORWARD", "-o", "bar", "-j", "ACCEPT", "-w"},
1170 true},
1171 {IpFamily::Dual,
1172 "foo",
1173 "",
1174 {"-A", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1175 {"-D", "FORWARD", "-i", "foo", "-j", "ACCEPT", "-w"},
1176 true},
1177 };
1178
1179 for (const auto& tt : testcases) {
1180 MockProcessRunner runner;
1181 MockFirewall firewall;
1182 if (tt.result) {
1183 if (tt.family & IpFamily::IPv4) {
1184 EXPECT_CALL(runner,
1185 iptables(StrEq("filter"), tt.start_args, true, nullptr))
1186 .WillOnce(Return(0));
1187 EXPECT_CALL(runner,
1188 iptables(StrEq("filter"), tt.stop_args, true, nullptr))
1189 .WillOnce(Return(0));
1190 }
1191 if (tt.family & IpFamily::IPv6) {
1192 EXPECT_CALL(runner,
1193 ip6tables(StrEq("filter"), tt.start_args, true, nullptr))
1194 .WillOnce(Return(0));
1195 EXPECT_CALL(runner,
1196 ip6tables(StrEq("filter"), tt.stop_args, true, nullptr))
1197 .WillOnce(Return(0));
1198 }
1199 }
1200 Datapath datapath(&runner, &firewall);
1201
1202 EXPECT_EQ(tt.result, datapath.StartIpForwarding(tt.family, tt.iif, tt.oif));
1203 EXPECT_EQ(tt.result, datapath.StopIpForwarding(tt.family, tt.iif, tt.oif));
1204 }
1205}
1206
Hugo Benichi76be34a2020-08-26 22:35:54 +09001207TEST(DatapathTest, StartStopConnectionPinning) {
1208 MockProcessRunner runner;
1209 MockFirewall firewall;
Hugo Benichi1af52392020-11-27 18:09:32 +09001210
1211 // Setup
Hugo Benichi76be34a2020-08-26 22:35:54 +09001212 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1213 ElementsAre("-A", "POSTROUTING", "-o", "eth0",
1214 "-j", "CONNMARK", "--set-mark",
1215 "0x03eb0000/0xffff0000", "-w"),
1216 true, nullptr));
Hugo Benichi76be34a2020-08-26 22:35:54 +09001217 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1218 ElementsAre("-A", "POSTROUTING", "-o", "eth0",
1219 "-j", "CONNMARK", "--set-mark",
1220 "0x03eb0000/0xffff0000", "-w"),
1221 true, nullptr));
Hugo Benichi1af52392020-11-27 18:09:32 +09001222 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1223 ElementsAre("-A", "POSTROUTING", "-o", "eth0",
1224 "-j", "CONNMARK", "--save-mark",
1225 "--mask", "0x00003f00", "-w"),
1226 true, nullptr));
1227 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1228 ElementsAre("-A", "POSTROUTING", "-o", "eth0",
1229 "-j", "CONNMARK", "--save-mark",
1230 "--mask", "0x00003f00", "-w"),
1231 true, nullptr));
1232 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1233 ElementsAre("-A", "PREROUTING", "-i", "eth0",
1234 "-j", "CONNMARK", "--restore-mark",
1235 "--mask", "0x00003f00", "-w"),
1236 true, nullptr));
1237 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1238 ElementsAre("-A", "PREROUTING", "-i", "eth0",
1239 "-j", "CONNMARK", "--restore-mark",
1240 "--mask", "0x00003f00", "-w"),
1241 true, nullptr));
1242 // Teardown
1243 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1244 ElementsAre("-D", "POSTROUTING", "-o", "eth0",
1245 "-j", "CONNMARK", "--set-mark",
1246 "0x03eb0000/0xffff0000", "-w"),
1247 true, nullptr));
Hugo Benichi76be34a2020-08-26 22:35:54 +09001248 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1249 ElementsAre("-D", "POSTROUTING", "-o", "eth0",
1250 "-j", "CONNMARK", "--set-mark",
1251 "0x03eb0000/0xffff0000", "-w"),
1252 true, nullptr));
Hugo Benichi1af52392020-11-27 18:09:32 +09001253 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1254 ElementsAre("-D", "POSTROUTING", "-o", "eth0",
1255 "-j", "CONNMARK", "--save-mark",
1256 "--mask", "0x00003f00", "-w"),
1257 true, nullptr));
1258 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1259 ElementsAre("-D", "POSTROUTING", "-o", "eth0",
1260 "-j", "CONNMARK", "--save-mark",
1261 "--mask", "0x00003f00", "-w"),
1262 true, nullptr));
1263 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1264 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1265 "-j", "CONNMARK", "--restore-mark",
1266 "--mask", "0x00003f00", "-w"),
1267 true, nullptr));
1268 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1269 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1270 "-j", "CONNMARK", "--restore-mark",
1271 "--mask", "0x00003f00", "-w"),
1272 true, nullptr));
1273
Hugo Benichi76be34a2020-08-26 22:35:54 +09001274 Datapath datapath(&runner, &firewall);
1275 datapath.SetIfnameIndex("eth0", 3);
1276 datapath.StartConnectionPinning("eth0");
1277 datapath.StopConnectionPinning("eth0");
1278}
1279
Hugo Benichi2a940542020-10-26 18:50:49 +09001280TEST(DatapathTest, StartStopVpnRouting_NoVirtualDevices) {
1281 MockProcessRunner runner;
1282 MockFirewall firewall;
1283
1284 // Setup
1285 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1286 ElementsAre("-A", "POSTROUTING", "-o", "arcbr0",
1287 "-j", "CONNMARK", "--set-mark",
1288 "0x03ed0000/0xffff0000", "-w"),
1289 true, nullptr));
1290 EXPECT_CALL(runner,
1291 iptables(StrEq("mangle"),
1292 ElementsAre("-A", "apply_vpn_mark", "-j", "MARK",
1293 "--set-mark", "0x03ed0000/0xffff0000", "-w"),
1294 true, nullptr));
1295 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1296 ElementsAre("-A", "POSTROUTING", "-o", "arcbr0",
1297 "-j", "CONNMARK", "--set-mark",
1298 "0x03ed0000/0xffff0000", "-w"),
1299 true, nullptr));
1300 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1301 ElementsAre("-A", "apply_vpn_mark", "-j",
1302 "MARK", "--set-mark",
1303 "0x03ed0000/0xffff0000", "-w"),
1304 true, nullptr));
Hugo Benichi1af52392020-11-27 18:09:32 +09001305 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1306 ElementsAre("-A", "POSTROUTING", "-o", "arcbr0",
1307 "-j", "CONNMARK", "--save-mark",
1308 "--mask", "0x00003f00", "-w"),
1309 true, nullptr));
1310 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1311 ElementsAre("-A", "POSTROUTING", "-o", "arcbr0",
1312 "-j", "CONNMARK", "--save-mark",
1313 "--mask", "0x00003f00", "-w"),
1314 true, nullptr));
1315 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1316 ElementsAre("-A", "PREROUTING", "-i", "arcbr0",
1317 "-j", "CONNMARK", "--restore-mark",
1318 "--mask", "0x00003f00", "-w"),
1319 true, nullptr));
1320 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1321 ElementsAre("-A", "PREROUTING", "-i", "arcbr0",
1322 "-j", "CONNMARK", "--restore-mark",
1323 "--mask", "0x00003f00", "-w"),
1324 true, nullptr));
Hugo Benichi2a940542020-10-26 18:50:49 +09001325 // Teardown
1326 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1327 ElementsAre("-D", "POSTROUTING", "-o", "arcbr0",
1328 "-j", "CONNMARK", "--set-mark",
1329 "0x03ed0000/0xffff0000", "-w"),
1330 true, nullptr));
1331 EXPECT_CALL(runner,
1332 iptables(StrEq("mangle"),
1333 ElementsAre("-D", "apply_vpn_mark", "-j", "MARK",
1334 "--set-mark", "0x03ed0000/0xffff0000", "-w"),
1335 true, nullptr));
1336 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1337 ElementsAre("-D", "POSTROUTING", "-o", "arcbr0",
1338 "-j", "CONNMARK", "--set-mark",
1339 "0x03ed0000/0xffff0000", "-w"),
1340 true, nullptr));
1341 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1342 ElementsAre("-D", "apply_vpn_mark", "-j",
1343 "MARK", "--set-mark",
1344 "0x03ed0000/0xffff0000", "-w"),
1345 true, nullptr));
Hugo Benichi1af52392020-11-27 18:09:32 +09001346 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1347 ElementsAre("-D", "POSTROUTING", "-o", "arcbr0",
1348 "-j", "CONNMARK", "--save-mark",
1349 "--mask", "0x00003f00", "-w"),
1350 true, nullptr));
1351 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1352 ElementsAre("-D", "POSTROUTING", "-o", "arcbr0",
1353 "-j", "CONNMARK", "--save-mark",
1354 "--mask", "0x00003f00", "-w"),
1355 true, nullptr));
1356 EXPECT_CALL(runner, iptables(StrEq("mangle"),
1357 ElementsAre("-D", "PREROUTING", "-i", "arcbr0",
1358 "-j", "CONNMARK", "--restore-mark",
1359 "--mask", "0x00003f00", "-w"),
1360 true, nullptr));
1361 EXPECT_CALL(runner, ip6tables(StrEq("mangle"),
1362 ElementsAre("-D", "PREROUTING", "-i", "arcbr0",
1363 "-j", "CONNMARK", "--restore-mark",
1364 "--mask", "0x00003f00", "-w"),
1365 true, nullptr));
Hugo Benichi2a940542020-10-26 18:50:49 +09001366
1367 Datapath datapath(&runner, &firewall);
1368 datapath.SetIfnameIndex("arcbr0", 5);
1369 datapath.StartVpnRouting("arcbr0");
1370 datapath.StopVpnRouting("arcbr0");
1371}
1372
Garrick Evansf0ab7132019-06-18 14:50:42 +09001373TEST(DatapathTest, AddInboundIPv4DNAT) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001374 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001375 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +09001376 EXPECT_CALL(runner, iptables(StrEq("nat"),
1377 ElementsAre("-A", "PREROUTING", "-i", "eth0",
1378 "-m", "socket", "--nowildcard", "-j",
1379 "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001380 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001381 EXPECT_CALL(runner, iptables(StrEq("nat"),
1382 ElementsAre("-A", "PREROUTING", "-i", "eth0",
1383 "-p", "tcp", "-j", "DNAT",
1384 "--to-destination", "1.2.3.4", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001385 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001386 EXPECT_CALL(runner, iptables(StrEq("nat"),
1387 ElementsAre("-A", "PREROUTING", "-i", "eth0",
1388 "-p", "udp", "-j", "DNAT",
1389 "--to-destination", "1.2.3.4", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001390 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001391 Datapath datapath(&runner, &firewall);
Garrick Evansf0ab7132019-06-18 14:50:42 +09001392 datapath.AddInboundIPv4DNAT("eth0", "1.2.3.4");
Garrick Evansf0ab7132019-06-18 14:50:42 +09001393}
1394
1395TEST(DatapathTest, RemoveInboundIPv4DNAT) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001396 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001397 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +09001398 EXPECT_CALL(runner, iptables(StrEq("nat"),
1399 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1400 "-m", "socket", "--nowildcard", "-j",
1401 "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001402 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001403 EXPECT_CALL(runner, iptables(StrEq("nat"),
1404 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1405 "-p", "tcp", "-j", "DNAT",
1406 "--to-destination", "1.2.3.4", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001407 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001408 EXPECT_CALL(runner, iptables(StrEq("nat"),
1409 ElementsAre("-D", "PREROUTING", "-i", "eth0",
1410 "-p", "udp", "-j", "DNAT",
1411 "--to-destination", "1.2.3.4", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001412 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001413 Datapath datapath(&runner, &firewall);
Garrick Evansf0ab7132019-06-18 14:50:42 +09001414 datapath.RemoveInboundIPv4DNAT("eth0", "1.2.3.4");
Garrick Evansf0ab7132019-06-18 14:50:42 +09001415}
1416
Garrick Evans664a82f2019-12-17 12:18:05 +09001417TEST(DatapathTest, MaskInterfaceFlags) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001418 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001419 MockFirewall firewall;
1420 Datapath datapath(&runner, &firewall, ioctl_req_cap);
Hugo Benichi7c342672020-09-08 09:18:14 +09001421
Garrick Evans664a82f2019-12-17 12:18:05 +09001422 bool result = datapath.MaskInterfaceFlags("foo0", IFF_DEBUG);
Taoyu Li90c13912019-11-26 17:56:54 +09001423 EXPECT_TRUE(result);
Hugo Benichie8758b52020-04-03 14:49:01 +09001424 std::vector<ioctl_req_t> expected = {SIOCGIFFLAGS, SIOCSIFFLAGS};
Taoyu Li90c13912019-11-26 17:56:54 +09001425 EXPECT_EQ(ioctl_reqs, expected);
1426 ioctl_reqs.clear();
Hugo Benichi7c342672020-09-08 09:18:14 +09001427 ioctl_rtentry_args.clear();
Taoyu Li90c13912019-11-26 17:56:54 +09001428}
1429
1430TEST(DatapathTest, AddIPv6Forwarding) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001431 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001432 MockFirewall firewall;
Taoyu Lica49c832019-12-06 17:56:43 +09001433 // Return 1 on iptables -C to simulate rule not existing case
Garrick Evans8e8e3472020-01-23 14:03:50 +09001434 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1435 ElementsAre("-C", "FORWARD", "-i", "eth0", "-o",
1436 "arc_eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001437 false, nullptr))
Garrick Evans8e8e3472020-01-23 14:03:50 +09001438 .WillOnce(Return(1));
1439 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1440 ElementsAre("-A", "FORWARD", "-i", "eth0", "-o",
1441 "arc_eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001442 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001443 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1444 ElementsAre("-C", "FORWARD", "-i", "arc_eth0",
1445 "-o", "eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001446 false, nullptr))
Garrick Evans8e8e3472020-01-23 14:03:50 +09001447 .WillOnce(Return(1));
1448 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1449 ElementsAre("-A", "FORWARD", "-i", "arc_eth0",
1450 "-o", "eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001451 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001452 Datapath datapath(&runner, &firewall);
Taoyu Li90c13912019-11-26 17:56:54 +09001453 datapath.AddIPv6Forwarding("eth0", "arc_eth0");
Taoyu Li90c13912019-11-26 17:56:54 +09001454}
1455
Taoyu Lica49c832019-12-06 17:56:43 +09001456TEST(DatapathTest, AddIPv6ForwardingRuleExists) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001457 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001458 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +09001459 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1460 ElementsAre("-C", "FORWARD", "-i", "eth0", "-o",
1461 "arc_eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001462 false, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001463 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1464 ElementsAre("-C", "FORWARD", "-i", "arc_eth0",
1465 "-o", "eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001466 false, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001467 Datapath datapath(&runner, &firewall);
Taoyu Lica49c832019-12-06 17:56:43 +09001468 datapath.AddIPv6Forwarding("eth0", "arc_eth0");
Taoyu Lica49c832019-12-06 17:56:43 +09001469}
1470
Taoyu Li90c13912019-11-26 17:56:54 +09001471TEST(DatapathTest, RemoveIPv6Forwarding) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001472 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001473 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +09001474 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1475 ElementsAre("-D", "FORWARD", "-i", "eth0", "-o",
1476 "arc_eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001477 true, nullptr));
Garrick Evans8e8e3472020-01-23 14:03:50 +09001478 EXPECT_CALL(runner, ip6tables(StrEq("filter"),
1479 ElementsAre("-D", "FORWARD", "-i", "arc_eth0",
1480 "-o", "eth0", "-j", "ACCEPT", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001481 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001482 Datapath datapath(&runner, &firewall);
Taoyu Li90c13912019-11-26 17:56:54 +09001483 datapath.RemoveIPv6Forwarding("eth0", "arc_eth0");
Taoyu Li90c13912019-11-26 17:56:54 +09001484}
1485
Taoyu Lieb6cc8f2019-12-09 15:53:04 +09001486TEST(DatapathTest, AddIPv6HostRoute) {
Garrick Evans8e8e3472020-01-23 14:03:50 +09001487 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001488 MockFirewall firewall;
Garrick Evans8e8e3472020-01-23 14:03:50 +09001489 EXPECT_CALL(runner,
1490 ip6(StrEq("route"), StrEq("replace"),
1491 ElementsAre("2001:da8:e00::1234/128", "dev", "eth0"), true));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001492 Datapath datapath(&runner, &firewall);
Taoyu Lieb6cc8f2019-12-09 15:53:04 +09001493 datapath.AddIPv6HostRoute("eth0", "2001:da8:e00::1234", 128);
Taoyu Lieb6cc8f2019-12-09 15:53:04 +09001494}
1495
Hugo Benichie8758b52020-04-03 14:49:01 +09001496TEST(DatapathTest, AddIPv4Route) {
1497 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001498 MockFirewall firewall;
1499 Datapath datapath(&runner, &firewall, (ioctl_t)ioctl_rtentry_cap);
Hugo Benichie8758b52020-04-03 14:49:01 +09001500
1501 datapath.AddIPv4Route(Ipv4Addr(192, 168, 1, 1), Ipv4Addr(100, 115, 93, 0),
1502 Ipv4Addr(255, 255, 255, 0));
1503 datapath.DeleteIPv4Route(Ipv4Addr(192, 168, 1, 1), Ipv4Addr(100, 115, 93, 0),
1504 Ipv4Addr(255, 255, 255, 0));
1505 datapath.AddIPv4Route("eth0", Ipv4Addr(100, 115, 92, 8),
1506 Ipv4Addr(255, 255, 255, 252));
1507 datapath.DeleteIPv4Route("eth0", Ipv4Addr(100, 115, 92, 8),
1508 Ipv4Addr(255, 255, 255, 252));
1509
1510 std::vector<ioctl_req_t> expected_reqs = {SIOCADDRT, SIOCDELRT, SIOCADDRT,
1511 SIOCDELRT};
1512 EXPECT_EQ(expected_reqs, ioctl_reqs);
Hugo Benichie8758b52020-04-03 14:49:01 +09001513
1514 std::string route1 =
1515 "{rt_dst: {family: AF_INET, port: 0, addr: 100.115.93.0}, rt_genmask: "
1516 "{family: AF_INET, port: 0, addr: 255.255.255.0}, rt_gateway: {family: "
1517 "AF_INET, port: 0, addr: 192.168.1.1}, rt_dev: null, rt_flags: RTF_UP | "
1518 "RTF_GATEWAY}";
1519 std::string route2 =
1520 "{rt_dst: {family: AF_INET, port: 0, addr: 100.115.92.8}, rt_genmask: "
1521 "{family: AF_INET, port: 0, addr: 255.255.255.252}, rt_gateway: {unset}, "
1522 "rt_dev: eth0, rt_flags: RTF_UP | RTF_GATEWAY}";
1523 std::vector<std::string> captured_routes;
1524 for (const auto& route : ioctl_rtentry_args) {
1525 std::ostringstream stream;
1526 stream << route.second;
1527 captured_routes.emplace_back(stream.str());
1528 }
Hugo Benichie8758b52020-04-03 14:49:01 +09001529 EXPECT_EQ(route1, captured_routes[0]);
1530 EXPECT_EQ(route1, captured_routes[1]);
1531 EXPECT_EQ(route2, captured_routes[2]);
1532 EXPECT_EQ(route2, captured_routes[3]);
Hugo Benichi7c342672020-09-08 09:18:14 +09001533 ioctl_reqs.clear();
1534 ioctl_rtentry_args.clear();
Hugo Benichie8758b52020-04-03 14:49:01 +09001535}
1536
Garrick Evansd291af62020-05-25 10:39:06 +09001537TEST(DatapathTest, AddSNATMarkRules) {
1538 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001539 MockFirewall firewall;
Taoyu Li79871c92020-07-02 16:09:39 +09001540 EXPECT_CALL(
1541 runner,
1542 iptables(StrEq("filter"),
Hugo Benichi6c445322020-08-12 16:46:19 +09001543 ElementsAre("-A", "FORWARD", "-m", "mark", "--mark", "1/1", "-m",
Taoyu Li79871c92020-07-02 16:09:39 +09001544 "state", "--state", "INVALID", "-j", "DROP", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001545 true, nullptr));
Hugo Benichi6c445322020-08-12 16:46:19 +09001546 EXPECT_CALL(runner,
1547 iptables(StrEq("filter"),
1548 ElementsAre("-A", "FORWARD", "-m", "mark", "--mark",
1549 "1/1", "-j", "ACCEPT", "-w"),
1550 true, nullptr));
Garrick Evansd291af62020-05-25 10:39:06 +09001551 EXPECT_CALL(runner,
1552 iptables(StrEq("nat"),
1553 ElementsAre("-A", "POSTROUTING", "-m", "mark", "--mark",
Hugo Benichi6c445322020-08-12 16:46:19 +09001554 "1/1", "-j", "MASQUERADE", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001555 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001556 Datapath datapath(&runner, &firewall);
Garrick Evansd291af62020-05-25 10:39:06 +09001557 datapath.AddSNATMarkRules();
1558}
1559
1560TEST(DatapathTest, RemoveSNATMarkRules) {
1561 MockProcessRunner runner;
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001562 MockFirewall firewall;
Taoyu Li79871c92020-07-02 16:09:39 +09001563 EXPECT_CALL(
1564 runner,
1565 iptables(StrEq("filter"),
Hugo Benichi6c445322020-08-12 16:46:19 +09001566 ElementsAre("-D", "FORWARD", "-m", "mark", "--mark", "1/1", "-m",
Taoyu Li79871c92020-07-02 16:09:39 +09001567 "state", "--state", "INVALID", "-j", "DROP", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001568 true, nullptr));
Hugo Benichi6c445322020-08-12 16:46:19 +09001569 EXPECT_CALL(runner,
1570 iptables(StrEq("filter"),
1571 ElementsAre("-D", "FORWARD", "-m", "mark", "--mark",
1572 "1/1", "-j", "ACCEPT", "-w"),
1573 true, nullptr));
Garrick Evansd291af62020-05-25 10:39:06 +09001574 EXPECT_CALL(runner,
1575 iptables(StrEq("nat"),
1576 ElementsAre("-D", "POSTROUTING", "-m", "mark", "--mark",
Hugo Benichi6c445322020-08-12 16:46:19 +09001577 "1/1", "-j", "MASQUERADE", "-w"),
Jie Jiangcf5ce9c2020-07-14 17:22:03 +09001578 true, nullptr));
Jason Jeremy Imana7273a32020-08-04 11:25:31 +09001579 Datapath datapath(&runner, &firewall);
Garrick Evansd291af62020-05-25 10:39:06 +09001580 datapath.RemoveSNATMarkRules();
1581}
1582
Garrick Evans2f581a02020-05-11 10:43:35 +09001583TEST(DatapathTest, ArcVethHostName) {
1584 EXPECT_EQ("vetheth0", ArcVethHostName("eth0"));
1585 EXPECT_EQ("vethrmnet0", ArcVethHostName("rmnet0"));
1586 EXPECT_EQ("vethrmnet_data0", ArcVethHostName("rmnet_data0"));
1587 EXPECT_EQ("vethifnamsiz_i0", ArcVethHostName("ifnamsiz_ifnam0"));
1588 auto ifname = ArcVethHostName("exceeds_ifnamesiz_checkanyway");
1589 EXPECT_EQ("vethexceeds_ify", ifname);
1590 EXPECT_LT(ifname.length(), IFNAMSIZ);
1591}
1592
Garrick Evans8a067562020-05-11 12:47:30 +09001593TEST(DatapathTest, ArcBridgeName) {
1594 EXPECT_EQ("arc_eth0", ArcBridgeName("eth0"));
1595 EXPECT_EQ("arc_rmnet0", ArcBridgeName("rmnet0"));
1596 EXPECT_EQ("arc_rmnet_data0", ArcBridgeName("rmnet_data0"));
1597 EXPECT_EQ("arc_ifnamsiz_i0", ArcBridgeName("ifnamsiz_ifnam0"));
1598 auto ifname = ArcBridgeName("exceeds_ifnamesiz_checkanyway");
1599 EXPECT_EQ("arc_exceeds_ify", ifname);
1600 EXPECT_LT(ifname.length(), IFNAMSIZ);
1601}
1602
Garrick Evans3388a032020-03-24 11:25:55 +09001603} // namespace patchpanel