brintos

brintos / linux-shallow public Read only

0
0
Text · 4.2 KiB · e1bf141 Raw
169 lines · c
1// SPDX-License-Identifier: GPL-2.02#include <test_progs.h>3#include <network_helpers.h>4#include <bpf/btf.h>5#include <linux/if_link.h>6#include <linux/udp.h>7#include <net/if.h>8#include <unistd.h>9 10#include "xdp_flowtable.skel.h"11 12#define TX_NETNS_NAME	"ns0"13#define RX_NETNS_NAME	"ns1"14 15#define TX_NAME		"v0"16#define FORWARD_NAME	"v1"17#define RX_NAME		"d0"18 19#define TX_MAC		"00:00:00:00:00:01"20#define FORWARD_MAC	"00:00:00:00:00:02"21#define RX_MAC		"00:00:00:00:00:03"22#define DST_MAC		"00:00:00:00:00:04"23 24#define TX_ADDR		"10.0.0.1"25#define FORWARD_ADDR	"10.0.0.2"26#define RX_ADDR		"20.0.0.1"27#define DST_ADDR	"20.0.0.2"28 29#define PREFIX_LEN	"8"30#define N_PACKETS	1031#define UDP_PORT	1234532#define UDP_PORT_STR	"12345"33 34static int send_udp_traffic(void)35{36	struct sockaddr_storage addr;37	int i, sock;38 39	if (make_sockaddr(AF_INET, DST_ADDR, UDP_PORT, &addr, NULL))40		return -EINVAL;41 42	sock = socket(AF_INET, SOCK_DGRAM, 0);43	if (sock < 0)44		return sock;45 46	for (i = 0; i < N_PACKETS; i++) {47		unsigned char buf[] = { 0xaa, 0xbb, 0xcc };48		int n;49 50		n = sendto(sock, buf, sizeof(buf), MSG_NOSIGNAL | MSG_CONFIRM,51			   (struct sockaddr *)&addr, sizeof(addr));52		if (n != sizeof(buf)) {53			close(sock);54			return -EINVAL;55		}56 57		usleep(50000); /* 50ms */58	}59	close(sock);60 61	return 0;62}63 64void test_xdp_flowtable(void)65{66	struct xdp_flowtable *skel = NULL;67	struct nstoken *tok = NULL;68	int iifindex, stats_fd;69	__u32 value, key = 0;70	struct bpf_link *link;71 72	if (SYS_NOFAIL("nft -v")) {73		fprintf(stdout, "Missing required nft tool\n");74		test__skip();75		return;76	}77 78	SYS(out, "ip netns add " TX_NETNS_NAME);79	SYS(out, "ip netns add " RX_NETNS_NAME);80 81	tok = open_netns(RX_NETNS_NAME);82	if (!ASSERT_OK_PTR(tok, "setns"))83		goto out;84 85	SYS(out, "sysctl -qw net.ipv4.conf.all.forwarding=1");86 87	SYS(out, "ip link add " TX_NAME " type veth peer " FORWARD_NAME);88	SYS(out, "ip link set " TX_NAME " netns " TX_NETNS_NAME);89	SYS(out, "ip link set dev " FORWARD_NAME " address " FORWARD_MAC);90	SYS(out,91	    "ip addr add " FORWARD_ADDR "/" PREFIX_LEN " dev " FORWARD_NAME);92	SYS(out, "ip link set dev " FORWARD_NAME " up");93 94	SYS(out, "ip link add " RX_NAME " type dummy");95	SYS(out, "ip link set dev " RX_NAME " address " RX_MAC);96	SYS(out, "ip addr add " RX_ADDR "/" PREFIX_LEN " dev " RX_NAME);97	SYS(out, "ip link set dev " RX_NAME " up");98 99	/* configure the flowtable */100	SYS(out, "nft add table ip filter");101	SYS(out,102	    "nft add flowtable ip filter f { hook ingress priority 0\\; "103	    "devices = { " FORWARD_NAME ", " RX_NAME " }\\; }");104	SYS(out,105	    "nft add chain ip filter forward "106	    "{ type filter hook forward priority 0\\; }");107	SYS(out,108	    "nft add rule ip filter forward ip protocol udp th dport "109	    UDP_PORT_STR " flow add @f");110 111	/* Avoid ARP calls */112	SYS(out,113	    "ip -4 neigh add " DST_ADDR " lladdr " DST_MAC " dev " RX_NAME);114 115	close_netns(tok);116	tok = open_netns(TX_NETNS_NAME);117	if (!ASSERT_OK_PTR(tok, "setns"))118		goto out;119 120	SYS(out, "ip addr add " TX_ADDR "/" PREFIX_LEN " dev " TX_NAME);121	SYS(out, "ip link set dev " TX_NAME " address " TX_MAC);122	SYS(out, "ip link set dev " TX_NAME " up");123	SYS(out, "ip route add default via " FORWARD_ADDR);124 125	close_netns(tok);126	tok = open_netns(RX_NETNS_NAME);127	if (!ASSERT_OK_PTR(tok, "setns"))128		goto out;129 130	iifindex = if_nametoindex(FORWARD_NAME);131	if (!ASSERT_NEQ(iifindex, 0, "iifindex"))132		goto out;133 134	skel = xdp_flowtable__open_and_load();135	if (!ASSERT_OK_PTR(skel, "skel"))136		goto out;137 138	link = bpf_program__attach_xdp(skel->progs.xdp_flowtable_do_lookup,139				       iifindex);140	if (!ASSERT_OK_PTR(link, "prog_attach"))141		goto out;142 143	close_netns(tok);144	tok = open_netns(TX_NETNS_NAME);145	if (!ASSERT_OK_PTR(tok, "setns"))146		goto out;147 148	if (!ASSERT_OK(send_udp_traffic(), "send udp"))149		goto out;150 151	close_netns(tok);152	tok = open_netns(RX_NETNS_NAME);153	if (!ASSERT_OK_PTR(tok, "setns"))154		goto out;155 156	stats_fd = bpf_map__fd(skel->maps.stats);157	if (!ASSERT_OK(bpf_map_lookup_elem(stats_fd, &key, &value),158		       "bpf_map_update_elem stats"))159		goto out;160 161	ASSERT_GE(value, N_PACKETS - 2, "bpf_xdp_flow_lookup failed");162out:163	xdp_flowtable__destroy(skel);164	if (tok)165		close_netns(tok);166	SYS_NOFAIL("ip netns del " TX_NETNS_NAME);167	SYS_NOFAIL("ip netns del " RX_NETNS_NAME);168}169