From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.8 required=3.0 tests=DKIM_SIGNED,DKIM_VALID, DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH,MAILING_LIST_MULTI,SIGNED_OFF_BY, SPF_PASS,USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 8A076C43381 for ; Wed, 20 Mar 2019 14:50:32 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id 582802146E for ; Wed, 20 Mar 2019 14:50:32 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="KknKW56Y" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728298AbfCTOub (ORCPT ); Wed, 20 Mar 2019 10:50:31 -0400 Received: from mail-qt1-f195.google.com ([209.85.160.195]:41891 "EHLO mail-qt1-f195.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728122AbfCTOuA (ORCPT ); Wed, 20 Mar 2019 10:50:00 -0400 Received: by mail-qt1-f195.google.com with SMTP id w30so2795851qta.8 for ; Wed, 20 Mar 2019 07:49:59 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=BonSCT/GwMRrnyr8rbiB+8hA54xantrSveQJYaHbGxU=; b=KknKW56Y+YwUzU74Pz4o0FPsAdbvObYGtxXbJ8fObgl5tgUbzOqPARw/15hytLITji cmnUAbk1Y4DddHed88yNjGQ09ML51G9Syzw0M2x1Qihz7QLRZGz2R+lH9eU3cY2LbNjZ S2ryT3QszvVGY1BJINu6hNgcyePBhUYjhVrpvJU8KGhR96tr1mg6W2/07sDJ2sbkgFMK VFz1sTn3fnCTeBiPtzx5/6KNfPoisNTt8sXwCtHTeKrnQnXw0OFO6AjCiqyFS4CoS6eY A7fEavxEhbk9evWqXAE4zQbZQ31JpMJKxZo74RvfKtF2ho6J0fvoMy+KfbEHEqKVQkEw 8yNg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=BonSCT/GwMRrnyr8rbiB+8hA54xantrSveQJYaHbGxU=; b=V7D44gMr6/4JSOZo4kMtVssUoAppom5aEQ5pHoz9f7bUGCjkZfMMIGqbQSJH7UGvzK dfnZBBinKuIaRfqKwPjBg5k9yuLfZTRja9GPKfne/ieBkhcSXxMLuSkPeRvkdXNzcTeO llv23GclMdq1nxFT5h1sT3/ES7tgaD7585bokq73wWqg3kHO+P5uh5Qp8dnuqUoanocH 6/uohGbQKfGgRSG1RG4w0RD1ljxjttPbd57N27wls4L6dKsHOKqHooKrzHSbZ0N9biTl OOd9msbRvZbtk9L95DnX0RBeyHuA9Mt5tcCAeHwvX7a2NcpColzzypYFguVWacpxvqNu f47Q== X-Gm-Message-State: APjAAAXvSrJ4KdzEafehb/CKUjxelnblX47dth6qPLjnTuNc7F7XDMla ObG13Iii/0EsMnmL4tm1O+qSH0qn X-Google-Smtp-Source: APXvYqxGy9/LNuSi1dLY8WcSD/BSTIGEy2vXzQ7n9dfu7IFvVYMjQc9oUZxcPWhhpTzsk5iNEPs84w== X-Received: by 2002:aed:23e1:: with SMTP id k30mr7738049qtc.17.1553093398816; Wed, 20 Mar 2019 07:49:58 -0700 (PDT) Received: from willemb1.nyc.corp.google.com ([2620:0:1003:315:3fa1:a34c:1128:1d39]) by smtp.gmail.com with ESMTPSA id x201sm1142257qkb.92.2019.03.20.07.49.57 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 20 Mar 2019 07:49:57 -0700 (PDT) From: Willem de Bruijn To: netdev@vger.kernel.org Cc: ast@kernel.org, daniel@iogearbox.net, sdf@google.com, posk@google.com, Willem de Bruijn Subject: [PATCH bpf-next 07/13] bpf: add bpf_skb_adjust_room mode BPF_ADJ_ROOM_MAC Date: Wed, 20 Mar 2019 10:49:38 -0400 Message-Id: <20190320144944.147862-8-willemdebruijn.kernel@gmail.com> X-Mailer: git-send-email 2.21.0.225.g810b269d1ac-goog In-Reply-To: <20190320144944.147862-1-willemdebruijn.kernel@gmail.com> References: <20190320144944.147862-1-willemdebruijn.kernel@gmail.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org From: Willem de Bruijn bpf_skb_adjust_room net allows inserting room in an skb. Existing mode BPF_ADJ_ROOM_NET inserts room after the network header by pulling the skb, moving the network header forward and zeroing the new space. Add new mode BPF_ADJUST_ROOM_MAC that inserts room after the mac header. This allows inserting tunnel headers in front of the network header without having to recreate the network header in the original space, avoiding two copies. Signed-off-by: Willem de Bruijn --- include/uapi/linux/bpf.h | 6 +++++- net/core/filter.c | 38 ++++++++++++++++++++------------------ 2 files changed, 25 insertions(+), 19 deletions(-) diff --git a/include/uapi/linux/bpf.h b/include/uapi/linux/bpf.h index 929c8e537a14a..4f5c918e6fcf4 100644 --- a/include/uapi/linux/bpf.h +++ b/include/uapi/linux/bpf.h @@ -1478,7 +1478,10 @@ union bpf_attr { * Grow or shrink the room for data in the packet associated to * *skb* by *len_diff*, and according to the selected *mode*. * - * There is a single supported mode at this time: + * There are two supported modes at this time: + * + * * **BPF_ADJ_ROOM_MAC**: Adjust room at the mac layer + * (room space is added or removed below the layer 2 header). * * * **BPF_ADJ_ROOM_NET**: Adjust room at the network layer * (room space is added or removed below the layer 3 header). @@ -2593,6 +2596,7 @@ enum bpf_func_id { /* Mode for BPF_FUNC_skb_adjust_room helper. */ enum bpf_adj_room_mode { BPF_ADJ_ROOM_NET, + BPF_ADJ_ROOM_MAC, }; /* Mode for BPF_FUNC_skb_load_bytes_relative helper. */ diff --git a/net/core/filter.c b/net/core/filter.c index 8e15fb919b574..1a0cf578b4502 100644 --- a/net/core/filter.c +++ b/net/core/filter.c @@ -2963,9 +2963,8 @@ static u32 bpf_skb_net_base_len(const struct sk_buff *skb) } } -static int bpf_skb_net_grow(struct sk_buff *skb, u32 len_diff) +static int bpf_skb_net_grow(struct sk_buff *skb, u32 off, u32 len_diff) { - u32 off = skb_mac_header_len(skb) + bpf_skb_net_base_len(skb); int ret; if (skb_is_gso(skb) && !skb_is_gso_tcp(skb)) @@ -2992,9 +2991,8 @@ static int bpf_skb_net_grow(struct sk_buff *skb, u32 len_diff) return 0; } -static int bpf_skb_net_shrink(struct sk_buff *skb, u32 len_diff) +static int bpf_skb_net_shrink(struct sk_buff *skb, u32 off, u32 len_diff) { - u32 off = skb_mac_header_len(skb) + bpf_skb_net_base_len(skb); int ret; if (skb_is_gso(skb) && !skb_is_gso_tcp(skb)) @@ -3027,7 +3025,8 @@ static u32 __bpf_skb_max_len(const struct sk_buff *skb) SKB_MAX_ALLOC; } -static int bpf_skb_adjust_net(struct sk_buff *skb, s32 len_diff) +BPF_CALL_4(bpf_skb_adjust_room, struct sk_buff *, skb, s32, len_diff, + u32, mode, u64, flags) { bool trans_same = skb->transport_header == skb->network_header; u32 len_cur, len_diff_abs = abs(len_diff); @@ -3035,14 +3034,28 @@ static int bpf_skb_adjust_net(struct sk_buff *skb, s32 len_diff) u32 len_max = __bpf_skb_max_len(skb); __be16 proto = skb->protocol; bool shrink = len_diff < 0; + u32 off; int ret; + if (unlikely(flags)) + return -EINVAL; if (unlikely(len_diff_abs > 0xfffU)) return -EFAULT; if (unlikely(proto != htons(ETH_P_IP) && proto != htons(ETH_P_IPV6))) return -ENOTSUPP; + off = skb_mac_header_len(skb); + switch (mode) { + case BPF_ADJ_ROOM_NET: + off += bpf_skb_net_base_len(skb); + break; + case BPF_ADJ_ROOM_MAC: + break; + default: + return -ENOTSUPP; + } + len_cur = skb->len - skb_network_offset(skb); if (skb_transport_header_was_set(skb) && !trans_same) len_cur = skb_network_header_len(skb); @@ -3052,24 +3065,13 @@ static int bpf_skb_adjust_net(struct sk_buff *skb, s32 len_diff) !skb_is_gso(skb)))) return -ENOTSUPP; - ret = shrink ? bpf_skb_net_shrink(skb, len_diff_abs) : - bpf_skb_net_grow(skb, len_diff_abs); + ret = shrink ? bpf_skb_net_shrink(skb, off, len_diff_abs) : + bpf_skb_net_grow(skb, off, len_diff_abs); bpf_compute_data_pointers(skb); return ret; } -BPF_CALL_4(bpf_skb_adjust_room, struct sk_buff *, skb, s32, len_diff, - u32, mode, u64, flags) -{ - if (unlikely(flags)) - return -EINVAL; - if (likely(mode == BPF_ADJ_ROOM_NET)) - return bpf_skb_adjust_net(skb, len_diff); - - return -ENOTSUPP; -} - static const struct bpf_func_proto bpf_skb_adjust_room_proto = { .func = bpf_skb_adjust_room, .gpl_only = false, -- 2.21.0.225.g810b269d1ac-goog