1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3 * Landlock tests - Network
4 *
5 * Copyright © 2022-2023 Huawei Tech. Co., Ltd.
6 * Copyright © 2023 Microsoft Corporation
7 */
8
9 #define _GNU_SOURCE
10 #include <arpa/inet.h>
11 #include <errno.h>
12 #include <fcntl.h>
13 #include <linux/landlock.h>
14 #include <linux/in.h>
15 #include <sched.h>
16 #include <stdint.h>
17 #include <string.h>
18 #include <sys/prctl.h>
19 #include <sys/socket.h>
20 #include <sys/syscall.h>
21 #include <sys/un.h>
22
23 #include "audit.h"
24 #include "common.h"
25
26 const short sock_port_start = (1 << 10);
27
28 static const char loopback_ipv4[] = "127.0.0.1";
29 static const char loopback_ipv6[] = "::1";
30
31 /* Number pending connections queue to be hold. */
32 const short backlog = 10;
33
34 enum sandbox_type {
35 NO_SANDBOX,
36 /* This may be used to test rules that allow *and* deny accesses. */
37 TCP_SANDBOX,
38 UDP_SANDBOX,
39 };
40
set_service(struct service_fixture * const srv,const struct protocol_variant prot,const unsigned short index)41 static int set_service(struct service_fixture *const srv,
42 const struct protocol_variant prot,
43 const unsigned short index)
44 {
45 memset(srv, 0, sizeof(*srv));
46
47 /*
48 * Copies all protocol properties in case of the variant only contains
49 * a subset of them.
50 */
51 srv->protocol = prot;
52
53 /* Checks for port overflow. */
54 if (index > 2)
55 return 1;
56 srv->port = sock_port_start << (2 * index);
57
58 switch (prot.domain) {
59 case AF_UNSPEC:
60 case AF_INET:
61 srv->ipv4_addr.sin_family = prot.domain;
62 srv->ipv4_addr.sin_port = htons(srv->port);
63 srv->ipv4_addr.sin_addr.s_addr = inet_addr(loopback_ipv4);
64 return 0;
65
66 case AF_INET6:
67 srv->ipv6_addr.sin6_family = prot.domain;
68 srv->ipv6_addr.sin6_port = htons(srv->port);
69 inet_pton(AF_INET6, loopback_ipv6, &srv->ipv6_addr.sin6_addr);
70 return 0;
71
72 case AF_UNIX:
73 set_unix_address(srv, index);
74 return 0;
75 }
76 return 1;
77 }
78
setup_loopback(struct __test_metadata * const _metadata)79 static void setup_loopback(struct __test_metadata *const _metadata)
80 {
81 set_cap(_metadata, CAP_SYS_ADMIN);
82 ASSERT_EQ(0, unshare(CLONE_NEWNET));
83 clear_cap(_metadata, CAP_SYS_ADMIN);
84
85 set_ambient_cap(_metadata, CAP_NET_ADMIN);
86 ASSERT_EQ(0, system("ip link set dev lo up"));
87 clear_ambient_cap(_metadata, CAP_NET_ADMIN);
88 }
89
prot_is_tcp(const struct protocol_variant * const prot)90 static bool prot_is_tcp(const struct protocol_variant *const prot)
91 {
92 return (prot->domain == AF_INET || prot->domain == AF_INET6) &&
93 prot->type == SOCK_STREAM &&
94 (prot->protocol == IPPROTO_TCP || prot->protocol == IPPROTO_IP);
95 }
96
prot_is_udp(const struct protocol_variant * const prot)97 static bool prot_is_udp(const struct protocol_variant *const prot)
98 {
99 return (prot->domain == AF_INET || prot->domain == AF_INET6) &&
100 prot->type == SOCK_DGRAM &&
101 (prot->protocol == IPPROTO_UDP || prot->protocol == IPPROTO_IP);
102 }
103
is_restricted(const struct protocol_variant * const prot,const enum sandbox_type sandbox)104 static bool is_restricted(const struct protocol_variant *const prot,
105 const enum sandbox_type sandbox)
106 {
107 if (sandbox == TCP_SANDBOX)
108 return prot_is_tcp(prot);
109 else if (sandbox == UDP_SANDBOX)
110 return prot_is_udp(prot);
111 return false;
112 }
113
socket_variant(const struct service_fixture * const srv)114 static int socket_variant(const struct service_fixture *const srv)
115 {
116 /* Arbitrary value just to not block other tests indefinitely. */
117 const struct timeval timeout = {
118 .tv_sec = 0,
119 .tv_usec = 100000,
120 };
121 int sockfd;
122 int ret;
123
124 sockfd = socket(srv->protocol.domain, srv->protocol.type | SOCK_CLOEXEC,
125 srv->protocol.protocol);
126 if (sockfd < 0)
127 return -errno;
128
129 ret = setsockopt(sockfd, SOL_SOCKET, SO_RCVTIMEO, &timeout,
130 sizeof(timeout));
131 if (ret != 0) {
132 ret = -errno;
133 close(sockfd);
134 return ret;
135 }
136 ret = setsockopt(sockfd, SOL_SOCKET, SO_SNDTIMEO, &timeout,
137 sizeof(timeout));
138 if (ret != 0) {
139 ret = -errno;
140 close(sockfd);
141 return ret;
142 }
143 return sockfd;
144 }
145
146 #ifndef SIN6_LEN_RFC2133
147 #define SIN6_LEN_RFC2133 24
148 #endif
149
get_addrlen(const struct service_fixture * const srv,const bool minimal)150 static socklen_t get_addrlen(const struct service_fixture *const srv,
151 const bool minimal)
152 {
153 switch (srv->protocol.domain) {
154 case AF_UNSPEC:
155 if (minimal)
156 return sizeof(sa_family_t);
157 return sizeof(struct sockaddr_storage);
158
159 case AF_INET:
160 return sizeof(srv->ipv4_addr);
161
162 case AF_INET6:
163 if (minimal)
164 return SIN6_LEN_RFC2133;
165 return sizeof(srv->ipv6_addr);
166
167 case AF_UNIX:
168 if (minimal)
169 return sizeof(srv->unix_addr) -
170 sizeof(srv->unix_addr.sun_path);
171 return srv->unix_addr_len;
172
173 default:
174 return 0;
175 }
176 }
177
set_port(struct service_fixture * const srv,uint16_t port)178 static void set_port(struct service_fixture *const srv, uint16_t port)
179 {
180 switch (srv->protocol.domain) {
181 case AF_UNSPEC:
182 case AF_INET:
183 srv->ipv4_addr.sin_port = htons(port);
184 return;
185
186 case AF_INET6:
187 srv->ipv6_addr.sin6_port = htons(port);
188 return;
189
190 default:
191 return;
192 }
193 }
194
get_binded_port(int socket_fd,const struct protocol_variant * const prot)195 static uint16_t get_binded_port(int socket_fd,
196 const struct protocol_variant *const prot)
197 {
198 struct sockaddr_in ipv4_addr;
199 struct sockaddr_in6 ipv6_addr;
200 socklen_t ipv4_addr_len, ipv6_addr_len;
201
202 /* Gets binded port. */
203 switch (prot->domain) {
204 case AF_UNSPEC:
205 case AF_INET:
206 ipv4_addr_len = sizeof(ipv4_addr);
207 getsockname(socket_fd, &ipv4_addr, &ipv4_addr_len);
208 return ntohs(ipv4_addr.sin_port);
209
210 case AF_INET6:
211 ipv6_addr_len = sizeof(ipv6_addr);
212 getsockname(socket_fd, &ipv6_addr, &ipv6_addr_len);
213 return ntohs(ipv6_addr.sin6_port);
214
215 default:
216 return 0;
217 }
218 }
219
bind_variant_addrlen(const int sock_fd,const struct service_fixture * const srv,const socklen_t addrlen)220 static int bind_variant_addrlen(const int sock_fd,
221 const struct service_fixture *const srv,
222 const socklen_t addrlen)
223 {
224 int ret;
225
226 switch (srv->protocol.domain) {
227 case AF_UNSPEC:
228 case AF_INET:
229 ret = bind(sock_fd, &srv->ipv4_addr, addrlen);
230 break;
231
232 case AF_INET6:
233 ret = bind(sock_fd, &srv->ipv6_addr, addrlen);
234 break;
235
236 case AF_UNIX:
237 ret = bind(sock_fd, &srv->unix_addr, addrlen);
238 break;
239
240 default:
241 errno = EAFNOSUPPORT;
242 return -errno;
243 }
244
245 if (ret < 0)
246 return -errno;
247 return ret;
248 }
249
bind_variant(const int sock_fd,const struct service_fixture * const srv)250 static int bind_variant(const int sock_fd,
251 const struct service_fixture *const srv)
252 {
253 return bind_variant_addrlen(sock_fd, srv, get_addrlen(srv, false));
254 }
255
connect_variant_addrlen(const int sock_fd,const struct service_fixture * const srv,const socklen_t addrlen)256 static int connect_variant_addrlen(const int sock_fd,
257 const struct service_fixture *const srv,
258 const socklen_t addrlen)
259 {
260 int ret;
261
262 switch (srv->protocol.domain) {
263 case AF_UNSPEC:
264 case AF_INET:
265 ret = connect(sock_fd, &srv->ipv4_addr, addrlen);
266 break;
267
268 case AF_INET6:
269 ret = connect(sock_fd, &srv->ipv6_addr, addrlen);
270 break;
271
272 case AF_UNIX:
273 ret = connect(sock_fd, &srv->unix_addr, addrlen);
274 break;
275
276 default:
277 errno = -EAFNOSUPPORT;
278 return -errno;
279 }
280
281 if (ret < 0)
282 return -errno;
283 return ret;
284 }
285
connect_variant(const int sock_fd,const struct service_fixture * const srv)286 static int connect_variant(const int sock_fd,
287 const struct service_fixture *const srv)
288 {
289 return connect_variant_addrlen(sock_fd, srv, get_addrlen(srv, false));
290 }
291
sendto_variant_addrlen(const int sock_fd,const struct service_fixture * const srv,const socklen_t addrlen,void * buf,size_t len,size_t flags)292 static int sendto_variant_addrlen(const int sock_fd,
293 const struct service_fixture *const srv,
294 const socklen_t addrlen, void *buf,
295 size_t len, size_t flags)
296 {
297 const struct sockaddr *dst = NULL;
298 ssize_t ret;
299
300 /*
301 * We never want our processes to be killed by SIGPIPE: we check return
302 * codes and errno, so that we have actual error messages.
303 */
304 flags |= MSG_NOSIGNAL;
305
306 if (srv != NULL) {
307 switch (srv->protocol.domain) {
308 case AF_UNSPEC:
309 case AF_INET:
310 dst = (const struct sockaddr *)&srv->ipv4_addr;
311 break;
312
313 case AF_INET6:
314 dst = (const struct sockaddr *)&srv->ipv6_addr;
315 break;
316
317 case AF_UNIX:
318 dst = (const struct sockaddr *)&srv->unix_addr;
319 break;
320
321 default:
322 errno = EAFNOSUPPORT;
323 return -errno;
324 }
325 }
326
327 ret = sendto(sock_fd, buf, len, flags, dst, addrlen);
328 if (ret < 0)
329 return -errno;
330
331 /* errno is not set in cases of partial writes. */
332 if (ret != len)
333 return -EINTR;
334
335 return 0;
336 }
337
sendto_variant(const int sock_fd,const struct service_fixture * const srv,void * buf,size_t len,size_t flags)338 static int sendto_variant(const int sock_fd,
339 const struct service_fixture *const srv, void *buf,
340 size_t len, size_t flags)
341 {
342 socklen_t addrlen = 0;
343
344 if (srv != NULL)
345 addrlen = get_addrlen(srv, false);
346
347 return sendto_variant_addrlen(sock_fd, srv, addrlen, buf, len, flags);
348 }
349
test_sendmsg(struct __test_metadata * const _metadata,const struct protocol_variant * prot,int client_fd,int server_fd,const struct service_fixture * srv,bool bind_denied,bool send_denied)350 static int test_sendmsg(struct __test_metadata *const _metadata,
351 const struct protocol_variant *prot, int client_fd,
352 int server_fd, const struct service_fixture *srv,
353 bool bind_denied, bool send_denied)
354 {
355 int ret;
356 socklen_t opt_len;
357 int sock_type;
358 int addr_family;
359 struct sockaddr_storage peer_addr = { 0 };
360 bool has_remote_port;
361 bool needs_autobind;
362 char read_buf[1] = { 0 };
363
364 /*
365 * Prepare the test by inspecting the socket type and whether it has a
366 * local/remote address set (all of which determine the expected
367 * outcomes).
368 */
369 opt_len = sizeof(sock_type);
370 ASSERT_EQ(0, getsockopt(client_fd, SOL_SOCKET, SO_TYPE, &sock_type,
371 &opt_len));
372 opt_len = sizeof(addr_family);
373 ASSERT_EQ(0, getsockopt(client_fd, SOL_SOCKET, SO_DOMAIN, &addr_family,
374 &opt_len));
375 opt_len = sizeof(peer_addr);
376 has_remote_port = (getpeername(client_fd, (struct sockaddr *)&peer_addr,
377 &opt_len) == 0);
378 needs_autobind = (addr_family == AF_INET || addr_family == AF_INET6) &&
379 get_binded_port(client_fd, prot) == 0;
380
381 /* First, check error code with truncated explicit address. */
382 if (srv != NULL) {
383 ret = sendto_variant_addrlen(
384 client_fd, srv, get_addrlen(srv, true) - 1, "A", 1, 0);
385 if (sock_type == SOCK_STREAM && !has_remote_port) {
386 EXPECT_EQ(-EPIPE, ret)
387 {
388 return -1;
389 }
390 } else if (bind_denied && needs_autobind) {
391 EXPECT_EQ(-EACCES, ret)
392 {
393 return -1;
394 }
395 } else {
396 EXPECT_EQ(-EINVAL, ret)
397 {
398 return -1;
399 }
400 }
401 }
402
403 /* With or without explicit destination address (srv can be NULL). */
404 ret = sendto_variant(client_fd, srv, "B", 1, 0);
405 if (sock_type == SOCK_STREAM && !has_remote_port) {
406 EXPECT_EQ(-EPIPE, ret)
407 {
408 return -1;
409 }
410 } else if ((send_denied && srv != NULL) ||
411 (bind_denied && needs_autobind)) {
412 ASSERT_EQ(-EACCES, ret)
413 {
414 return -1;
415 }
416 } else if (srv == NULL && !has_remote_port) {
417 if (addr_family == AF_UNIX) {
418 ASSERT_EQ(-ENOTCONN, ret)
419 {
420 return -1;
421 }
422 } else if (sock_type == SOCK_STREAM) {
423 ASSERT_EQ(-EPIPE, ret)
424 {
425 return -1;
426 }
427 } else {
428 ASSERT_EQ(-EDESTADDRREQ, ret)
429 {
430 return -1;
431 }
432 }
433 } else {
434 ASSERT_EQ(0, ret);
435 ASSERT_EQ(1, recv(server_fd, read_buf, 1, 0));
436 ASSERT_EQ(read_buf[0], 'B')
437 {
438 return -1;
439 }
440 }
441
442 return 0;
443 }
444
FIXTURE(protocol)445 FIXTURE(protocol)
446 {
447 struct service_fixture srv0, srv1, srv2;
448 struct service_fixture unspec_any0, unspec_srv0, unspec_srv1;
449 };
450
FIXTURE_VARIANT(protocol)451 FIXTURE_VARIANT(protocol)
452 {
453 const enum sandbox_type sandbox;
454 const struct protocol_variant prot;
455 };
456
FIXTURE_SETUP(protocol)457 FIXTURE_SETUP(protocol)
458 {
459 struct protocol_variant prot_unspec = variant->prot;
460
461 prot_unspec.domain = AF_UNSPEC;
462
463 disable_caps(_metadata);
464
465 ASSERT_EQ(0, set_service(&self->srv0, variant->prot, 0));
466 ASSERT_EQ(0, set_service(&self->srv1, variant->prot, 1));
467 ASSERT_EQ(0, set_service(&self->srv2, variant->prot, 2));
468
469 ASSERT_EQ(0, set_service(&self->unspec_srv0, prot_unspec, 0));
470 ASSERT_EQ(0, set_service(&self->unspec_srv1, prot_unspec, 1));
471
472 ASSERT_EQ(0, set_service(&self->unspec_any0, prot_unspec, 0));
473 self->unspec_any0.ipv4_addr.sin_addr.s_addr = htonl(INADDR_ANY);
474
475 setup_loopback(_metadata);
476 };
477
FIXTURE_TEARDOWN(protocol)478 FIXTURE_TEARDOWN(protocol)
479 {
480 }
481
482 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv4_tcp1)483 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv4_tcp1) {
484 /* clang-format on */
485 .sandbox = NO_SANDBOX,
486 .prot = {
487 .domain = AF_INET,
488 .type = SOCK_STREAM,
489 /* IPPROTO_IP == 0 */
490 .protocol = IPPROTO_IP,
491 },
492 };
493
494 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv4_tcp2)495 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv4_tcp2) {
496 /* clang-format on */
497 .sandbox = NO_SANDBOX,
498 .prot = {
499 .domain = AF_INET,
500 .type = SOCK_STREAM,
501 .protocol = IPPROTO_TCP,
502 },
503 };
504
505 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv4_mptcp)506 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv4_mptcp) {
507 /* clang-format on */
508 .sandbox = NO_SANDBOX,
509 .prot = {
510 .domain = AF_INET,
511 .type = SOCK_STREAM,
512 .protocol = IPPROTO_MPTCP,
513 },
514 };
515
516 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv6_tcp1)517 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv6_tcp1) {
518 /* clang-format on */
519 .sandbox = NO_SANDBOX,
520 .prot = {
521 .domain = AF_INET6,
522 .type = SOCK_STREAM,
523 /* IPPROTO_IP == 0 */
524 .protocol = IPPROTO_IP,
525 },
526 };
527
528 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv6_tcp2)529 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv6_tcp2) {
530 /* clang-format on */
531 .sandbox = NO_SANDBOX,
532 .prot = {
533 .domain = AF_INET6,
534 .type = SOCK_STREAM,
535 .protocol = IPPROTO_TCP,
536 },
537 };
538
539 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv6_mptcp)540 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv6_mptcp) {
541 /* clang-format on */
542 .sandbox = NO_SANDBOX,
543 .prot = {
544 .domain = AF_INET6,
545 .type = SOCK_STREAM,
546 .protocol = IPPROTO_MPTCP,
547 },
548 };
549
550 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv4_udp)551 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv4_udp) {
552 /* clang-format on */
553 .sandbox = NO_SANDBOX,
554 .prot = {
555 .domain = AF_INET,
556 .type = SOCK_DGRAM,
557 },
558 };
559
560 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_ipv6_udp)561 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_ipv6_udp) {
562 /* clang-format on */
563 .sandbox = NO_SANDBOX,
564 .prot = {
565 .domain = AF_INET6,
566 .type = SOCK_DGRAM,
567 },
568 };
569
570 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_unix_stream)571 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_unix_stream) {
572 /* clang-format on */
573 .sandbox = NO_SANDBOX,
574 .prot = {
575 .domain = AF_UNIX,
576 .type = SOCK_STREAM,
577 },
578 };
579
580 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,no_sandbox_with_unix_datagram)581 FIXTURE_VARIANT_ADD(protocol, no_sandbox_with_unix_datagram) {
582 /* clang-format on */
583 .sandbox = NO_SANDBOX,
584 .prot = {
585 .domain = AF_UNIX,
586 .type = SOCK_DGRAM,
587 },
588 };
589
590 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv4_tcp1)591 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv4_tcp1) {
592 /* clang-format on */
593 .sandbox = TCP_SANDBOX,
594 .prot = {
595 .domain = AF_INET,
596 .type = SOCK_STREAM,
597 /* IPPROTO_IP == 0 */
598 .protocol = IPPROTO_IP,
599 },
600 };
601
602 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv4_tcp2)603 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv4_tcp2) {
604 /* clang-format on */
605 .sandbox = TCP_SANDBOX,
606 .prot = {
607 .domain = AF_INET,
608 .type = SOCK_STREAM,
609 .protocol = IPPROTO_TCP,
610 },
611 };
612
613 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv4_mptcp)614 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv4_mptcp) {
615 /* clang-format on */
616 .sandbox = TCP_SANDBOX,
617 .prot = {
618 .domain = AF_INET,
619 .type = SOCK_STREAM,
620 .protocol = IPPROTO_MPTCP,
621 },
622 };
623
624 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv6_tcp1)625 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv6_tcp1) {
626 /* clang-format on */
627 .sandbox = TCP_SANDBOX,
628 .prot = {
629 .domain = AF_INET6,
630 .type = SOCK_STREAM,
631 /* IPPROTO_IP == 0 */
632 .protocol = IPPROTO_IP,
633 },
634 };
635
636 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv6_tcp2)637 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv6_tcp2) {
638 /* clang-format on */
639 .sandbox = TCP_SANDBOX,
640 .prot = {
641 .domain = AF_INET6,
642 .type = SOCK_STREAM,
643 .protocol = IPPROTO_TCP,
644 },
645 };
646
647 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv6_mptcp)648 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv6_mptcp) {
649 /* clang-format on */
650 .sandbox = TCP_SANDBOX,
651 .prot = {
652 .domain = AF_INET6,
653 .type = SOCK_STREAM,
654 .protocol = IPPROTO_MPTCP,
655 },
656 };
657
658 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv4_udp)659 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv4_udp) {
660 /* clang-format on */
661 .sandbox = TCP_SANDBOX,
662 .prot = {
663 .domain = AF_INET,
664 .type = SOCK_DGRAM,
665 },
666 };
667
668 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_ipv6_udp)669 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_ipv6_udp) {
670 /* clang-format on */
671 .sandbox = TCP_SANDBOX,
672 .prot = {
673 .domain = AF_INET6,
674 .type = SOCK_DGRAM,
675 },
676 };
677
678 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_unix_stream)679 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_unix_stream) {
680 /* clang-format on */
681 .sandbox = TCP_SANDBOX,
682 .prot = {
683 .domain = AF_UNIX,
684 .type = SOCK_STREAM,
685 },
686 };
687
688 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,tcp_sandbox_with_unix_datagram)689 FIXTURE_VARIANT_ADD(protocol, tcp_sandbox_with_unix_datagram) {
690 /* clang-format on */
691 .sandbox = TCP_SANDBOX,
692 .prot = {
693 .domain = AF_UNIX,
694 .type = SOCK_DGRAM,
695 },
696 };
697
698 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv4_udp1)699 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv4_udp1) {
700 /* clang-format on */
701 .sandbox = UDP_SANDBOX,
702 .prot = {
703 .domain = AF_INET,
704 .type = SOCK_DGRAM,
705 .protocol = IPPROTO_UDP,
706 },
707 };
708
709 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv4_udp2)710 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv4_udp2) {
711 /* clang-format on */
712 .sandbox = UDP_SANDBOX,
713 .prot = {
714 .domain = AF_INET,
715 .type = SOCK_DGRAM,
716 /* IPPROTO_IP == 0 */
717 .protocol = IPPROTO_IP,
718 },
719 };
720
721 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv6_udp1)722 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv6_udp1) {
723 /* clang-format on */
724 .sandbox = UDP_SANDBOX,
725 .prot = {
726 .domain = AF_INET6,
727 .type = SOCK_DGRAM,
728 .protocol = IPPROTO_UDP,
729 },
730 };
731
732 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv6_udp2)733 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv6_udp2) {
734 /* clang-format on */
735 .sandbox = UDP_SANDBOX,
736 .prot = {
737 .domain = AF_INET6,
738 .type = SOCK_DGRAM,
739 /* IPPROTO_IP == 0 */
740 .protocol = IPPROTO_IP,
741 },
742 };
743
744 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv4_tcp)745 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv4_tcp) {
746 /* clang-format on */
747 .sandbox = UDP_SANDBOX,
748 .prot = {
749 .domain = AF_INET,
750 .type = SOCK_STREAM,
751 },
752 };
753
754 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_ipv6_tcp)755 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_ipv6_tcp) {
756 /* clang-format on */
757 .sandbox = UDP_SANDBOX,
758 .prot = {
759 .domain = AF_INET6,
760 .type = SOCK_STREAM,
761 },
762 };
763
764 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_unix_stream)765 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_unix_stream) {
766 /* clang-format on */
767 .sandbox = UDP_SANDBOX,
768 .prot = {
769 .domain = AF_UNIX,
770 .type = SOCK_STREAM,
771 },
772 };
773
774 /* clang-format off */
FIXTURE_VARIANT_ADD(protocol,udp_sandbox_with_unix_datagram)775 FIXTURE_VARIANT_ADD(protocol, udp_sandbox_with_unix_datagram) {
776 /* clang-format on */
777 .sandbox = UDP_SANDBOX,
778 .prot = {
779 .domain = AF_UNIX,
780 .type = SOCK_DGRAM,
781 },
782 };
783
test_bind_and_connect(struct __test_metadata * const _metadata,const struct service_fixture * const srv,const bool deny_bind,const bool deny_connect)784 static void test_bind_and_connect(struct __test_metadata *const _metadata,
785 const struct service_fixture *const srv,
786 const bool deny_bind, const bool deny_connect)
787 {
788 char buf = '\0';
789 int inval_fd, bind_fd, client_fd, status, ret;
790 pid_t child;
791
792 /* Starts invalid addrlen tests with bind. */
793 inval_fd = socket_variant(srv);
794 ASSERT_LE(0, inval_fd)
795 {
796 TH_LOG("Failed to create socket: %s", strerror(errno));
797 }
798
799 /* Tries to bind with zero as addrlen. */
800 EXPECT_EQ(-EINVAL, bind_variant_addrlen(inval_fd, srv, 0));
801
802 /* Tries to bind with too small addrlen. */
803 EXPECT_EQ(-EINVAL, bind_variant_addrlen(inval_fd, srv,
804 get_addrlen(srv, true) - 1));
805
806 /* Tries to bind with minimal addrlen. */
807 ret = bind_variant_addrlen(inval_fd, srv, get_addrlen(srv, true));
808 if (deny_bind) {
809 EXPECT_EQ(-EACCES, ret);
810 } else {
811 EXPECT_EQ(0, ret)
812 {
813 TH_LOG("Failed to bind to socket: %s", strerror(errno));
814 }
815 }
816 EXPECT_EQ(0, close(inval_fd));
817
818 /* Starts invalid addrlen tests with connect. */
819 inval_fd = socket_variant(srv);
820 ASSERT_LE(0, inval_fd);
821
822 /* Tries to connect with zero as addrlen. */
823 EXPECT_EQ(-EINVAL, connect_variant_addrlen(inval_fd, srv, 0));
824
825 /* Tries to connect with too small addrlen. */
826 EXPECT_EQ(-EINVAL, connect_variant_addrlen(inval_fd, srv,
827 get_addrlen(srv, true) - 1));
828
829 /* Tries to connect with minimal addrlen. */
830 ret = connect_variant_addrlen(inval_fd, srv, get_addrlen(srv, true));
831 if (srv->protocol.domain == AF_UNIX) {
832 EXPECT_EQ(-EINVAL, ret);
833 } else if (deny_connect) {
834 EXPECT_EQ(-EACCES, ret);
835 } else if (srv->protocol.type == SOCK_STREAM) {
836 /* No listening server, whatever the value of deny_bind. */
837 EXPECT_EQ(-ECONNREFUSED, ret);
838 } else {
839 EXPECT_EQ(0, ret)
840 {
841 TH_LOG("Failed to connect to socket: %s",
842 strerror(errno));
843 }
844 }
845 EXPECT_EQ(0, close(inval_fd));
846
847 /* Starts connection tests. */
848 bind_fd = socket_variant(srv);
849 ASSERT_LE(0, bind_fd);
850
851 ret = bind_variant(bind_fd, srv);
852 if (deny_bind) {
853 EXPECT_EQ(-EACCES, ret);
854 } else {
855 EXPECT_EQ(0, ret);
856
857 /* Creates a listening socket. */
858 if (srv->protocol.type == SOCK_STREAM)
859 EXPECT_EQ(0, listen(bind_fd, backlog));
860 }
861
862 child = fork();
863 ASSERT_LE(0, child);
864 if (child == 0) {
865 int connect_fd, ret;
866
867 /* Closes listening socket for the child. */
868 EXPECT_EQ(0, close(bind_fd));
869
870 /* Starts connection tests. */
871 connect_fd = socket_variant(srv);
872 ASSERT_LE(0, connect_fd);
873 ret = connect_variant(connect_fd, srv);
874 if (deny_connect) {
875 EXPECT_EQ(-EACCES, ret);
876 } else if (deny_bind && srv->protocol.type == SOCK_STREAM) {
877 /* No listening server. */
878 EXPECT_EQ(-ECONNREFUSED, ret);
879 } else {
880 EXPECT_EQ(0, ret);
881 EXPECT_EQ(1, write(connect_fd, ".", 1));
882 }
883
884 EXPECT_EQ(0, close(connect_fd));
885 _exit(_metadata->exit_code);
886 return;
887 }
888
889 /* Accepts connection from the child. */
890 client_fd = bind_fd;
891 if (!deny_bind && !deny_connect) {
892 if (srv->protocol.type == SOCK_STREAM) {
893 client_fd = accept(bind_fd, NULL, 0);
894 ASSERT_LE(0, client_fd);
895 }
896
897 EXPECT_EQ(1, read(client_fd, &buf, 1));
898 EXPECT_EQ('.', buf);
899 }
900
901 EXPECT_EQ(child, waitpid(child, &status, 0));
902 EXPECT_EQ(1, WIFEXITED(status));
903 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
904
905 /* Closes connection, if any. */
906 if (client_fd != bind_fd)
907 EXPECT_LE(0, close(client_fd));
908
909 /* Closes listening socket. */
910 EXPECT_EQ(0, close(bind_fd));
911 }
912
TEST_F(protocol,bind)913 TEST_F(protocol, bind)
914 {
915 if (variant->sandbox == TCP_SANDBOX ||
916 variant->sandbox == UDP_SANDBOX) {
917 const __u64 bind_access =
918 (variant->sandbox == TCP_SANDBOX ?
919 LANDLOCK_ACCESS_NET_BIND_TCP :
920 LANDLOCK_ACCESS_NET_BIND_UDP);
921 const __u64 conn_access =
922 (variant->sandbox == TCP_SANDBOX ?
923 LANDLOCK_ACCESS_NET_CONNECT_TCP :
924 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
925 const struct landlock_ruleset_attr ruleset_attr = {
926 .handled_access_net = bind_access | conn_access,
927 };
928 const struct landlock_net_port_attr bind_connect_p0 = {
929 .allowed_access = bind_access | conn_access,
930 .port = self->srv0.port,
931 };
932 const struct landlock_net_port_attr connect_p1 = {
933 .allowed_access = conn_access,
934 .port = self->srv1.port,
935 };
936 int ruleset_fd;
937
938 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
939 sizeof(ruleset_attr), 0);
940 ASSERT_LE(0, ruleset_fd);
941
942 /* Allows connect and bind for the first port. */
943 ASSERT_EQ(0,
944 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
945 &bind_connect_p0, 0));
946
947 /* Allows connect and denies bind for the second port. */
948 ASSERT_EQ(0,
949 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
950 &connect_p1, 0));
951
952 /*
953 * For UDP sockets, allows binding to ephemeral ports (required
954 * to connect or send a first datagram)
955 */
956 if (variant->sandbox == UDP_SANDBOX) {
957 const struct landlock_net_port_attr bind_ephemeral = {
958 .allowed_access = bind_access,
959 .port = 0,
960 };
961 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
962 LANDLOCK_RULE_NET_PORT,
963 &bind_ephemeral, 0));
964 }
965
966 enforce_ruleset(_metadata, ruleset_fd);
967 EXPECT_EQ(0, close(ruleset_fd));
968 }
969
970 /* Binds a socket to the first port. */
971 test_bind_and_connect(_metadata, &self->srv0, false, false);
972
973 /* Binds a socket to the second port. */
974 test_bind_and_connect(_metadata, &self->srv1,
975 is_restricted(&variant->prot, variant->sandbox),
976 false);
977
978 /* Binds a socket to the third port. */
979 test_bind_and_connect(_metadata, &self->srv2,
980 is_restricted(&variant->prot, variant->sandbox),
981 is_restricted(&variant->prot, variant->sandbox));
982 }
983
TEST_F(protocol,connect)984 TEST_F(protocol, connect)
985 {
986 if (variant->sandbox == TCP_SANDBOX ||
987 variant->sandbox == UDP_SANDBOX) {
988 const __u64 bind_access =
989 (variant->sandbox == TCP_SANDBOX ?
990 LANDLOCK_ACCESS_NET_BIND_TCP :
991 LANDLOCK_ACCESS_NET_BIND_UDP);
992 const __u64 conn_access =
993 (variant->sandbox == TCP_SANDBOX ?
994 LANDLOCK_ACCESS_NET_CONNECT_TCP :
995 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
996 const struct landlock_ruleset_attr ruleset_attr = {
997 .handled_access_net = bind_access | conn_access,
998 };
999 const struct landlock_net_port_attr bind_connect_p0 = {
1000 .allowed_access = bind_access | conn_access,
1001 .port = self->srv0.port,
1002 };
1003 const struct landlock_net_port_attr bind_p1 = {
1004 .allowed_access = bind_access,
1005 .port = self->srv1.port,
1006 };
1007 int ruleset_fd;
1008
1009 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
1010 sizeof(ruleset_attr), 0);
1011 ASSERT_LE(0, ruleset_fd);
1012
1013 /* Allows connect and bind for the first port. */
1014 ASSERT_EQ(0,
1015 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
1016 &bind_connect_p0, 0));
1017
1018 /* Allows bind and denies connect for the second port. */
1019 ASSERT_EQ(0,
1020 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
1021 &bind_p1, 0));
1022
1023 /*
1024 * For UDP sockets, allows binding to ephemeral ports (required
1025 * to connect or send a first datagram)
1026 */
1027 if (variant->sandbox == UDP_SANDBOX) {
1028 const struct landlock_net_port_attr bind_ephemeral = {
1029 .allowed_access = bind_access,
1030 .port = 0,
1031 };
1032 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
1033 LANDLOCK_RULE_NET_PORT,
1034 &bind_ephemeral, 0));
1035 }
1036
1037 enforce_ruleset(_metadata, ruleset_fd);
1038 EXPECT_EQ(0, close(ruleset_fd));
1039 }
1040
1041 test_bind_and_connect(_metadata, &self->srv0, false, false);
1042
1043 test_bind_and_connect(_metadata, &self->srv1, false,
1044 is_restricted(&variant->prot, variant->sandbox));
1045
1046 test_bind_and_connect(_metadata, &self->srv2,
1047 is_restricted(&variant->prot, variant->sandbox),
1048 is_restricted(&variant->prot, variant->sandbox));
1049 }
1050
TEST_F(protocol,bind_unspec)1051 TEST_F(protocol, bind_unspec)
1052 {
1053 const __u64 bind_access = (variant->sandbox == TCP_SANDBOX ?
1054 LANDLOCK_ACCESS_NET_BIND_TCP :
1055 LANDLOCK_ACCESS_NET_BIND_UDP);
1056 const struct landlock_ruleset_attr ruleset_attr = {
1057 .handled_access_net = bind_access,
1058 };
1059 const struct landlock_net_port_attr rule_bind = {
1060 .allowed_access = bind_access,
1061 .port = self->srv0.port,
1062 };
1063 int bind_fd, ret;
1064
1065 if (variant->sandbox == TCP_SANDBOX ||
1066 variant->sandbox == UDP_SANDBOX) {
1067 const int ruleset_fd = landlock_create_ruleset(
1068 &ruleset_attr, sizeof(ruleset_attr), 0);
1069 ASSERT_LE(0, ruleset_fd);
1070
1071 /* Allows bind. */
1072 ASSERT_EQ(0,
1073 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
1074 &rule_bind, 0));
1075 enforce_ruleset(_metadata, ruleset_fd);
1076 EXPECT_EQ(0, close(ruleset_fd));
1077 }
1078
1079 bind_fd = socket_variant(&self->srv0);
1080 ASSERT_LE(0, bind_fd);
1081
1082 /* Tries to bind with too small addrlen. */
1083 EXPECT_EQ(-EINVAL, bind_variant_addrlen(
1084 bind_fd, &self->unspec_any0,
1085 get_addrlen(&self->unspec_any0, true) - 1));
1086
1087 /* Allowed bind on AF_UNSPEC/INADDR_ANY. */
1088 ret = bind_variant(bind_fd, &self->unspec_any0);
1089 if (variant->prot.domain == AF_INET) {
1090 EXPECT_EQ(0, ret)
1091 {
1092 TH_LOG("Failed to bind to unspec/any socket: %s",
1093 strerror(errno));
1094 }
1095 } else if (variant->prot.domain == AF_INET6) {
1096 EXPECT_EQ(-EAFNOSUPPORT, ret);
1097 } else {
1098 EXPECT_EQ(-EINVAL, ret);
1099 }
1100 EXPECT_EQ(0, close(bind_fd));
1101
1102 if (variant->sandbox == TCP_SANDBOX ||
1103 variant->sandbox == UDP_SANDBOX) {
1104 const int ruleset_fd = landlock_create_ruleset(
1105 &ruleset_attr, sizeof(ruleset_attr), 0);
1106 ASSERT_LE(0, ruleset_fd);
1107
1108 /* Denies bind. */
1109 enforce_ruleset(_metadata, ruleset_fd);
1110 EXPECT_EQ(0, close(ruleset_fd));
1111 }
1112
1113 bind_fd = socket_variant(&self->srv0);
1114 ASSERT_LE(0, bind_fd);
1115
1116 /* Denied bind on AF_UNSPEC/INADDR_ANY. */
1117 ret = bind_variant(bind_fd, &self->unspec_any0);
1118 if (variant->prot.domain == AF_INET) {
1119 if (is_restricted(&variant->prot, variant->sandbox)) {
1120 EXPECT_EQ(-EACCES, ret);
1121 } else {
1122 EXPECT_EQ(0, ret);
1123 }
1124 } else if (variant->prot.domain == AF_INET6) {
1125 EXPECT_EQ(-EAFNOSUPPORT, ret);
1126 } else {
1127 EXPECT_EQ(-EINVAL, ret);
1128 }
1129 EXPECT_EQ(0, close(bind_fd));
1130
1131 /* Checks bind with AF_UNSPEC and the loopback address. */
1132 bind_fd = socket_variant(&self->srv0);
1133 ASSERT_LE(0, bind_fd);
1134 ret = bind_variant(bind_fd, &self->unspec_srv0);
1135 if (variant->prot.domain == AF_INET ||
1136 variant->prot.domain == AF_INET6) {
1137 EXPECT_EQ(-EAFNOSUPPORT, ret);
1138 } else {
1139 EXPECT_EQ(-EINVAL, ret)
1140 {
1141 TH_LOG("Wrong bind error: %s", strerror(errno));
1142 }
1143 }
1144 EXPECT_EQ(0, close(bind_fd));
1145 }
1146
TEST_F(protocol,connect_unspec)1147 TEST_F(protocol, connect_unspec)
1148 {
1149 const __u64 connect_right =
1150 (variant->sandbox == TCP_SANDBOX ?
1151 LANDLOCK_ACCESS_NET_CONNECT_TCP :
1152 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
1153 const __u64 bind_right = (variant->sandbox == TCP_SANDBOX ?
1154 LANDLOCK_ACCESS_NET_BIND_TCP :
1155 LANDLOCK_ACCESS_NET_BIND_UDP);
1156 const struct landlock_ruleset_attr ruleset_conn = {
1157 .handled_access_net = connect_right,
1158 };
1159 const struct landlock_ruleset_attr ruleset_conn_bind = {
1160 .handled_access_net = connect_right | bind_right,
1161 };
1162 const struct landlock_net_port_attr rule_connect = {
1163 .allowed_access = connect_right,
1164 .port = self->srv0.port,
1165 };
1166 int bind_fd, client_fd, status;
1167 pid_t child;
1168
1169 /* Specific connection tests. */
1170 bind_fd = socket_variant(&self->srv0);
1171 ASSERT_LE(0, bind_fd);
1172 EXPECT_EQ(0, bind_variant(bind_fd, &self->srv0));
1173 if (self->srv0.protocol.type == SOCK_STREAM)
1174 EXPECT_EQ(0, listen(bind_fd, backlog));
1175
1176 child = fork();
1177 ASSERT_LE(0, child);
1178 if (child == 0) {
1179 int connect_fd, ret;
1180
1181 /* Closes listening socket for the child. */
1182 EXPECT_EQ(0, close(bind_fd));
1183
1184 connect_fd = socket_variant(&self->srv0);
1185 ASSERT_LE(0, connect_fd);
1186 EXPECT_EQ(0, connect_variant(connect_fd, &self->srv0));
1187
1188 /* Tries to connect again, or set peer. */
1189 ret = connect_variant(connect_fd, &self->srv0);
1190 if (self->srv0.protocol.type == SOCK_STREAM) {
1191 EXPECT_EQ(-EISCONN, ret);
1192 } else {
1193 EXPECT_EQ(0, ret);
1194 }
1195
1196 if (variant->sandbox == TCP_SANDBOX ||
1197 variant->sandbox == UDP_SANDBOX) {
1198 const int ruleset_fd = landlock_create_ruleset(
1199 &ruleset_conn, sizeof(ruleset_conn), 0);
1200 ASSERT_LE(0, ruleset_fd);
1201
1202 /* Allows connect. */
1203 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
1204 LANDLOCK_RULE_NET_PORT,
1205 &rule_connect, 0));
1206 enforce_ruleset(_metadata, ruleset_fd);
1207 EXPECT_EQ(0, close(ruleset_fd));
1208 }
1209
1210 /* Disconnects already connected socket, or set peer. */
1211 ret = connect_variant(connect_fd, &self->unspec_any0);
1212 if (self->srv0.protocol.domain == AF_UNIX &&
1213 self->srv0.protocol.type == SOCK_STREAM) {
1214 EXPECT_EQ(-EINVAL, ret);
1215 } else {
1216 EXPECT_EQ(0, ret);
1217 }
1218
1219 /* Tries to reconnect, or set peer. */
1220 ret = connect_variant(connect_fd, &self->srv0);
1221 if (self->srv0.protocol.domain == AF_UNIX &&
1222 self->srv0.protocol.type == SOCK_STREAM) {
1223 EXPECT_EQ(-EISCONN, ret);
1224 } else {
1225 EXPECT_EQ(0, ret);
1226 }
1227
1228 if (variant->sandbox == TCP_SANDBOX ||
1229 variant->sandbox == UDP_SANDBOX) {
1230 const int ruleset_fd = landlock_create_ruleset(
1231 &ruleset_conn_bind, sizeof(ruleset_conn_bind),
1232 0);
1233 ASSERT_LE(0, ruleset_fd);
1234
1235 /* Denies connect and bind. */
1236 enforce_ruleset(_metadata, ruleset_fd);
1237 EXPECT_EQ(0, close(ruleset_fd));
1238 }
1239
1240 /* Try to re-disconnect with a truncated address struct. */
1241 EXPECT_EQ(-EINVAL,
1242 connect_variant_addrlen(
1243 connect_fd, &self->unspec_any0,
1244 get_addrlen(&self->unspec_any0, true) - 1));
1245
1246 /*
1247 * Re-disconnect, with a minimal sockaddr struct (just a
1248 * bare af_family=AF_UNSPEC field).
1249 */
1250 ret = connect_variant_addrlen(connect_fd, &self->unspec_any0,
1251 get_addrlen(&self->unspec_any0,
1252 true));
1253 if (self->srv0.protocol.domain == AF_UNIX &&
1254 self->srv0.protocol.type == SOCK_STREAM) {
1255 EXPECT_EQ(-EINVAL, ret);
1256 } else {
1257 /* Always allowed to disconnect. */
1258 EXPECT_EQ(0, ret);
1259 }
1260
1261 EXPECT_EQ(0, close(connect_fd));
1262 _exit(_metadata->exit_code);
1263 return;
1264 }
1265
1266 client_fd = bind_fd;
1267 if (self->srv0.protocol.type == SOCK_STREAM) {
1268 client_fd = accept(bind_fd, NULL, 0);
1269 ASSERT_LE(0, client_fd);
1270 }
1271
1272 EXPECT_EQ(child, waitpid(child, &status, 0));
1273 EXPECT_EQ(1, WIFEXITED(status));
1274 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1275
1276 /* Closes connection, if any. */
1277 if (client_fd != bind_fd)
1278 EXPECT_LE(0, close(client_fd));
1279
1280 /* Closes listening socket. */
1281 EXPECT_EQ(0, close(bind_fd));
1282 }
1283
TEST_F(protocol,tcp_fastopen)1284 TEST_F(protocol, tcp_fastopen)
1285 {
1286 const bool restricted = variant->sandbox == TCP_SANDBOX &&
1287 variant->prot.type == SOCK_STREAM &&
1288 (variant->prot.protocol == IPPROTO_TCP ||
1289 variant->prot.protocol == IPPROTO_IP) &&
1290 (variant->prot.domain == AF_INET ||
1291 variant->prot.domain == AF_INET6);
1292 const struct landlock_ruleset_attr ruleset_attr = {
1293 .handled_access_net = LANDLOCK_ACCESS_NET_CONNECT_TCP,
1294 };
1295 int bind_fd, client_fd, status;
1296 char buf;
1297 pid_t child;
1298
1299 bind_fd = socket_variant(&self->srv0);
1300 ASSERT_LE(0, bind_fd);
1301 EXPECT_EQ(0, bind_variant(bind_fd, &self->srv0));
1302 if (self->srv0.protocol.type == SOCK_STREAM)
1303 EXPECT_EQ(0, listen(bind_fd, backlog));
1304
1305 child = fork();
1306 ASSERT_LE(0, child);
1307 if (child == 0) {
1308 int connect_fd, ret;
1309
1310 /* Closes listening socket for the child. */
1311 EXPECT_EQ(0, close(bind_fd));
1312
1313 connect_fd = socket_variant(&self->srv0);
1314 ASSERT_LE(0, connect_fd);
1315
1316 if (variant->sandbox == TCP_SANDBOX) {
1317 const int ruleset_fd = landlock_create_ruleset(
1318 &ruleset_attr, sizeof(ruleset_attr), 0);
1319 ASSERT_LE(0, ruleset_fd);
1320
1321 enforce_ruleset(_metadata, ruleset_fd);
1322 EXPECT_EQ(0, close(ruleset_fd));
1323 }
1324
1325 /* Fast Open with no address. */
1326 ret = sendto_variant(connect_fd, NULL, NULL, 0, MSG_FASTOPEN);
1327 if (self->srv0.protocol.domain == AF_UNIX) {
1328 EXPECT_EQ(-ENOTCONN, ret);
1329 } else if (self->srv0.protocol.type == SOCK_DGRAM) {
1330 EXPECT_EQ(-EDESTADDRREQ, ret);
1331 } else {
1332 EXPECT_EQ(-EINVAL, ret);
1333 }
1334
1335 /* Fast Open to a denied address. */
1336 ret = sendto_variant(connect_fd, &self->srv0, "A", 1,
1337 MSG_FASTOPEN);
1338 if (restricted) {
1339 EXPECT_EQ(-EACCES, ret);
1340 } else if (self->srv0.protocol.domain == AF_UNIX &&
1341 self->srv0.protocol.type == SOCK_STREAM) {
1342 EXPECT_EQ(-EOPNOTSUPP, ret);
1343 } else {
1344 EXPECT_EQ(0, ret);
1345 }
1346
1347 EXPECT_EQ(0, close(connect_fd));
1348 _exit(_metadata->exit_code);
1349 return;
1350 }
1351
1352 client_fd = bind_fd;
1353 if (!restricted && self->srv0.protocol.type == SOCK_STREAM &&
1354 self->srv0.protocol.domain != AF_UNIX) {
1355 client_fd = accept(bind_fd, NULL, 0);
1356 ASSERT_LE(0, client_fd);
1357 }
1358
1359 if (restricted) {
1360 EXPECT_EQ(-1, read(client_fd, &buf, 1));
1361 EXPECT_EQ(ENOTCONN, errno);
1362 } else if (self->srv0.protocol.domain == AF_UNIX &&
1363 self->srv0.protocol.type == SOCK_STREAM) {
1364 EXPECT_EQ(-1, read(client_fd, &buf, 1));
1365 EXPECT_EQ(EINVAL, errno);
1366 } else {
1367 EXPECT_EQ(1, read(client_fd, &buf, 1));
1368 EXPECT_EQ('A', buf);
1369 }
1370
1371 EXPECT_EQ(child, waitpid(child, &status, 0));
1372 EXPECT_EQ(1, WIFEXITED(status));
1373 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1374
1375 if (client_fd != bind_fd)
1376 EXPECT_LE(0, close(client_fd));
1377
1378 EXPECT_EQ(0, close(bind_fd));
1379 }
1380
TEST_F(protocol,sendmsg_stream)1381 TEST_F(protocol, sendmsg_stream)
1382 {
1383 int srv0_fd, tmp_fd, client_fd, res;
1384 char read_buf[1] = { 0 };
1385
1386 /*
1387 * Simple test for stream sockets: just deny all connect()/
1388 * send(explicit addr)/bind(), and make sure we don't interfere with any
1389 * operation.
1390 */
1391 if (variant->prot.type != SOCK_STREAM)
1392 return;
1393
1394 if (variant->sandbox == UDP_SANDBOX) {
1395 const struct landlock_ruleset_attr ruleset_attr = {
1396 .handled_access_net =
1397 LANDLOCK_ACCESS_NET_BIND_UDP |
1398 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1399 };
1400 const int ruleset_fd = landlock_create_ruleset(
1401 &ruleset_attr, sizeof(ruleset_attr), 0);
1402 ASSERT_LE(0, ruleset_fd);
1403 enforce_ruleset(_metadata, ruleset_fd);
1404 EXPECT_EQ(0, close(ruleset_fd));
1405 }
1406
1407 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1408 ASSERT_LE(0, srv0_fd = socket_variant(&self->srv0));
1409 ASSERT_EQ(0, bind_variant(srv0_fd, &self->srv0));
1410 ASSERT_EQ(0, listen(srv0_fd, backlog));
1411
1412 /* Send on a non-connected socket. */
1413 res = sendto_variant(client_fd, NULL, "A", 1, 0);
1414 if (variant->prot.domain == AF_UNIX) {
1415 EXPECT_EQ(-ENOTCONN, res);
1416 } else {
1417 EXPECT_EQ(-EPIPE, res);
1418 }
1419
1420 /* Send to a truncated (invalid) address on a non-connected socket. */
1421 res = sendto_variant_addrlen(client_fd, &self->srv0,
1422 get_addrlen(&self->srv0, true) - 1, "B", 1,
1423 0);
1424 if (variant->prot.domain == AF_UNIX) {
1425 EXPECT_EQ(-EOPNOTSUPP, res);
1426 } else {
1427 EXPECT_EQ(-EPIPE, res);
1428 }
1429
1430 /* Connect. */
1431 ASSERT_EQ(0, connect_variant(client_fd, &self->srv0));
1432 tmp_fd = accept(srv0_fd, NULL, 0);
1433 ASSERT_LE(0, tmp_fd);
1434 EXPECT_EQ(0, close(srv0_fd));
1435 srv0_fd = tmp_fd;
1436
1437 /* Send without an explicit address. */
1438 EXPECT_EQ(0, sendto_variant(client_fd, NULL, "C", 1, 0));
1439 EXPECT_EQ(1, recv(srv0_fd, read_buf, 1, 0))
1440 {
1441 TH_LOG("recv() failed: %s", strerror(errno));
1442 }
1443 EXPECT_EQ(read_buf[0], 'C');
1444
1445 /* Send to a truncated (invalid) address. */
1446 res = sendto_variant_addrlen(client_fd, &self->srv0,
1447 get_addrlen(&self->srv0, true) - 1, "D", 1,
1448 0);
1449 if (variant->prot.domain == AF_UNIX) {
1450 EXPECT_EQ(-EISCONN, res);
1451 } else {
1452 ASSERT_EQ(0, res);
1453 EXPECT_EQ(1, recv(srv0_fd, read_buf, 1, 0))
1454 {
1455 TH_LOG("recv() failed: %s", strerror(errno));
1456 }
1457 EXPECT_EQ(read_buf[0], 'D');
1458 }
1459
1460 /* Send to a valid but different address. */
1461 res = sendto_variant(client_fd, &self->srv1, "E", 1, 0);
1462 if (variant->prot.domain == AF_UNIX) {
1463 EXPECT_EQ(-EISCONN, res);
1464 } else {
1465 ASSERT_EQ(0, res);
1466 EXPECT_EQ(1, recv(srv0_fd, read_buf, 1, 0))
1467 {
1468 TH_LOG("recv() failed: %s", strerror(errno));
1469 }
1470 EXPECT_EQ(read_buf[0], 'E');
1471 }
1472
1473 EXPECT_EQ(0, close(client_fd));
1474 }
1475
TEST_F(protocol,sendmsg_dgram)1476 TEST_F(protocol, sendmsg_dgram)
1477 {
1478 const bool restricted = is_restricted(&variant->prot, variant->sandbox);
1479 int srv0_fd, srv1_fd, client_fd, child, status, res;
1480
1481 if (variant->prot.type != SOCK_DGRAM)
1482 return;
1483
1484 /* Prepare server on port #0 to be allowed. */
1485 ASSERT_LE(0, srv0_fd = socket_variant(&self->srv0));
1486 ASSERT_EQ(0, bind_variant(srv0_fd, &self->srv0));
1487
1488 /* And another server on port #1 to be denied. */
1489 ASSERT_LE(0, srv1_fd = socket_variant(&self->srv1));
1490 ASSERT_EQ(0, bind_variant(srv1_fd, &self->srv1));
1491
1492 /*
1493 * Check that sockets connected before restrictions are not impacted in
1494 * any way.
1495 */
1496 child = fork();
1497 ASSERT_LE(0, child);
1498 if (child == 0) {
1499 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1500 ASSERT_EQ(0, connect_variant(client_fd, &self->srv0));
1501 if (variant->sandbox == UDP_SANDBOX) {
1502 /* Deny all connect()/send(explicit addr)/bind(). */
1503 const struct landlock_ruleset_attr ruleset_attr = {
1504 .handled_access_net =
1505 LANDLOCK_ACCESS_NET_BIND_UDP |
1506 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1507 };
1508 const int ruleset_fd = landlock_create_ruleset(
1509 &ruleset_attr, sizeof(ruleset_attr), 0);
1510 ASSERT_LE(0, ruleset_fd);
1511 enforce_ruleset(_metadata, ruleset_fd);
1512 EXPECT_EQ(0, close(ruleset_fd));
1513 }
1514 EXPECT_EQ(0,
1515 test_sendmsg(_metadata, &variant->prot, client_fd,
1516 srv0_fd, NULL, restricted, restricted));
1517 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1518 srv0_fd, &self->srv0, restricted,
1519 restricted));
1520 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1521 srv1_fd, &self->srv1, restricted,
1522 restricted));
1523 EXPECT_EQ(0, close(client_fd));
1524 _exit(_metadata->exit_code);
1525 }
1526 EXPECT_EQ(child, waitpid(child, &status, 0));
1527 EXPECT_EQ(1, WIFEXITED(status));
1528 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1529
1530 /*
1531 * Restrict connect/send, but not bind(). Then try sending with no
1532 * destination (and no remote peer set), an allowed destination, then a
1533 * denied destination.
1534 */
1535 child = fork();
1536 ASSERT_LE(0, child);
1537 if (child == 0) {
1538 if (variant->sandbox == UDP_SANDBOX) {
1539 const struct landlock_ruleset_attr ruleset_attr = {
1540 .handled_access_net =
1541 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1542 };
1543 const struct landlock_net_port_attr send_p0 = {
1544 .allowed_access =
1545 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1546 .port = self->srv0.port,
1547 };
1548 const int ruleset_fd = landlock_create_ruleset(
1549 &ruleset_attr, sizeof(ruleset_attr), 0);
1550 ASSERT_LE(0, ruleset_fd);
1551 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
1552 LANDLOCK_RULE_NET_PORT,
1553 &send_p0, 0));
1554 enforce_ruleset(_metadata, ruleset_fd);
1555 EXPECT_EQ(0, close(ruleset_fd));
1556 }
1557 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1558 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1559 -1, NULL, false, false));
1560 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1561 srv0_fd, &self->srv0, false, false));
1562 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1563 srv1_fd, &self->srv1, false,
1564 restricted));
1565 EXPECT_EQ(0, close(client_fd));
1566 _exit(_metadata->exit_code);
1567 return;
1568 }
1569 EXPECT_EQ(child, waitpid(child, &status, 0));
1570 EXPECT_EQ(1, WIFEXITED(status));
1571 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1572
1573 /*
1574 * Rest of this test is just for autobind enforcement, which only exists
1575 * in IP sockets.
1576 */
1577 if (variant->prot.domain != AF_INET && variant->prot.domain != AF_INET6)
1578 return;
1579
1580 /* Restrict bind() to explicit calls with an arbitrary (non-0) port. */
1581 child = fork();
1582 ASSERT_LE(0, child);
1583 if (child == 0) {
1584 const uint16_t allowed_src_port = 42424;
1585 struct service_fixture allowed_src;
1586
1587 allowed_src = self->srv0;
1588 set_port(&allowed_src, allowed_src_port);
1589 if (variant->sandbox == UDP_SANDBOX) {
1590 const struct landlock_ruleset_attr ruleset_attr = {
1591 .handled_access_net =
1592 LANDLOCK_ACCESS_NET_BIND_UDP,
1593 };
1594 const struct landlock_net_port_attr rule = {
1595 .allowed_access = LANDLOCK_ACCESS_NET_BIND_UDP,
1596 .port = allowed_src_port,
1597 };
1598 const int ruleset_fd = landlock_create_ruleset(
1599 &ruleset_attr, sizeof(ruleset_attr), 0);
1600 ASSERT_LE(0, ruleset_fd);
1601 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
1602 LANDLOCK_RULE_NET_PORT,
1603 &rule, 0));
1604 enforce_ruleset(_metadata, ruleset_fd);
1605 EXPECT_EQ(0, close(ruleset_fd));
1606 }
1607 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1608
1609 /* Check that implicit bind(0) in sendmsg() is denied. */
1610 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1611 srv0_fd, &self->srv0, restricted,
1612 false));
1613
1614 /* Same thing for autobind in connect(). */
1615 res = connect_variant(client_fd, &self->srv0);
1616 if (restricted) {
1617 EXPECT_EQ(-EACCES, res);
1618 } else {
1619 EXPECT_EQ(0, res);
1620 }
1621 EXPECT_EQ(0, close(client_fd));
1622
1623 /* Make sendmsg() work by explicitly binding to the only allowed port. */
1624 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1625 EXPECT_EQ(0, bind_variant(client_fd, &allowed_src));
1626 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1627 srv0_fd, &self->srv0, restricted,
1628 false));
1629 EXPECT_EQ(0, close(client_fd));
1630
1631 /* Make connect() work by explicitly binding to the only allowed port. */
1632 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1633 EXPECT_EQ(0, bind_variant(client_fd, &allowed_src));
1634 EXPECT_EQ(0, connect_variant(client_fd, &self->srv0));
1635 EXPECT_EQ(0, close(client_fd));
1636
1637 _exit(_metadata->exit_code);
1638 return;
1639 }
1640 EXPECT_EQ(child, waitpid(child, &status, 0));
1641 EXPECT_EQ(1, WIFEXITED(status));
1642 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1643
1644 /*
1645 * Check that %LANDLOCK_ACCESS_NET_BIND_UDP on port 0 allows implicit
1646 * autobinds.
1647 */
1648 child = fork();
1649 ASSERT_LE(0, child);
1650 if (child == 0) {
1651 if (variant->sandbox == UDP_SANDBOX) {
1652 const struct landlock_ruleset_attr ruleset_attr = {
1653 .handled_access_net =
1654 LANDLOCK_ACCESS_NET_BIND_UDP,
1655 };
1656 const struct landlock_net_port_attr rule = {
1657 .allowed_access = LANDLOCK_ACCESS_NET_BIND_UDP,
1658 .port = 0,
1659 };
1660 const int ruleset_fd = landlock_create_ruleset(
1661 &ruleset_attr, sizeof(ruleset_attr), 0);
1662 ASSERT_LE(0, ruleset_fd);
1663 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
1664 LANDLOCK_RULE_NET_PORT,
1665 &rule, 0));
1666 enforce_ruleset(_metadata, ruleset_fd);
1667 EXPECT_EQ(0, close(ruleset_fd));
1668 }
1669 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1670 EXPECT_EQ(0, test_sendmsg(_metadata, &variant->prot, client_fd,
1671 srv0_fd, &self->srv0, false, false));
1672 EXPECT_EQ(0, close(client_fd));
1673 _exit(_metadata->exit_code);
1674 }
1675 EXPECT_EQ(child, waitpid(child, &status, 0));
1676 EXPECT_EQ(1, WIFEXITED(status));
1677 EXPECT_EQ(EXIT_SUCCESS, WEXITSTATUS(status));
1678 }
1679
TEST_F(protocol,sendmsg_unspec)1680 TEST_F(protocol, sendmsg_unspec)
1681 {
1682 const bool restricted = is_restricted(&variant->prot, variant->sandbox);
1683 int client_fd, srv0_fd, srv1_fd, res;
1684 char read_buf[1] = { 0 };
1685
1686 /*
1687 * We already test for the absence of influence on sendmsg for other
1688 * socket types and other address families, there's no point in adapting
1689 * this test for stream sockets too.
1690 */
1691 if (variant->prot.type != SOCK_DGRAM)
1692 return;
1693
1694 /* Prepare client of the right family. */
1695 ASSERT_LE(0, client_fd = socket_variant(&self->srv0));
1696
1697 /* Prepare server on port #0 to be allowed. */
1698 ASSERT_LE(0, srv0_fd = socket_variant(&self->srv0));
1699 ASSERT_EQ(0, bind_variant(srv0_fd, &self->srv0));
1700
1701 /* And another server on port #1 to be denied. */
1702 ASSERT_LE(0, srv1_fd = socket_variant(&self->srv1));
1703 ASSERT_EQ(0, bind_variant(srv1_fd, &self->srv1));
1704
1705 if (variant->sandbox == UDP_SANDBOX) {
1706 const struct landlock_ruleset_attr ruleset_attr = {
1707 .handled_access_net =
1708 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1709 };
1710 const struct landlock_net_port_attr rule = {
1711 .allowed_access = LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
1712 .port = self->srv0.port,
1713 };
1714 const int ruleset_fd = landlock_create_ruleset(
1715 &ruleset_attr, sizeof(ruleset_attr), 0);
1716 ASSERT_LE(0, ruleset_fd);
1717 ASSERT_EQ(0,
1718 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
1719 &rule, 0));
1720 enforce_ruleset(_metadata, ruleset_fd);
1721 EXPECT_EQ(0, close(ruleset_fd));
1722 }
1723
1724 /* Explicit AF_UNSPEC address but truncated. */
1725 EXPECT_EQ(-EINVAL, sendto_variant_addrlen(
1726 client_fd, &self->unspec_srv0,
1727 get_addrlen(&self->unspec_srv0, true) - 1,
1728 "A", 1, 0));
1729
1730 /*
1731 * Explicit AF_UNSPEC address, should be treated as AF_INET by IPv4
1732 * sockets (and thus map to srv0, allowed), but be denied by IPv6
1733 * sockets.
1734 */
1735 res = sendto_variant(client_fd, &self->unspec_srv0, "B", 1, 0);
1736 if (variant->prot.domain == AF_INET6) {
1737 if (restricted) {
1738 /* Always denied on IPv6 socket. */
1739 EXPECT_EQ(-EACCES, res);
1740 } else {
1741 /* IPv6 sockets treat AF_UNSPEC as a NULL address. */
1742 EXPECT_EQ(-EDESTADDRREQ, res);
1743 }
1744 } else if (variant->prot.domain == AF_INET) {
1745 ASSERT_EQ(0, res);
1746 EXPECT_EQ(1, read(srv0_fd, read_buf, 1))
1747 {
1748 TH_LOG("read() failed: %s", strerror(errno));
1749 }
1750 EXPECT_EQ(read_buf[0], 'B');
1751 } else {
1752 /* Unix sockets don't accept AF_UNSPEC. */
1753 EXPECT_EQ(-EINVAL, res);
1754 }
1755
1756 /*
1757 * Explicit AF_UNSPEC address, should be treated as AF_INET on IPv4
1758 * sockets (and thus map to srv1, denied), and be denied on IPv6 sockets
1759 * as always.
1760 */
1761 res = sendto_variant(client_fd, &self->unspec_srv1, "C", 1, 0);
1762 if (variant->prot.domain == AF_INET6) {
1763 if (restricted) {
1764 /* Always denied on IPv6 socket. */
1765 EXPECT_EQ(-EACCES, res);
1766 } else {
1767 /* IPv6 sockets treat AF_UNSPEC as a NULL address. */
1768 EXPECT_EQ(-EDESTADDRREQ, res);
1769 }
1770 } else if (variant->prot.domain == AF_INET) {
1771 if (restricted) {
1772 /* Sending to srv1 is not allowed, only srv0. */
1773 EXPECT_EQ(-EACCES, res);
1774 } else {
1775 ASSERT_EQ(0, res);
1776 EXPECT_EQ(1, read(srv1_fd, read_buf, 1))
1777 {
1778 TH_LOG("read() failed: %s", strerror(errno));
1779 }
1780 EXPECT_EQ(read_buf[0], 'C');
1781 }
1782 } else {
1783 /* Unix sockets don't accept AF_UNSPEC. */
1784 EXPECT_EQ(-EINVAL, res);
1785 }
1786
1787 ASSERT_EQ(0, connect_variant(client_fd, &self->srv0));
1788
1789 /* Minimal explicit AF_UNSPEC address (just the sa_family_t field) */
1790 res = sendto_variant_addrlen(client_fd, &self->unspec_srv0,
1791 get_addrlen(&self->unspec_srv0, true), "D",
1792 1, 0);
1793 if (variant->prot.domain == AF_INET6) {
1794 if (restricted) {
1795 /* AF_UNSPEC is always denied in IPv6. */
1796 EXPECT_EQ(-EACCES, res);
1797 } else {
1798 /*
1799 * IPv6 sockets treat AF_UNSPEC as a NULL address,
1800 * falling back to the connected address.
1801 */
1802 ASSERT_EQ(0, res);
1803 EXPECT_EQ(1, read(srv0_fd, read_buf, 1));
1804 EXPECT_EQ(read_buf[0], 'D');
1805 }
1806 } else {
1807 /*
1808 * IPv4 socket will expect a struct sockaddr_in, our address is
1809 * considered truncated. And Unix sockets don't accept
1810 * AF_UNSPEC at all.
1811 */
1812 EXPECT_EQ(-EINVAL, res);
1813 }
1814 }
1815
FIXTURE(ipv4)1816 FIXTURE(ipv4)
1817 {
1818 struct service_fixture srv0, srv1;
1819 };
1820
FIXTURE_VARIANT(ipv4)1821 FIXTURE_VARIANT(ipv4)
1822 {
1823 const enum sandbox_type sandbox;
1824 const int type;
1825 };
1826
1827 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,no_sandbox_with_tcp)1828 FIXTURE_VARIANT_ADD(ipv4, no_sandbox_with_tcp) {
1829 /* clang-format on */
1830 .sandbox = NO_SANDBOX,
1831 .type = SOCK_STREAM,
1832 };
1833
1834 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,tcp_sandbox_with_tcp)1835 FIXTURE_VARIANT_ADD(ipv4, tcp_sandbox_with_tcp) {
1836 /* clang-format on */
1837 .sandbox = TCP_SANDBOX,
1838 .type = SOCK_STREAM,
1839 };
1840
1841 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,udp_sandbox_with_tcp)1842 FIXTURE_VARIANT_ADD(ipv4, udp_sandbox_with_tcp) {
1843 /* clang-format on */
1844 .sandbox = UDP_SANDBOX,
1845 .type = SOCK_STREAM,
1846 };
1847
1848 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,no_sandbox_with_udp)1849 FIXTURE_VARIANT_ADD(ipv4, no_sandbox_with_udp) {
1850 /* clang-format on */
1851 .sandbox = NO_SANDBOX,
1852 .type = SOCK_DGRAM,
1853 };
1854
1855 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,tcp_sandbox_with_udp)1856 FIXTURE_VARIANT_ADD(ipv4, tcp_sandbox_with_udp) {
1857 /* clang-format on */
1858 .sandbox = TCP_SANDBOX,
1859 .type = SOCK_DGRAM,
1860 };
1861
1862 /* clang-format off */
FIXTURE_VARIANT_ADD(ipv4,udp_sandbox_with_udp)1863 FIXTURE_VARIANT_ADD(ipv4, udp_sandbox_with_udp) {
1864 /* clang-format on */
1865 .sandbox = UDP_SANDBOX,
1866 .type = SOCK_DGRAM,
1867 };
1868
FIXTURE_SETUP(ipv4)1869 FIXTURE_SETUP(ipv4)
1870 {
1871 const struct protocol_variant prot = {
1872 .domain = AF_INET,
1873 .type = variant->type,
1874 };
1875
1876 disable_caps(_metadata);
1877
1878 set_service(&self->srv0, prot, 0);
1879 set_service(&self->srv1, prot, 1);
1880
1881 setup_loopback(_metadata);
1882 };
1883
FIXTURE_TEARDOWN(ipv4)1884 FIXTURE_TEARDOWN(ipv4)
1885 {
1886 }
1887
TEST_F(ipv4,from_unix_to_inet)1888 TEST_F(ipv4, from_unix_to_inet)
1889 {
1890 int unix_stream_fd, unix_dgram_fd;
1891
1892 if (variant->sandbox == TCP_SANDBOX ||
1893 variant->sandbox == UDP_SANDBOX) {
1894 const __u64 access_rights =
1895 (variant->sandbox == TCP_SANDBOX ?
1896 LANDLOCK_ACCESS_NET_BIND_TCP |
1897 LANDLOCK_ACCESS_NET_CONNECT_TCP :
1898 LANDLOCK_ACCESS_NET_BIND_UDP |
1899 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
1900 const struct landlock_ruleset_attr ruleset_attr = {
1901 .handled_access_net = access_rights,
1902 };
1903 const struct landlock_net_port_attr tcp_bind_connect_p0 = {
1904 .allowed_access = access_rights,
1905 .port = self->srv0.port,
1906 };
1907 int ruleset_fd;
1908
1909 /* Denies connect and bind to check errno value. */
1910 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
1911 sizeof(ruleset_attr), 0);
1912 ASSERT_LE(0, ruleset_fd);
1913
1914 /* Allows connect and bind for srv0. */
1915 ASSERT_EQ(0,
1916 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
1917 &tcp_bind_connect_p0, 0));
1918
1919 enforce_ruleset(_metadata, ruleset_fd);
1920 EXPECT_EQ(0, close(ruleset_fd));
1921 }
1922
1923 unix_stream_fd = socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0);
1924 ASSERT_LE(0, unix_stream_fd);
1925
1926 unix_dgram_fd = socket(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC, 0);
1927 ASSERT_LE(0, unix_dgram_fd);
1928
1929 /* Checks unix stream bind and connect for srv0. */
1930 EXPECT_EQ(-EINVAL, bind_variant(unix_stream_fd, &self->srv0));
1931 EXPECT_EQ(-EINVAL, connect_variant(unix_stream_fd, &self->srv0));
1932
1933 /* Checks unix stream bind and connect for srv1. */
1934 EXPECT_EQ(-EINVAL, bind_variant(unix_stream_fd, &self->srv1))
1935 {
1936 TH_LOG("Wrong bind error: %s", strerror(errno));
1937 }
1938 EXPECT_EQ(-EINVAL, connect_variant(unix_stream_fd, &self->srv1));
1939
1940 /* Checks unix datagram bind and connect for srv0. */
1941 EXPECT_EQ(-EINVAL, bind_variant(unix_dgram_fd, &self->srv0));
1942 EXPECT_EQ(-EINVAL, connect_variant(unix_dgram_fd, &self->srv0));
1943
1944 /* Checks unix datagram bind and connect for srv1. */
1945 EXPECT_EQ(-EINVAL, bind_variant(unix_dgram_fd, &self->srv1));
1946 EXPECT_EQ(-EINVAL, connect_variant(unix_dgram_fd, &self->srv1));
1947 }
1948
FIXTURE(tcp_layers)1949 FIXTURE(tcp_layers)
1950 {
1951 struct service_fixture srv0, srv1;
1952 };
1953
FIXTURE_VARIANT(tcp_layers)1954 FIXTURE_VARIANT(tcp_layers)
1955 {
1956 const size_t num_layers;
1957 const int domain;
1958 };
1959
FIXTURE_SETUP(tcp_layers)1960 FIXTURE_SETUP(tcp_layers)
1961 {
1962 const struct protocol_variant prot = {
1963 .domain = variant->domain,
1964 .type = SOCK_STREAM,
1965 };
1966
1967 disable_caps(_metadata);
1968
1969 ASSERT_EQ(0, set_service(&self->srv0, prot, 0));
1970 ASSERT_EQ(0, set_service(&self->srv1, prot, 1));
1971
1972 setup_loopback(_metadata);
1973 };
1974
FIXTURE_TEARDOWN(tcp_layers)1975 FIXTURE_TEARDOWN(tcp_layers)
1976 {
1977 }
1978
1979 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,no_sandbox_with_ipv4)1980 FIXTURE_VARIANT_ADD(tcp_layers, no_sandbox_with_ipv4) {
1981 /* clang-format on */
1982 .domain = AF_INET,
1983 .num_layers = 0,
1984 };
1985
1986 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,one_sandbox_with_ipv4)1987 FIXTURE_VARIANT_ADD(tcp_layers, one_sandbox_with_ipv4) {
1988 /* clang-format on */
1989 .domain = AF_INET,
1990 .num_layers = 1,
1991 };
1992
1993 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,two_sandboxes_with_ipv4)1994 FIXTURE_VARIANT_ADD(tcp_layers, two_sandboxes_with_ipv4) {
1995 /* clang-format on */
1996 .domain = AF_INET,
1997 .num_layers = 2,
1998 };
1999
2000 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,three_sandboxes_with_ipv4)2001 FIXTURE_VARIANT_ADD(tcp_layers, three_sandboxes_with_ipv4) {
2002 /* clang-format on */
2003 .domain = AF_INET,
2004 .num_layers = 3,
2005 };
2006
2007 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,no_sandbox_with_ipv6)2008 FIXTURE_VARIANT_ADD(tcp_layers, no_sandbox_with_ipv6) {
2009 /* clang-format on */
2010 .domain = AF_INET6,
2011 .num_layers = 0,
2012 };
2013
2014 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,one_sandbox_with_ipv6)2015 FIXTURE_VARIANT_ADD(tcp_layers, one_sandbox_with_ipv6) {
2016 /* clang-format on */
2017 .domain = AF_INET6,
2018 .num_layers = 1,
2019 };
2020
2021 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,two_sandboxes_with_ipv6)2022 FIXTURE_VARIANT_ADD(tcp_layers, two_sandboxes_with_ipv6) {
2023 /* clang-format on */
2024 .domain = AF_INET6,
2025 .num_layers = 2,
2026 };
2027
2028 /* clang-format off */
FIXTURE_VARIANT_ADD(tcp_layers,three_sandboxes_with_ipv6)2029 FIXTURE_VARIANT_ADD(tcp_layers, three_sandboxes_with_ipv6) {
2030 /* clang-format on */
2031 .domain = AF_INET6,
2032 .num_layers = 3,
2033 };
2034
TEST_F(tcp_layers,ruleset_overlap)2035 TEST_F(tcp_layers, ruleset_overlap)
2036 {
2037 const struct landlock_ruleset_attr ruleset_attr = {
2038 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP |
2039 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2040 };
2041 const struct landlock_net_port_attr tcp_bind = {
2042 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2043 .port = self->srv0.port,
2044 };
2045 const struct landlock_net_port_attr tcp_bind_connect = {
2046 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP |
2047 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2048 .port = self->srv0.port,
2049 };
2050
2051 if (variant->num_layers >= 1) {
2052 int ruleset_fd;
2053
2054 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2055 sizeof(ruleset_attr), 0);
2056 ASSERT_LE(0, ruleset_fd);
2057
2058 /* Allows bind. */
2059 ASSERT_EQ(0,
2060 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2061 &tcp_bind, 0));
2062 /* Also allows bind, but allows connect too. */
2063 ASSERT_EQ(0,
2064 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2065 &tcp_bind_connect, 0));
2066 enforce_ruleset(_metadata, ruleset_fd);
2067 EXPECT_EQ(0, close(ruleset_fd));
2068 }
2069
2070 if (variant->num_layers >= 2) {
2071 int ruleset_fd;
2072
2073 /* Creates another ruleset layer. */
2074 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2075 sizeof(ruleset_attr), 0);
2076 ASSERT_LE(0, ruleset_fd);
2077
2078 /* Only allows bind. */
2079 ASSERT_EQ(0,
2080 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2081 &tcp_bind, 0));
2082 enforce_ruleset(_metadata, ruleset_fd);
2083 EXPECT_EQ(0, close(ruleset_fd));
2084 }
2085
2086 if (variant->num_layers >= 3) {
2087 int ruleset_fd;
2088
2089 /* Creates another ruleset layer. */
2090 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2091 sizeof(ruleset_attr), 0);
2092 ASSERT_LE(0, ruleset_fd);
2093
2094 /* Try to allow bind and connect. */
2095 ASSERT_EQ(0,
2096 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2097 &tcp_bind_connect, 0));
2098 enforce_ruleset(_metadata, ruleset_fd);
2099 EXPECT_EQ(0, close(ruleset_fd));
2100 }
2101
2102 /*
2103 * Forbids to connect to the socket because only one ruleset layer
2104 * allows connect.
2105 */
2106 test_bind_and_connect(_metadata, &self->srv0, false,
2107 variant->num_layers >= 2);
2108 }
2109
TEST_F(tcp_layers,ruleset_expand)2110 TEST_F(tcp_layers, ruleset_expand)
2111 {
2112 if (variant->num_layers >= 1) {
2113 const struct landlock_ruleset_attr ruleset_attr = {
2114 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP,
2115 };
2116 /* Allows bind for srv0. */
2117 const struct landlock_net_port_attr bind_srv0 = {
2118 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2119 .port = self->srv0.port,
2120 };
2121 int ruleset_fd;
2122
2123 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2124 sizeof(ruleset_attr), 0);
2125 ASSERT_LE(0, ruleset_fd);
2126 ASSERT_EQ(0,
2127 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2128 &bind_srv0, 0));
2129 enforce_ruleset(_metadata, ruleset_fd);
2130 EXPECT_EQ(0, close(ruleset_fd));
2131 }
2132
2133 if (variant->num_layers >= 2) {
2134 /* Expands network mask with connect action. */
2135 const struct landlock_ruleset_attr ruleset_attr = {
2136 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP |
2137 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2138 };
2139 /* Allows bind for srv0 and connect to srv0. */
2140 const struct landlock_net_port_attr tcp_bind_connect_p0 = {
2141 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP |
2142 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2143 .port = self->srv0.port,
2144 };
2145 /* Try to allow bind for srv1. */
2146 const struct landlock_net_port_attr tcp_bind_p1 = {
2147 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2148 .port = self->srv1.port,
2149 };
2150 int ruleset_fd;
2151
2152 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2153 sizeof(ruleset_attr), 0);
2154 ASSERT_LE(0, ruleset_fd);
2155 ASSERT_EQ(0,
2156 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2157 &tcp_bind_connect_p0, 0));
2158 ASSERT_EQ(0,
2159 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2160 &tcp_bind_p1, 0));
2161 enforce_ruleset(_metadata, ruleset_fd);
2162 EXPECT_EQ(0, close(ruleset_fd));
2163 }
2164
2165 if (variant->num_layers >= 3) {
2166 const struct landlock_ruleset_attr ruleset_attr = {
2167 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP |
2168 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2169 };
2170 /* Allows connect to srv0, without bind rule. */
2171 const struct landlock_net_port_attr tcp_bind_p0 = {
2172 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2173 .port = self->srv0.port,
2174 };
2175 int ruleset_fd;
2176
2177 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2178 sizeof(ruleset_attr), 0);
2179 ASSERT_LE(0, ruleset_fd);
2180 ASSERT_EQ(0,
2181 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2182 &tcp_bind_p0, 0));
2183 enforce_ruleset(_metadata, ruleset_fd);
2184 EXPECT_EQ(0, close(ruleset_fd));
2185 }
2186
2187 test_bind_and_connect(_metadata, &self->srv0, false,
2188 variant->num_layers >= 3);
2189
2190 test_bind_and_connect(_metadata, &self->srv1, variant->num_layers >= 1,
2191 variant->num_layers >= 2);
2192 }
2193
2194 /* clang-format off */
FIXTURE(mini)2195 FIXTURE(mini) {};
2196 /* clang-format on */
2197
FIXTURE_SETUP(mini)2198 FIXTURE_SETUP(mini)
2199 {
2200 disable_caps(_metadata);
2201
2202 setup_loopback(_metadata);
2203 };
2204
FIXTURE_TEARDOWN(mini)2205 FIXTURE_TEARDOWN(mini)
2206 {
2207 }
2208
2209 /* clang-format off */
2210
2211 #define ACCESS_LAST LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP
2212
2213 #define ACCESS_ALL ( \
2214 LANDLOCK_ACCESS_NET_BIND_TCP | \
2215 LANDLOCK_ACCESS_NET_CONNECT_TCP | \
2216 LANDLOCK_ACCESS_NET_BIND_UDP | \
2217 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP)
2218
2219 /* clang-format on */
2220
TEST_F(mini,network_access_rights)2221 TEST_F(mini, network_access_rights)
2222 {
2223 const struct landlock_ruleset_attr ruleset_attr = {
2224 .handled_access_net = ACCESS_ALL,
2225 };
2226 struct landlock_net_port_attr net_port = {
2227 .port = sock_port_start,
2228 };
2229 int ruleset_fd;
2230 __u64 access;
2231
2232 ruleset_fd =
2233 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2234 ASSERT_LE(0, ruleset_fd);
2235
2236 for (access = 1; access <= ACCESS_LAST; access <<= 1) {
2237 net_port.allowed_access = access;
2238 EXPECT_EQ(0,
2239 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2240 &net_port, 0))
2241 {
2242 TH_LOG("Failed to add rule with access 0x%llx: %s",
2243 (unsigned long long)access, strerror(errno));
2244 }
2245 }
2246 EXPECT_EQ(0, close(ruleset_fd));
2247 }
2248
2249 /* Checks invalid attribute, out of landlock network access range. */
TEST_F(mini,ruleset_with_unknown_access)2250 TEST_F(mini, ruleset_with_unknown_access)
2251 {
2252 __u64 access_mask;
2253
2254 for (access_mask = 1ULL << 63; access_mask != ACCESS_LAST;
2255 access_mask >>= 1) {
2256 const struct landlock_ruleset_attr ruleset_attr = {
2257 .handled_access_net = access_mask,
2258 };
2259
2260 EXPECT_EQ(-1, landlock_create_ruleset(&ruleset_attr,
2261 sizeof(ruleset_attr), 0));
2262 EXPECT_EQ(EINVAL, errno);
2263 }
2264 }
2265
TEST_F(mini,rule_with_unknown_access)2266 TEST_F(mini, rule_with_unknown_access)
2267 {
2268 const struct landlock_ruleset_attr ruleset_attr = {
2269 .handled_access_net = ACCESS_ALL,
2270 };
2271 struct landlock_net_port_attr net_port = {
2272 .port = sock_port_start,
2273 };
2274 int ruleset_fd;
2275 __u64 access;
2276
2277 ruleset_fd =
2278 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2279 ASSERT_LE(0, ruleset_fd);
2280
2281 for (access = 1ULL << 63; access != ACCESS_LAST; access >>= 1) {
2282 net_port.allowed_access = access;
2283 EXPECT_EQ(-1,
2284 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2285 &net_port, 0));
2286 EXPECT_EQ(EINVAL, errno);
2287 }
2288 EXPECT_EQ(0, close(ruleset_fd));
2289 }
2290
TEST_F(mini,rule_with_unhandled_access)2291 TEST_F(mini, rule_with_unhandled_access)
2292 {
2293 struct landlock_ruleset_attr ruleset_attr = {
2294 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP,
2295 };
2296 struct landlock_net_port_attr net_port = {
2297 .port = sock_port_start,
2298 };
2299 int ruleset_fd;
2300 __u64 access;
2301
2302 ruleset_fd =
2303 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2304 ASSERT_LE(0, ruleset_fd);
2305
2306 for (access = 1; access > 0; access <<= 1) {
2307 int err;
2308
2309 net_port.allowed_access = access;
2310 err = landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2311 &net_port, 0);
2312 if (access == ruleset_attr.handled_access_net) {
2313 EXPECT_EQ(0, err);
2314 } else {
2315 EXPECT_EQ(-1, err);
2316 EXPECT_EQ(EINVAL, errno);
2317 }
2318 }
2319
2320 EXPECT_EQ(0, close(ruleset_fd));
2321 }
2322
TEST_F(mini,inval)2323 TEST_F(mini, inval)
2324 {
2325 const struct landlock_ruleset_attr ruleset_attr = {
2326 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP
2327 };
2328 const struct landlock_net_port_attr tcp_bind_connect = {
2329 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP |
2330 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2331 .port = sock_port_start,
2332 };
2333 const struct landlock_net_port_attr tcp_denied = {
2334 .allowed_access = 0,
2335 .port = sock_port_start,
2336 };
2337 const struct landlock_net_port_attr tcp_bind = {
2338 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2339 .port = sock_port_start,
2340 };
2341 int ruleset_fd;
2342
2343 ruleset_fd =
2344 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2345 ASSERT_LE(0, ruleset_fd);
2346
2347 /* Checks unhandled allowed_access. */
2348 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2349 &tcp_bind_connect, 0));
2350 EXPECT_EQ(EINVAL, errno);
2351
2352 /* Checks zero access value. */
2353 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2354 &tcp_denied, 0));
2355 EXPECT_EQ(ENOMSG, errno);
2356
2357 /* Adds with legitimate values. */
2358 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2359 &tcp_bind, 0));
2360 }
2361
TEST_F(mini,tcp_port_overflow)2362 TEST_F(mini, tcp_port_overflow)
2363 {
2364 const struct landlock_ruleset_attr ruleset_attr = {
2365 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP |
2366 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2367 };
2368 const struct landlock_net_port_attr port_max_bind = {
2369 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2370 .port = UINT16_MAX,
2371 };
2372 const struct landlock_net_port_attr port_max_connect = {
2373 .allowed_access = LANDLOCK_ACCESS_NET_CONNECT_TCP,
2374 .port = UINT16_MAX,
2375 };
2376 const struct landlock_net_port_attr port_overflow1 = {
2377 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2378 .port = UINT16_MAX + 1,
2379 };
2380 const struct landlock_net_port_attr port_overflow2 = {
2381 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2382 .port = UINT16_MAX + 2,
2383 };
2384 const struct landlock_net_port_attr port_overflow3 = {
2385 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2386 .port = UINT32_MAX + 1UL,
2387 };
2388 const struct landlock_net_port_attr port_overflow4 = {
2389 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2390 .port = UINT32_MAX + 2UL,
2391 };
2392 const struct protocol_variant ipv4_tcp = {
2393 .domain = AF_INET,
2394 .type = SOCK_STREAM,
2395 };
2396 struct service_fixture srv_denied, srv_max_allowed;
2397 int ruleset_fd;
2398
2399 ASSERT_EQ(0, set_service(&srv_denied, ipv4_tcp, 0));
2400
2401 /* Be careful to avoid port inconsistencies. */
2402 srv_max_allowed = srv_denied;
2403 srv_max_allowed.port = port_max_bind.port;
2404 srv_max_allowed.ipv4_addr.sin_port = htons(port_max_bind.port);
2405
2406 ruleset_fd =
2407 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2408 ASSERT_LE(0, ruleset_fd);
2409
2410 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2411 &port_max_bind, 0));
2412
2413 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2414 &port_overflow1, 0));
2415 EXPECT_EQ(EINVAL, errno);
2416
2417 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2418 &port_overflow2, 0));
2419 EXPECT_EQ(EINVAL, errno);
2420
2421 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2422 &port_overflow3, 0));
2423 EXPECT_EQ(EINVAL, errno);
2424
2425 /* Interleaves with invalid rule additions. */
2426 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2427 &port_max_connect, 0));
2428
2429 EXPECT_EQ(-1, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2430 &port_overflow4, 0));
2431 EXPECT_EQ(EINVAL, errno);
2432
2433 enforce_ruleset(_metadata, ruleset_fd);
2434
2435 test_bind_and_connect(_metadata, &srv_denied, true, true);
2436 test_bind_and_connect(_metadata, &srv_max_allowed, false, false);
2437 }
2438
FIXTURE(ipv4_tcp)2439 FIXTURE(ipv4_tcp)
2440 {
2441 struct service_fixture srv0, srv1;
2442 };
2443
FIXTURE_SETUP(ipv4_tcp)2444 FIXTURE_SETUP(ipv4_tcp)
2445 {
2446 const struct protocol_variant ipv4_tcp = {
2447 .domain = AF_INET,
2448 .type = SOCK_STREAM,
2449 };
2450
2451 disable_caps(_metadata);
2452
2453 ASSERT_EQ(0, set_service(&self->srv0, ipv4_tcp, 0));
2454 ASSERT_EQ(0, set_service(&self->srv1, ipv4_tcp, 1));
2455
2456 setup_loopback(_metadata);
2457 };
2458
FIXTURE_TEARDOWN(ipv4_tcp)2459 FIXTURE_TEARDOWN(ipv4_tcp)
2460 {
2461 }
2462
TEST_F(ipv4_tcp,port_endianness)2463 TEST_F(ipv4_tcp, port_endianness)
2464 {
2465 const struct landlock_ruleset_attr ruleset_attr = {
2466 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP |
2467 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2468 };
2469 const struct landlock_net_port_attr bind_host_endian_p0 = {
2470 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2471 /* Host port format. */
2472 .port = self->srv0.port,
2473 };
2474 const struct landlock_net_port_attr connect_big_endian_p0 = {
2475 .allowed_access = LANDLOCK_ACCESS_NET_CONNECT_TCP,
2476 /* Big endian port format. */
2477 .port = htons(self->srv0.port),
2478 };
2479 const struct landlock_net_port_attr bind_connect_host_endian_p1 = {
2480 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP |
2481 LANDLOCK_ACCESS_NET_CONNECT_TCP,
2482 /* Host port format. */
2483 .port = self->srv1.port,
2484 };
2485 const unsigned int one = 1;
2486 const char little_endian = *(const char *)&one;
2487 int ruleset_fd;
2488
2489 ruleset_fd =
2490 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2491 ASSERT_LE(0, ruleset_fd);
2492 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2493 &bind_host_endian_p0, 0));
2494 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2495 &connect_big_endian_p0, 0));
2496 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2497 &bind_connect_host_endian_p1, 0));
2498 enforce_ruleset(_metadata, ruleset_fd);
2499
2500 /* No restriction for big endinan CPU. */
2501 test_bind_and_connect(_metadata, &self->srv0, false, little_endian);
2502
2503 /* No restriction for any CPU. */
2504 test_bind_and_connect(_metadata, &self->srv1, false, false);
2505 }
2506
TEST_F(ipv4_tcp,with_fs)2507 TEST_F(ipv4_tcp, with_fs)
2508 {
2509 const struct landlock_ruleset_attr ruleset_attr_fs_net = {
2510 .handled_access_fs = LANDLOCK_ACCESS_FS_READ_DIR,
2511 .handled_access_net = LANDLOCK_ACCESS_NET_BIND_TCP,
2512 };
2513 struct landlock_path_beneath_attr path_beneath = {
2514 .allowed_access = LANDLOCK_ACCESS_FS_READ_DIR,
2515 .parent_fd = -1,
2516 };
2517 struct landlock_net_port_attr tcp_bind = {
2518 .allowed_access = LANDLOCK_ACCESS_NET_BIND_TCP,
2519 .port = self->srv0.port,
2520 };
2521 int ruleset_fd, bind_fd, dir_fd;
2522
2523 /* Creates ruleset both for filesystem and network access. */
2524 ruleset_fd = landlock_create_ruleset(&ruleset_attr_fs_net,
2525 sizeof(ruleset_attr_fs_net), 0);
2526 ASSERT_LE(0, ruleset_fd);
2527
2528 /* Adds a filesystem rule. */
2529 path_beneath.parent_fd = open("/dev", O_PATH | O_DIRECTORY | O_CLOEXEC);
2530 ASSERT_LE(0, path_beneath.parent_fd);
2531 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_PATH_BENEATH,
2532 &path_beneath, 0));
2533 EXPECT_EQ(0, close(path_beneath.parent_fd));
2534
2535 /* Adds a network rule. */
2536 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2537 &tcp_bind, 0));
2538
2539 enforce_ruleset(_metadata, ruleset_fd);
2540 EXPECT_EQ(0, close(ruleset_fd));
2541
2542 /* Tests file access. */
2543 dir_fd = open("/dev", O_RDONLY);
2544 EXPECT_LE(0, dir_fd);
2545 EXPECT_EQ(0, close(dir_fd));
2546
2547 dir_fd = open("/", O_RDONLY);
2548 EXPECT_EQ(-1, dir_fd);
2549 EXPECT_EQ(EACCES, errno);
2550
2551 /* Tests port binding. */
2552 bind_fd = socket(AF_INET, SOCK_STREAM | SOCK_CLOEXEC, 0);
2553 ASSERT_LE(0, bind_fd);
2554 EXPECT_EQ(0, bind_variant(bind_fd, &self->srv0));
2555 EXPECT_EQ(0, close(bind_fd));
2556
2557 bind_fd = socket(AF_INET, SOCK_STREAM | SOCK_CLOEXEC, 0);
2558 ASSERT_LE(0, bind_fd);
2559 EXPECT_EQ(-EACCES, bind_variant(bind_fd, &self->srv1));
2560 }
2561
FIXTURE(port_specific)2562 FIXTURE(port_specific)
2563 {
2564 struct service_fixture srv0;
2565 struct service_fixture cli1;
2566 };
2567
FIXTURE_VARIANT(port_specific)2568 FIXTURE_VARIANT(port_specific)
2569 {
2570 const enum sandbox_type sandbox;
2571 const struct protocol_variant prot;
2572 };
2573
2574 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,no_sandbox_with_ipv4)2575 FIXTURE_VARIANT_ADD(port_specific, no_sandbox_with_ipv4) {
2576 /* clang-format on */
2577 .sandbox = NO_SANDBOX,
2578 .prot = {
2579 .domain = AF_INET,
2580 .type = SOCK_STREAM,
2581 },
2582 };
2583
2584 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,tcp_sandbox_with_ipv4)2585 FIXTURE_VARIANT_ADD(port_specific, tcp_sandbox_with_ipv4) {
2586 /* clang-format on */
2587 .sandbox = TCP_SANDBOX,
2588 .prot = {
2589 .domain = AF_INET,
2590 .type = SOCK_STREAM,
2591 },
2592 };
2593
2594 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,udp_sandbox_with_ipv4)2595 FIXTURE_VARIANT_ADD(port_specific, udp_sandbox_with_ipv4) {
2596 /* clang-format on */
2597 .sandbox = UDP_SANDBOX,
2598 .prot = {
2599 .domain = AF_INET,
2600 .type = SOCK_DGRAM,
2601 },
2602 };
2603
2604 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,no_sandbox_with_ipv6)2605 FIXTURE_VARIANT_ADD(port_specific, no_sandbox_with_ipv6) {
2606 /* clang-format on */
2607 .sandbox = NO_SANDBOX,
2608 .prot = {
2609 .domain = AF_INET6,
2610 .type = SOCK_STREAM,
2611 },
2612 };
2613
2614 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,tcp_sandbox_with_ipv6)2615 FIXTURE_VARIANT_ADD(port_specific, tcp_sandbox_with_ipv6) {
2616 /* clang-format on */
2617 .sandbox = TCP_SANDBOX,
2618 .prot = {
2619 .domain = AF_INET6,
2620 .type = SOCK_STREAM,
2621 },
2622 };
2623
2624 /* clang-format off */
FIXTURE_VARIANT_ADD(port_specific,udp_sandbox_with_ipv6)2625 FIXTURE_VARIANT_ADD(port_specific, udp_sandbox_with_ipv6) {
2626 /* clang-format on */
2627 .sandbox = UDP_SANDBOX,
2628 .prot = {
2629 .domain = AF_INET6,
2630 .type = SOCK_DGRAM,
2631 },
2632 };
2633
FIXTURE_SETUP(port_specific)2634 FIXTURE_SETUP(port_specific)
2635 {
2636 disable_caps(_metadata);
2637
2638 ASSERT_EQ(0, set_service(&self->srv0, variant->prot, 0));
2639 ASSERT_EQ(0, set_service(&self->cli1, variant->prot, 1));
2640
2641 setup_loopback(_metadata);
2642 };
2643
FIXTURE_TEARDOWN(port_specific)2644 FIXTURE_TEARDOWN(port_specific)
2645 {
2646 }
2647
TEST_F(port_specific,bind_connect_zero)2648 TEST_F(port_specific, bind_connect_zero)
2649 {
2650 int bind_fd, connect_fd, ret;
2651 uint16_t port;
2652
2653 /* Adds a rule layer with bind and connect actions. */
2654 if (variant->sandbox == TCP_SANDBOX ||
2655 variant->sandbox == UDP_SANDBOX) {
2656 const __u64 access_rights =
2657 (variant->sandbox == TCP_SANDBOX ?
2658 LANDLOCK_ACCESS_NET_BIND_TCP |
2659 LANDLOCK_ACCESS_NET_CONNECT_TCP :
2660 LANDLOCK_ACCESS_NET_BIND_UDP |
2661 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
2662 const struct landlock_ruleset_attr ruleset_attr = {
2663 .handled_access_net = access_rights,
2664 };
2665 const struct landlock_net_port_attr bind_connect_zero = {
2666 .allowed_access = access_rights,
2667 .port = 0,
2668 };
2669 int ruleset_fd;
2670
2671 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2672 sizeof(ruleset_attr), 0);
2673 ASSERT_LE(0, ruleset_fd);
2674
2675 /* Checks zero port value on bind and connect actions. */
2676 EXPECT_EQ(0,
2677 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2678 &bind_connect_zero, 0));
2679
2680 enforce_ruleset(_metadata, ruleset_fd);
2681 EXPECT_EQ(0, close(ruleset_fd));
2682 }
2683
2684 bind_fd = socket_variant(&self->srv0);
2685 ASSERT_LE(0, bind_fd);
2686
2687 connect_fd = socket_variant(&self->srv0);
2688 ASSERT_LE(0, connect_fd);
2689
2690 /* Sets address port to 0 for both protocol families. */
2691 set_port(&self->srv0, 0);
2692 /*
2693 * Binds on port 0, which selects a random port within
2694 * ip_local_port_range.
2695 */
2696 ret = bind_variant(bind_fd, &self->srv0);
2697 EXPECT_EQ(0, ret);
2698
2699 if (variant->prot.type == SOCK_STREAM)
2700 EXPECT_EQ(0, listen(bind_fd, backlog));
2701
2702 /* Connects on port 0. */
2703 ret = connect_variant(connect_fd, &self->srv0);
2704 if (variant->prot.type == SOCK_STREAM) {
2705 EXPECT_EQ(-ECONNREFUSED, ret);
2706 } else {
2707 EXPECT_EQ(0, ret);
2708 }
2709
2710 /* Sets binded port for both protocol families. */
2711 port = get_binded_port(bind_fd, &variant->prot);
2712 EXPECT_NE(0, port);
2713 set_port(&self->srv0, port);
2714 /* Connects on the binded port. */
2715 ret = connect_variant(connect_fd, &self->srv0);
2716 if (is_restricted(&variant->prot, variant->sandbox)) {
2717 /* Denied by Landlock. */
2718 EXPECT_EQ(-EACCES, ret);
2719 } else {
2720 EXPECT_EQ(0, ret);
2721 }
2722
2723 EXPECT_EQ(0, close(connect_fd));
2724 EXPECT_EQ(0, close(bind_fd));
2725 }
2726
TEST_F(port_specific,bind_connect_1023)2727 TEST_F(port_specific, bind_connect_1023)
2728 {
2729 int bind_fd, connect_fd, ret;
2730
2731 /* Adds a rule layer with bind and connect actions. */
2732 if (variant->sandbox == TCP_SANDBOX ||
2733 variant->sandbox == UDP_SANDBOX) {
2734 const __u64 bind_right = (variant->sandbox == TCP_SANDBOX ?
2735 LANDLOCK_ACCESS_NET_BIND_TCP :
2736 LANDLOCK_ACCESS_NET_BIND_UDP);
2737 const __u64 access_rights =
2738 (variant->sandbox == TCP_SANDBOX ?
2739 (LANDLOCK_ACCESS_NET_BIND_TCP |
2740 LANDLOCK_ACCESS_NET_CONNECT_TCP) :
2741 (LANDLOCK_ACCESS_NET_BIND_UDP |
2742 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP));
2743 const struct landlock_ruleset_attr ruleset_attr = {
2744 .handled_access_net = access_rights,
2745 };
2746 /* A rule with port value less than 1024. */
2747 const struct landlock_net_port_attr bind_connect_low_range = {
2748 .allowed_access = access_rights,
2749 .port = 1023,
2750 };
2751 /* A rule with 1024 port. */
2752 const struct landlock_net_port_attr bind_connect = {
2753 .allowed_access = access_rights,
2754 .port = 1024,
2755 };
2756 /* A rule with cli1's port, to use as source port. */
2757 const struct landlock_net_port_attr srcport = {
2758 .allowed_access = bind_right,
2759 .port = self->cli1.port,
2760 };
2761 int ruleset_fd;
2762
2763 ruleset_fd = landlock_create_ruleset(&ruleset_attr,
2764 sizeof(ruleset_attr), 0);
2765 ASSERT_LE(0, ruleset_fd);
2766
2767 ASSERT_EQ(0,
2768 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2769 &bind_connect_low_range, 0));
2770 ASSERT_EQ(0,
2771 landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2772 &bind_connect, 0));
2773 if (variant->sandbox == UDP_SANDBOX) {
2774 ASSERT_EQ(0, landlock_add_rule(ruleset_fd,
2775 LANDLOCK_RULE_NET_PORT,
2776 &srcport, 0));
2777 }
2778
2779 enforce_ruleset(_metadata, ruleset_fd);
2780 EXPECT_EQ(0, close(ruleset_fd));
2781 }
2782
2783 bind_fd = socket_variant(&self->srv0);
2784 ASSERT_LE(0, bind_fd);
2785
2786 /* Sets address port to 1023 for both protocol families. */
2787 set_port(&self->srv0, 1023);
2788 /* Binds on port 1023. */
2789 ret = bind_variant(bind_fd, &self->srv0);
2790 /* Denied by the system. */
2791 EXPECT_EQ(-EACCES, ret);
2792
2793 /* Binds on port 1023. */
2794 set_cap(_metadata, CAP_NET_BIND_SERVICE);
2795 ret = bind_variant(bind_fd, &self->srv0);
2796 clear_cap(_metadata, CAP_NET_BIND_SERVICE);
2797 EXPECT_EQ(0, ret);
2798 if (variant->prot.type == SOCK_STREAM)
2799 EXPECT_EQ(0, listen(bind_fd, backlog));
2800
2801 connect_fd = socket_variant(&self->srv0);
2802 ASSERT_LE(0, connect_fd);
2803 if (variant->prot.type == SOCK_DGRAM) {
2804 /*
2805 * We are about to connect(), but bind() is restricted, so for
2806 * UDP sockets we need to use cli1's port as source port (the
2807 * only one we are allowed to use).
2808 */
2809 EXPECT_EQ(0, bind_variant(connect_fd, &self->cli1));
2810 }
2811 /* Connects on the binded port 1023. */
2812 ret = connect_variant(connect_fd, &self->srv0);
2813 EXPECT_EQ(0, ret);
2814
2815 EXPECT_EQ(0, close(connect_fd));
2816 EXPECT_EQ(0, close(bind_fd));
2817
2818 bind_fd = socket_variant(&self->srv0);
2819 ASSERT_LE(0, bind_fd);
2820
2821 connect_fd = socket_variant(&self->srv0);
2822 ASSERT_LE(0, connect_fd);
2823
2824 /* Sets address port to 1024 for both protocol families. */
2825 set_port(&self->srv0, 1024);
2826 /* Binds on port 1024. */
2827 ret = bind_variant(bind_fd, &self->srv0);
2828 EXPECT_EQ(0, ret);
2829 if (variant->prot.type == SOCK_STREAM)
2830 EXPECT_EQ(0, listen(bind_fd, backlog));
2831 if (variant->prot.type == SOCK_DGRAM)
2832 EXPECT_EQ(0, bind_variant(connect_fd, &self->cli1));
2833
2834 /* Connects on the binded port 1024. */
2835 ret = connect_variant(connect_fd, &self->srv0);
2836 EXPECT_EQ(0, ret);
2837
2838 EXPECT_EQ(0, close(connect_fd));
2839 EXPECT_EQ(0, close(bind_fd));
2840 }
2841
2842 /**
2843 * matches_auditlog - Check audit log for a network access denial
2844 *
2845 * @audit_fd: Audit file descriptor.
2846 * @blockers: A regex-escaped blocker string, e.g., "net\.bind_tcp".
2847 * @dir_addr: Either "saddr" or "daddr", ignored if addr is NULL.
2848 * @addr: A regex-escaped IP address string, or NULL.
2849 * @dir_port: Either "src" or "dest", ignored if addr is NULL.
2850 * @port: A port number, ignored if addr is NULL.
2851 */
matches_auditlog(const int audit_fd,const char * const blockers,const char * const dir_addr,const char * const addr,const char * const dir_port,const __u16 port)2852 static int matches_auditlog(const int audit_fd, const char *const blockers,
2853 const char *const dir_addr, const char *const addr,
2854 const char *const dir_port, const __u16 port)
2855 {
2856 static const char log_with_addrport_tmpl[] = REGEX_LANDLOCK_PREFIX
2857 " blockers=%s %s=%s %s=%u$";
2858 static const char log_without_addrport_tmpl[] = REGEX_LANDLOCK_PREFIX
2859 " blockers=%s";
2860 /*
2861 * Max strlen(blockers): 16
2862 * Max strlen(dir_addr): 5
2863 * Max strlen(addr): 12
2864 * Max strlen(dir_port): 4
2865 * Max strlen(%u port): 5
2866 */
2867 char log_match[sizeof(log_with_addrport_tmpl) + 42];
2868 int log_match_len;
2869
2870 if (addr == NULL)
2871 log_match_len = snprintf(log_match, sizeof(log_match),
2872 log_without_addrport_tmpl, blockers);
2873 else
2874 log_match_len = snprintf(log_match, sizeof(log_match),
2875 log_with_addrport_tmpl, blockers,
2876 dir_addr, addr, dir_port, port);
2877 if (log_match_len > sizeof(log_match))
2878 return -E2BIG;
2879
2880 return audit_match_record(audit_fd, AUDIT_LANDLOCK_ACCESS, log_match,
2881 NULL);
2882 }
2883
FIXTURE(audit)2884 FIXTURE(audit)
2885 {
2886 struct service_fixture srv0;
2887 struct service_fixture srv1;
2888 /* srv2 has a rule with no access but quiet bit set. */
2889 struct service_fixture srv2;
2890 struct service_fixture unspec_srv0;
2891 struct audit_filter audit_filter;
2892 int audit_fd;
2893 };
2894
FIXTURE_VARIANT(audit)2895 FIXTURE_VARIANT(audit)
2896 {
2897 const char *const addr;
2898 const struct protocol_variant prot;
2899 };
2900
2901 /* clang-format off */
FIXTURE_VARIANT_ADD(audit,ipv4_tcp)2902 FIXTURE_VARIANT_ADD(audit, ipv4_tcp) {
2903 /* clang-format on */
2904 .addr = "127\\.0\\.0\\.1",
2905 .prot = {
2906 .domain = AF_INET,
2907 .type = SOCK_STREAM,
2908 },
2909 };
2910
2911 /* clang-format off */
FIXTURE_VARIANT_ADD(audit,ipv4_udp)2912 FIXTURE_VARIANT_ADD(audit, ipv4_udp) {
2913 /* clang-format on */
2914 .addr = "127\\.0\\.0\\.1",
2915 .prot = {
2916 .domain = AF_INET,
2917 .type = SOCK_DGRAM,
2918 },
2919 };
2920
2921 /* clang-format off */
FIXTURE_VARIANT_ADD(audit,ipv6_tcp)2922 FIXTURE_VARIANT_ADD(audit, ipv6_tcp) {
2923 /* clang-format on */
2924 .addr = "::1",
2925 .prot = {
2926 .domain = AF_INET6,
2927 .type = SOCK_STREAM,
2928 },
2929 };
2930
2931 /* clang-format off */
FIXTURE_VARIANT_ADD(audit,ipv6_udp)2932 FIXTURE_VARIANT_ADD(audit, ipv6_udp) {
2933 /* clang-format on */
2934 .addr = "::1",
2935 .prot = {
2936 .domain = AF_INET6,
2937 .type = SOCK_DGRAM,
2938 },
2939 };
2940
FIXTURE_SETUP(audit)2941 FIXTURE_SETUP(audit)
2942 {
2943 struct protocol_variant prot_unspec = variant->prot;
2944
2945 prot_unspec.domain = AF_UNSPEC;
2946
2947 ASSERT_EQ(0, set_service(&self->srv0, variant->prot, 0));
2948 ASSERT_EQ(0, set_service(&self->srv1, variant->prot, 1));
2949 ASSERT_EQ(0, set_service(&self->srv2, variant->prot, 2));
2950 ASSERT_EQ(0, set_service(&self->unspec_srv0, prot_unspec, 0));
2951
2952 setup_loopback(_metadata);
2953
2954 set_cap(_metadata, CAP_AUDIT_CONTROL);
2955 self->audit_fd = audit_init_with_exe_filter(&self->audit_filter);
2956 EXPECT_LE(0, self->audit_fd);
2957 disable_caps(_metadata);
2958 };
2959
FIXTURE_TEARDOWN(audit)2960 FIXTURE_TEARDOWN(audit)
2961 {
2962 set_cap(_metadata, CAP_AUDIT_CONTROL);
2963 EXPECT_EQ(0, audit_cleanup(self->audit_fd, &self->audit_filter));
2964 clear_cap(_metadata, CAP_AUDIT_CONTROL);
2965 }
2966
TEST_F(audit,bind)2967 TEST_F(audit, bind)
2968 {
2969 const char *audit_evt = (variant->prot.type == SOCK_STREAM ?
2970 "net\\.bind_tcp" :
2971 "net\\.bind_udp");
2972 const __u64 access_rights =
2973 (variant->prot.type == SOCK_STREAM ?
2974 LANDLOCK_ACCESS_NET_BIND_TCP |
2975 LANDLOCK_ACCESS_NET_CONNECT_TCP :
2976 LANDLOCK_ACCESS_NET_BIND_UDP |
2977 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
2978 const struct landlock_ruleset_attr ruleset_attr = {
2979 .handled_access_net = access_rights,
2980 .quiet_access_net = access_rights,
2981 };
2982 const struct landlock_net_port_attr quiet_rule = {
2983 .allowed_access = 0,
2984 .port = self->srv2.port,
2985 };
2986 struct audit_records records;
2987 int ruleset_fd, sock_fd;
2988
2989 ruleset_fd =
2990 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
2991 ASSERT_LE(0, ruleset_fd);
2992 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
2993 &quiet_rule, LANDLOCK_ADD_RULE_QUIET));
2994 enforce_ruleset(_metadata, ruleset_fd);
2995 EXPECT_EQ(0, close(ruleset_fd));
2996
2997 sock_fd = socket_variant(&self->srv0);
2998 ASSERT_LE(0, sock_fd);
2999 EXPECT_EQ(-EACCES, bind_variant(sock_fd, &self->srv0));
3000 EXPECT_EQ(0, matches_auditlog(self->audit_fd, audit_evt, "saddr",
3001 variant->addr, "src", self->srv0.port));
3002
3003 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3004 EXPECT_EQ(0, records.access);
3005 EXPECT_EQ(1, records.domain);
3006
3007 EXPECT_EQ(0, close(sock_fd));
3008
3009 /* Bind to srv2 (with quiet rule): no new audit logs. */
3010 sock_fd = socket_variant(&self->srv2);
3011 ASSERT_LE(0, sock_fd);
3012 EXPECT_EQ(-EACCES, bind_variant(sock_fd, &self->srv2));
3013
3014 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3015 EXPECT_EQ(0, records.access);
3016 EXPECT_EQ(0, records.domain);
3017
3018 EXPECT_EQ(0, close(sock_fd));
3019 }
3020
TEST_F(audit,connect)3021 TEST_F(audit, connect)
3022 {
3023 const char *audit_evt = (variant->prot.type == SOCK_STREAM ?
3024 "net\\.connect_tcp" :
3025 "net\\.connect_send_udp");
3026 const __u64 bind_right = (variant->prot.type == SOCK_STREAM ?
3027 LANDLOCK_ACCESS_NET_BIND_TCP :
3028 LANDLOCK_ACCESS_NET_BIND_UDP);
3029 const __u64 conn_right = (variant->prot.type == SOCK_STREAM ?
3030 LANDLOCK_ACCESS_NET_CONNECT_TCP :
3031 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
3032 const __u64 access_rights = bind_right | conn_right;
3033 const struct landlock_ruleset_attr ruleset_attr = {
3034 .handled_access_net = access_rights,
3035 .quiet_access_net = access_rights,
3036 };
3037 const struct landlock_net_port_attr rule_connect_p1 = {
3038 .allowed_access = conn_right,
3039 .port = self->srv1.port,
3040 };
3041 const struct landlock_net_port_attr quiet_rule = {
3042 .allowed_access = 0,
3043 .port = self->srv2.port,
3044 };
3045 struct audit_records records;
3046 int ruleset_fd, sock_fd;
3047
3048 ruleset_fd =
3049 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
3050 ASSERT_LE(0, ruleset_fd);
3051 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3052 &rule_connect_p1, 0));
3053 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3054 &quiet_rule, LANDLOCK_ADD_RULE_QUIET));
3055 enforce_ruleset(_metadata, ruleset_fd);
3056 EXPECT_EQ(0, close(ruleset_fd));
3057
3058 sock_fd = socket_variant(&self->srv0);
3059 ASSERT_LE(0, sock_fd);
3060 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &self->srv0));
3061 EXPECT_EQ(0, matches_auditlog(self->audit_fd, audit_evt, "daddr",
3062 variant->addr, "dest", self->srv0.port));
3063
3064 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3065 EXPECT_EQ(0, records.access);
3066 EXPECT_EQ(1, records.domain);
3067
3068 if (variant->prot.type == SOCK_DGRAM) {
3069 /* Check that autobind generates a denied bind event. */
3070 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &self->srv1));
3071
3072 EXPECT_EQ(0, matches_auditlog(self->audit_fd, "net\\.bind_udp",
3073 NULL, NULL, NULL, 0));
3074 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3075 EXPECT_EQ(0, records.access);
3076 EXPECT_EQ(0, records.domain);
3077 }
3078
3079 EXPECT_EQ(0, close(sock_fd));
3080
3081 /* Connect to srv2 (with quiet rule): no new audit logs. */
3082 sock_fd = socket_variant(&self->srv2);
3083 ASSERT_LE(0, sock_fd);
3084 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &self->srv2));
3085
3086 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3087 EXPECT_EQ(0, records.access);
3088 EXPECT_EQ(0, records.domain);
3089
3090 EXPECT_EQ(0, close(sock_fd));
3091 }
3092
3093 /* Quieting bind access has no effect on connect. */
TEST_F(audit,connect_quiet_bind)3094 TEST_F(audit, connect_quiet_bind)
3095 {
3096 const char *audit_evt = (variant->prot.type == SOCK_STREAM ?
3097 "net\\.connect_tcp" :
3098 "net\\.connect_send_udp");
3099 const int bind_right = (variant->prot.type == SOCK_STREAM ?
3100 LANDLOCK_ACCESS_NET_BIND_TCP :
3101 LANDLOCK_ACCESS_NET_BIND_UDP);
3102 const int conn_right = (variant->prot.type == SOCK_STREAM ?
3103 LANDLOCK_ACCESS_NET_CONNECT_TCP :
3104 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
3105 const int access_rights = bind_right | conn_right;
3106 const struct landlock_ruleset_attr ruleset_attr = {
3107 .handled_access_net = access_rights,
3108 .quiet_access_net = bind_right,
3109 };
3110 const struct landlock_ruleset_attr ruleset_attr_2 = {
3111 .handled_access_net = access_rights,
3112 .quiet_access_net = conn_right,
3113 };
3114 const struct landlock_net_port_attr quiet_rule = {
3115 .allowed_access = 0,
3116 .port = self->srv2.port,
3117 };
3118 struct audit_records records;
3119 int ruleset_fd, sock_fd;
3120
3121 ruleset_fd =
3122 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
3123 ASSERT_LE(0, ruleset_fd);
3124 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3125 &quiet_rule, LANDLOCK_ADD_RULE_QUIET));
3126 enforce_ruleset(_metadata, ruleset_fd);
3127 EXPECT_EQ(0, close(ruleset_fd));
3128
3129 sock_fd = socket_variant(&self->srv2);
3130 ASSERT_LE(0, sock_fd);
3131 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &self->srv2));
3132 EXPECT_EQ(0, matches_auditlog(self->audit_fd, audit_evt, "daddr",
3133 variant->addr, "dest", self->srv2.port));
3134
3135 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3136 EXPECT_EQ(0, records.access);
3137
3138 EXPECT_EQ(0, close(sock_fd));
3139
3140 /* New layer that also denies connect but has the correct quiet bit. */
3141 ruleset_fd = landlock_create_ruleset(&ruleset_attr_2,
3142 sizeof(ruleset_attr_2), 0);
3143 ASSERT_LE(0, ruleset_fd);
3144 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3145 &quiet_rule, LANDLOCK_ADD_RULE_QUIET));
3146 enforce_ruleset(_metadata, ruleset_fd);
3147 EXPECT_EQ(0, close(ruleset_fd));
3148
3149 sock_fd = socket_variant(&self->srv2);
3150 ASSERT_LE(0, sock_fd);
3151 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &self->srv2));
3152
3153 /* Quieted - no logs expected. */
3154 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3155 EXPECT_EQ(0, records.access);
3156
3157 EXPECT_EQ(0, close(sock_fd));
3158 }
3159
matches_log_connect_bound(int audit_fd,const char * const blockers,const char * const addr,__u16 lport,__u16 dport)3160 static int matches_log_connect_bound(int audit_fd, const char *const blockers,
3161 const char *const addr, __u16 lport,
3162 __u16 dport)
3163 {
3164 static const char log_template[] = REGEX_LANDLOCK_PREFIX
3165 " blockers=%s laddr=%s lport=%u daddr=%s dest=%u$";
3166 /* Slack for the blockers, two addresses and two port numbers. */
3167 char log_match[sizeof(log_template) + 60];
3168 int log_match_len;
3169
3170 log_match_len = snprintf(log_match, sizeof(log_match), log_template,
3171 blockers, addr, lport, addr, dport);
3172 if (log_match_len > sizeof(log_match))
3173 return -E2BIG;
3174
3175 return audit_match_record(audit_fd, AUDIT_LANDLOCK_ACCESS, log_match,
3176 NULL);
3177 }
3178
3179 /*
3180 * After a bind() to an allowed port, a denied connect must report laddr/lport
3181 * from the bound socket (made available through audit_net.sk) in addition to
3182 * the connect sockaddr's daddr/dest.
3183 */
TEST_F(audit,connect_bound)3184 TEST_F(audit, connect_bound)
3185 {
3186 const __u64 bind_right = (variant->prot.type == SOCK_STREAM ?
3187 LANDLOCK_ACCESS_NET_BIND_TCP :
3188 LANDLOCK_ACCESS_NET_BIND_UDP);
3189 const __u64 conn_right = (variant->prot.type == SOCK_STREAM ?
3190 LANDLOCK_ACCESS_NET_CONNECT_TCP :
3191 LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP);
3192 const char *const audit_evt = (variant->prot.type == SOCK_STREAM ?
3193 "net\\.connect_tcp" :
3194 "net\\.connect_send_udp");
3195 const struct landlock_ruleset_attr ruleset_attr = {
3196 .handled_access_net = bind_right | conn_right,
3197 };
3198 const struct landlock_net_port_attr rule_bind = {
3199 .allowed_access = bind_right,
3200 .port = self->srv0.port,
3201 };
3202 struct service_fixture srv_remote;
3203 struct audit_records records;
3204 int ruleset_fd, sock_fd;
3205
3206 /* Uses a second port as the denied connect target. */
3207 ASSERT_EQ(0, set_service(&srv_remote, variant->prot, 1));
3208
3209 ruleset_fd =
3210 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
3211 ASSERT_LE(0, ruleset_fd);
3212 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3213 &rule_bind, 0));
3214 enforce_ruleset(_metadata, ruleset_fd);
3215 EXPECT_EQ(0, close(ruleset_fd));
3216
3217 sock_fd = socket_variant(&self->srv0);
3218 ASSERT_LE(0, sock_fd);
3219 EXPECT_EQ(0, bind_variant(sock_fd, &self->srv0));
3220 EXPECT_EQ(-EACCES, connect_variant(sock_fd, &srv_remote));
3221 EXPECT_EQ(0, matches_log_connect_bound(self->audit_fd, audit_evt,
3222 variant->addr, self->srv0.port,
3223 srv_remote.port));
3224
3225 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3226 EXPECT_EQ(0, records.access);
3227 EXPECT_EQ(1, records.domain);
3228
3229 EXPECT_EQ(0, close(sock_fd));
3230 }
3231
TEST_F(audit,sendmsg)3232 TEST_F(audit, sendmsg)
3233 {
3234 const struct landlock_ruleset_attr ruleset_attr = {
3235 .handled_access_net = LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP |
3236 LANDLOCK_ACCESS_NET_BIND_UDP,
3237 };
3238 const struct landlock_net_port_attr rule = {
3239 .allowed_access = LANDLOCK_ACCESS_NET_CONNECT_SEND_UDP,
3240 .port = self->srv1.port,
3241 };
3242 struct audit_records records;
3243 int ruleset_fd;
3244 int sock_fd;
3245
3246 /* Sendmsg on stream sockets is never denied. */
3247 if (variant->prot.type != SOCK_DGRAM)
3248 return;
3249
3250 ruleset_fd =
3251 landlock_create_ruleset(&ruleset_attr, sizeof(ruleset_attr), 0);
3252 ASSERT_LE(0, ruleset_fd);
3253 ASSERT_EQ(0, landlock_add_rule(ruleset_fd, LANDLOCK_RULE_NET_PORT,
3254 &rule, 0));
3255 enforce_ruleset(_metadata, ruleset_fd);
3256 EXPECT_EQ(0, close(ruleset_fd));
3257
3258 sock_fd = socket_variant(&self->srv0);
3259 ASSERT_LE(0, sock_fd);
3260 EXPECT_EQ(-EACCES, sendto_variant(sock_fd, &self->srv0, "A", 1, 0));
3261 EXPECT_EQ(0, matches_auditlog(self->audit_fd, "net\\.connect_send_udp",
3262 "daddr", variant->addr, "dest",
3263 self->srv0.port));
3264
3265 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3266 EXPECT_EQ(0, records.access);
3267 EXPECT_EQ(1, records.domain);
3268
3269 /* Check that autobind generates a denied bind event. */
3270 EXPECT_EQ(-EACCES, sendto_variant(sock_fd, &self->srv1, "A", 1, 0));
3271 EXPECT_EQ(0, matches_auditlog(self->audit_fd, "net\\.bind_udp", NULL,
3272 NULL, NULL, 0));
3273 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3274 EXPECT_EQ(0, records.access);
3275 EXPECT_EQ(0, records.domain);
3276
3277 EXPECT_EQ(-EACCES,
3278 sendto_variant(sock_fd, &self->unspec_srv0, "B", 1, 0));
3279 EXPECT_EQ(0, matches_auditlog(self->audit_fd, "net\\.connect_send_udp",
3280 "daddr", NULL, "dest", 0));
3281 EXPECT_EQ(0, audit_count_records(self->audit_fd, &records));
3282 EXPECT_EQ(0, records.access);
3283 EXPECT_EQ(0, records.domain);
3284
3285 EXPECT_EQ(0, close(sock_fd));
3286 }
3287
3288 TEST_HARNESS_MAIN
3289