The following patchset is a PoC to add generic infrastructure to jit
nftables to bpf. Rationale is the following:
nft --> netlink --> nf_tables -> intermediate representation --> bpf
The idea is to convert our internal nf_tables structure representation
to an abstract syntax tree (our intermediate representation) that
represents the ruleset. Then, we walk over this abstract syntax tree to
generate bpf code. Finally, we store the bpf bytecode in a buffer in the
rule, then when ruleset updates happen.
Patch #1 adds the intermediate representation infrastructure that creates
the syntax tree for the payload and the meta expressions - that
allows us to match on payload and sk_buff meta information.
Patch #2 adds the infrastructure to walk over the syntax tree and invoke
the callbacks to generate the target backend representation.
Patch #3 adds the bpf backend jit, this places the struct nft_rule_jit
object in the rule object, that stores the bpf bytecode per
rule. Then, from commit phase in nftables, this collects all
per-rule bpf chunks and place them in the same program blob.
Benefits are many:
* Netlink-based interface, so we don't need to expose helper functions
from the ebpf because of the nf_tables jit support. This allow us to
keep all the scary details behind the curtain and let us evolve
* Simplified infrastructure: We don't need the ebpf verifier complexity
either given we trust the code we generate from the kernel. We don't
need any complex userspace tooling either, just libnftnl and nft
* Hardware offload: We can use this to offload rulesets to the only
smartnic driver that we have in the tree that already implements bpf
offload, hence, we can reuse this work already in place.
* Good support for incremental updates, we don't lose stateful
information when performing updates on the ruleset. No full table/blob
replacement as in iptables, which is a major well-known design
* Use existing bpf arch jits available in the tree.
Among many others that are also described in the nftables wiki .
Moreover, with some incremental work, this infrastructure will allow us
to translate software nftables configurations to any backend target,
including TCAM based hardware offloads commonly available in switches
P.S: Only classic bpf for this PoC at this stage, but it's a matter of
doing some knitting to get all the pieces together.
Pablo Neira Ayuso (3):
netfilter: nf_tables: add infrastructure to provide intermediate
netfilter: add ast to target transformation
netfilter: nf_tables: add BPF-based jit infrastructure
include/net/netfilter/nf_tables.h | 25 +++
include/net/netfilter/nf_tables_jit.h | 136 ++++++++++++++
net/ipv4/netfilter/nf_tables_ipv4.c | 7 +-
net/netfilter/Makefile | 3 +-
net/netfilter/nf_tables_api.c | 28 +++
net/netfilter/nf_tables_bpf.c | 92 +++++++++
net/netfilter/nf_tables_jit.c | 339 ++++++++++++++++++++++++++++++++++
net/netfilter/nft_cmp.c | 87 +++++++++
net/netfilter/nft_meta.c | 19 ++
net/netfilter/nft_payload.c | 22 +++
10 files changed, 752 insertions(+), 6 deletions(-)
create mode 100644 include/net/netfilter/nf_tables_jit.h
create mode 100644 net/netfilter/nf_tables_bpf.c
create mode 100644 net/netfilter/nf_tables_jit.c