From b67abc51ba6f78be79f344dfda9c6d0753d79aea Mon Sep 17 00:00:00 2001 From: Pablo Neira Ayuso Date: Tue, 2 Nov 2021 14:01:58 +0100 Subject: src: raw payload match and mangle on inner header / payload data This patch adds support to match on inner header / payload data: # nft add rule x y @ih,32,32 0x14000000 counter you can also mangle payload data: # nft add rule x y @ih,32,32 set 0x14000000 counter This update triggers a checksum update at the layer 4 header via csum_flags, mangling odd bytes is also aligned to 16-bits. Signed-off-by: Pablo Neira Ayuso --- src/evaluate.c | 3 +++ src/netlink_linearize.c | 5 +++-- src/parser_bison.y | 2 ++ src/proto.c | 2 ++ src/scanner.l | 1 + 5 files changed, 11 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/evaluate.c b/src/evaluate.c index 6a8c396f..a268b3cb 100644 --- a/src/evaluate.c +++ b/src/evaluate.c @@ -2446,6 +2446,9 @@ static bool stmt_evaluate_payload_need_csum(const struct expr *payload) { const struct proto_desc *desc; + if (payload->payload.base == PROTO_BASE_INNER_HDR) + return true; + desc = payload->payload.desc; return desc && desc->checksum_key; diff --git a/src/netlink_linearize.c b/src/netlink_linearize.c index 454b9ba3..111102fd 100644 --- a/src/netlink_linearize.c +++ b/src/netlink_linearize.c @@ -1028,8 +1028,9 @@ static void netlink_gen_payload_stmt(struct netlink_linearize_ctx *ctx, nftnl_expr_set_u32(nle, NFTNL_EXPR_PAYLOAD_CSUM_OFFSET, csum_off / BITS_PER_BYTE); } - if (expr->payload.base == PROTO_BASE_NETWORK_HDR && desc && - payload_needs_l4csum_update_pseudohdr(expr, desc)) + if ((expr->payload.base == PROTO_BASE_NETWORK_HDR && desc && + payload_needs_l4csum_update_pseudohdr(expr, desc)) || + expr->payload.base == PROTO_BASE_INNER_HDR) nftnl_expr_set_u32(nle, NFTNL_EXPR_PAYLOAD_FLAGS, NFT_PAYLOAD_L4CSUM_PSEUDOHDR); diff --git a/src/parser_bison.y b/src/parser_bison.y index 65fd35a3..eb89a589 100644 --- a/src/parser_bison.y +++ b/src/parser_bison.y @@ -318,6 +318,7 @@ int nft_lex(void *, void *, void *); %token LL_HDR "ll" %token NETWORK_HDR "nh" %token TRANSPORT_HDR "th" +%token INNER_HDR "ih" %token BRIDGE "bridge" @@ -5260,6 +5261,7 @@ payload_raw_expr : AT payload_base_spec COMMA NUM COMMA NUM payload_base_spec : LL_HDR { $$ = PROTO_BASE_LL_HDR; } | NETWORK_HDR { $$ = PROTO_BASE_NETWORK_HDR; } | TRANSPORT_HDR { $$ = PROTO_BASE_TRANSPORT_HDR; } + | INNER_HDR { $$ = PROTO_BASE_INNER_HDR; } ; eth_hdr_expr : ETHER eth_hdr_field close_scope_eth diff --git a/src/proto.c b/src/proto.c index 2b61e0ba..fe58c83a 100644 --- a/src/proto.c +++ b/src/proto.c @@ -28,6 +28,7 @@ const char *proto_base_names[] = { [PROTO_BASE_LL_HDR] = "link layer", [PROTO_BASE_NETWORK_HDR] = "network layer", [PROTO_BASE_TRANSPORT_HDR] = "transport layer", + [PROTO_BASE_INNER_HDR] = "payload data", }; const char *proto_base_tokens[] = { @@ -35,6 +36,7 @@ const char *proto_base_tokens[] = { [PROTO_BASE_LL_HDR] = "ll", [PROTO_BASE_NETWORK_HDR] = "nh", [PROTO_BASE_TRANSPORT_HDR] = "th", + [PROTO_BASE_INNER_HDR] = "ih", }; const struct proto_hdr_template proto_unknown_template = diff --git a/src/scanner.l b/src/scanner.l index 6cc7778d..5d263f9d 100644 --- a/src/scanner.l +++ b/src/scanner.l @@ -414,6 +414,7 @@ addrstring ({macaddr}|{ip4addr}|{ip6addr}) "ll" { return LL_HDR; } "nh" { return NETWORK_HDR; } "th" { return TRANSPORT_HDR; } +"ih" { return INNER_HDR; } "bridge" { return BRIDGE; } -- cgit v1.2.3