Skip to content

Commit 76e2a42

Browse files
committed
daemon: cgen: add cgroup_sock_addr flavor codegen
Implement bf_flavor_ops for BF_FLAVOR_CGROUP_SOCK_ADDR so chains with a default policy can be loaded and attached to a cgroup.
1 parent 61d4e29 commit 76e2a42

File tree

5 files changed

+119
-2
lines changed

5 files changed

+119
-2
lines changed

src/bpfilter/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ add_executable(bpfilter
1717
${CMAKE_CURRENT_SOURCE_DIR}/opts.h ${CMAKE_CURRENT_SOURCE_DIR}/opts.c
1818
${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgen.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgen.c
1919
${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgroup_skb.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgroup_skb.c
20+
${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgroup_sock_addr.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/cgroup_sock_addr.c
2021
${CMAKE_CURRENT_SOURCE_DIR}/cgen/dump.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/dump.c
2122
${CMAKE_CURRENT_SOURCE_DIR}/cgen/elfstub.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/elfstub.c
2223
${CMAKE_CURRENT_SOURCE_DIR}/cgen/fixup.h ${CMAKE_CURRENT_SOURCE_DIR}/cgen/fixup.c
Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
/* SPDX-License-Identifier: GPL-2.0-only */
2+
/*
3+
* Copyright (c) 2023 Meta Platforms, Inc. and affiliates.
4+
*/
5+
6+
#include "cgen/cgroup_sock_addr.h"
7+
8+
#include <linux/bpf_common.h>
9+
#include <linux/if_ether.h>
10+
11+
#include <assert.h>
12+
#include <errno.h>
13+
#include <stddef.h>
14+
#include <sys/socket.h>
15+
16+
#include <bpfilter/flavor.h>
17+
#include <bpfilter/verdict.h>
18+
19+
#include "cgen/program.h"
20+
#include "cgen/swich.h"
21+
#include "filter.h"
22+
#include "linux/bpf.h"
23+
24+
// Forward definition to avoid headers clusterfuck.
25+
uint16_t htons(uint16_t hostshort);
26+
27+
static int _bf_cgroup_sock_addr_gen_inline_prologue(struct bf_program *program)
28+
{
29+
int r;
30+
31+
assert(program);
32+
33+
// No packet data and no interface for sock_addr programs
34+
EMIT(program, BPF_ST_MEM(BPF_DW, BPF_REG_10, BF_PROG_CTX_OFF(pkt_size), 0));
35+
EMIT(program, BPF_ST_MEM(BPF_W, BPF_REG_10, BF_PROG_CTX_OFF(ifindex), 0));
36+
37+
/* Convert bpf_sock_addr.family to L3 protocol ID in R7, using the same
38+
* bf_swich pattern as cgroup_skb. */
39+
EMIT(program, BPF_LDX_MEM(BPF_W, BPF_REG_2, BPF_REG_1,
40+
offsetof(struct bpf_sock_addr, family)));
41+
42+
{
43+
_clean_bf_swich_ struct bf_swich swich =
44+
bf_swich_get(program, BPF_REG_2);
45+
46+
EMIT_SWICH_OPTION(&swich, AF_INET,
47+
BPF_MOV64_IMM(BPF_REG_7, htons(ETH_P_IP)));
48+
EMIT_SWICH_OPTION(&swich, AF_INET6,
49+
BPF_MOV64_IMM(BPF_REG_7, htons(ETH_P_IPV6)));
50+
EMIT_SWICH_DEFAULT(&swich, BPF_MOV64_IMM(BPF_REG_7, 0));
51+
52+
r = bf_swich_generate(&swich);
53+
if (r)
54+
return r;
55+
}
56+
57+
EMIT(program, BPF_LDX_MEM(BPF_W, BPF_REG_8, BPF_REG_1,
58+
offsetof(struct bpf_sock_addr, protocol)));
59+
60+
return 0;
61+
}
62+
63+
static int _bf_cgroup_sock_addr_gen_inline_epilogue(struct bf_program *program)
64+
{
65+
(void)program;
66+
67+
return 0;
68+
}
69+
70+
static int
71+
_bf_cgroup_sock_addr_gen_inline_matcher(struct bf_program *program,
72+
const struct bf_matcher *matcher)
73+
{
74+
(void)program;
75+
(void)matcher;
76+
77+
return -ENOTSUP;
78+
}
79+
80+
/**
81+
* Convert a standard verdict into a return value.
82+
*
83+
* @param verdict Verdict to convert. Must be valid.
84+
* @return Cgroup return code corresponding to the verdict, as an integer.
85+
*/
86+
static int _bf_cgroup_sock_addr_get_verdict(enum bf_verdict verdict)
87+
{
88+
switch (verdict) {
89+
case BF_VERDICT_ACCEPT:
90+
return 1;
91+
case BF_VERDICT_DROP:
92+
return 0;
93+
default:
94+
return -ENOTSUP;
95+
}
96+
}
97+
98+
const struct bf_flavor_ops bf_flavor_ops_cgroup_sock_addr = {
99+
.gen_inline_prologue = _bf_cgroup_sock_addr_gen_inline_prologue,
100+
.gen_inline_epilogue = _bf_cgroup_sock_addr_gen_inline_epilogue,
101+
.get_verdict = _bf_cgroup_sock_addr_get_verdict,
102+
.gen_inline_matcher = _bf_cgroup_sock_addr_gen_inline_matcher,
103+
};
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/* SPDX-License-Identifier: GPL-2.0-only */
2+
/*
3+
* Copyright (c) 2023 Meta Platforms, Inc. and affiliates.
4+
*/
5+
6+
#pragma once
7+
8+
#include <bpfilter/flavor.h>
9+
10+
extern const struct bf_flavor_ops bf_flavor_ops_cgroup_sock_addr;

src/bpfilter/cgen/prog/link.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@ int bf_link_new(struct bf_link **link, const char *name, enum bf_hook hook,
7373
fd = r;
7474
break;
7575
case BF_FLAVOR_CGROUP_SKB:
76+
case BF_FLAVOR_CGROUP_SOCK_ADDR:
7677
cgroup_fd = open(_hookopts->cgpath, O_DIRECTORY | O_RDONLY);
7778
if (cgroup_fd < 0) {
7879
return bf_err_r(errno, "failed to open cgroup '%s'",
@@ -81,7 +82,7 @@ int bf_link_new(struct bf_link **link, const char *name, enum bf_hook hook,
8182

8283
r = bf_bpf_link_create(prog_fd, cgroup_fd, hook, 0, 0, 0);
8384
if (r < 0)
84-
return bf_err_r(r, "failed to create cgroup_skb BPF link");
85+
return bf_err_r(r, "failed to create cgroup BPF link");
8586

8687
fd = r;
8788
break;
@@ -291,6 +292,7 @@ int bf_link_update(struct bf_link *link, int prog_fd)
291292
case BF_FLAVOR_XDP:
292293
case BF_FLAVOR_TC:
293294
case BF_FLAVOR_CGROUP_SKB:
295+
case BF_FLAVOR_CGROUP_SOCK_ADDR:
294296
r = bf_bpf_link_update(link->fd, prog_fd);
295297
break;
296298
case BF_FLAVOR_NF:

src/bpfilter/cgen/program.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737
#include <bpfilter/verdict.h>
3838

3939
#include "cgen/cgroup_skb.h"
40+
#include "cgen/cgroup_sock_addr.h"
4041
#include "cgen/dump.h"
4142
#include "cgen/fixup.h"
4243
#include "cgen/handle.h"
@@ -83,7 +84,7 @@ static const struct bf_flavor_ops *bf_flavor_ops_get(enum bf_flavor flavor)
8384
[BF_FLAVOR_NF] = &bf_flavor_ops_nf,
8485
[BF_FLAVOR_XDP] = &bf_flavor_ops_xdp,
8586
[BF_FLAVOR_CGROUP_SKB] = &bf_flavor_ops_cgroup_skb,
86-
[BF_FLAVOR_CGROUP_SOCK_ADDR] = NULL,
87+
[BF_FLAVOR_CGROUP_SOCK_ADDR] = &bf_flavor_ops_cgroup_sock_addr,
8788
};
8889

8990
static_assert_enum_mapping(flavor_ops, _BF_FLAVOR_MAX);

0 commit comments

Comments
 (0)