From patchwork Wed Nov 4 03:12:10 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andre Guedes X-Patchwork-Id: 1393607 X-Patchwork-Delegate: anthony.l.nguyen@intel.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=osuosl.org (client-ip=140.211.166.138; helo=whitealder.osuosl.org; envelope-from=intel-wired-lan-bounces@osuosl.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=intel.com Received: from whitealder.osuosl.org (smtp1.osuosl.org [140.211.166.138]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 4CQsCP45J8z9sPB for ; Wed, 4 Nov 2020 14:12:33 +1100 (AEDT) Received: from localhost (localhost [127.0.0.1]) by whitealder.osuosl.org (Postfix) with ESMTP id 328028697D; Wed, 4 Nov 2020 03:12:32 +0000 (UTC) X-Virus-Scanned: amavisd-new at osuosl.org Received: from whitealder.osuosl.org ([127.0.0.1]) by localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id ZcL5p26ZbqLo; Wed, 4 Nov 2020 03:12:31 +0000 (UTC) Received: from ash.osuosl.org (ash.osuosl.org [140.211.166.34]) by whitealder.osuosl.org (Postfix) with ESMTP id 16C0586AEA; Wed, 4 Nov 2020 03:12:31 +0000 (UTC) X-Original-To: intel-wired-lan@lists.osuosl.org Delivered-To: intel-wired-lan@lists.osuosl.org Received: from whitealder.osuosl.org (smtp1.osuosl.org [140.211.166.138]) by ash.osuosl.org (Postfix) with ESMTP id CF5E91BF989 for ; Wed, 4 Nov 2020 03:12:27 +0000 (UTC) Received: from localhost (localhost [127.0.0.1]) by whitealder.osuosl.org (Postfix) with ESMTP id C831486AEA for ; Wed, 4 Nov 2020 03:12:27 +0000 (UTC) X-Virus-Scanned: amavisd-new at osuosl.org Received: from whitealder.osuosl.org ([127.0.0.1]) by localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id xPp4TF802fyW for ; Wed, 4 Nov 2020 03:12:27 +0000 (UTC) X-Greylist: domain auto-whitelisted by SQLgrey-1.7.6 Received: from mga18.intel.com (mga18.intel.com [134.134.136.126]) by whitealder.osuosl.org (Postfix) with ESMTPS id 0588086AB1 for ; Wed, 4 Nov 2020 03:12:26 +0000 (UTC) IronPort-SDR: 7v3p0uE+I9PaU+S7D3AsV9wiyRuqaHIfLTfDQFqS9pDi0zmvNWARiNIwrefqTIvdQP1TozBuv+ QJ2r7W/aYLgg== X-IronPort-AV: E=McAfee;i="6000,8403,9794"; a="156934765" X-IronPort-AV: E=Sophos;i="5.77,449,1596524400"; d="scan'208";a="156934765" X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from orsmga004.jf.intel.com ([10.7.209.38]) by orsmga106.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 03 Nov 2020 19:12:26 -0800 IronPort-SDR: E7dD025xX9Bywo3VsvXBdZ73//fuawO/EQ8GogGUD/InOAFAtsh/1tRtppa1F/49zAEVJktplr sD26h4YpGsug== X-IronPort-AV: E=Sophos;i="5.77,449,1596524400"; d="scan'208";a="471042963" Received: from abkumar-dell.amr.corp.intel.com ([10.212.180.108]) by orsmga004-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 03 Nov 2020 19:12:26 -0800 From: Andre Guedes To: intel-wired-lan@lists.osuosl.org Date: Tue, 3 Nov 2020 19:12:10 -0800 Message-Id: <20201104031210.27772-10-andre.guedes@intel.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104031210.27772-1-andre.guedes@intel.com> References: <20201104031210.27772-1-andre.guedes@intel.com> MIME-Version: 1.0 Subject: [Intel-wired-lan] [PATCH v4 9/9] igc: Add support for XDP_REDIRECT action X-BeenThere: intel-wired-lan@osuosl.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Intel Wired Ethernet Linux Kernel Driver Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: intel-wired-lan-bounces@osuosl.org Sender: "Intel-wired-lan" This patch adds support for the XDP_REDIRECT action which enables XDP programs to redirect packets arriving at I225 NIC. It also implements the ndo_xdp_xmit ops, enabling the igc driver to transmit packets forwarded to it by xdp programs running on other interfaces. The patch tweaks the driver's page counting scheme (as described in '8ce29c679a6e i40e: tweak page counting for XDP_REDIRECT' and implemented by other Intel drivers) in order to properly support XDP_REDIRECT action. This patch has been tested with the sample apps "xdp_redirect_cpu" and "xdp_redirect_map" located in samples/bpf/. Signed-off-by: Andre Guedes Reviewed-by: Maciej Fijalkowski --- drivers/net/ethernet/intel/igc/igc_main.c | 59 +++++++++++++++++++++-- 1 file changed, 56 insertions(+), 3 deletions(-) diff --git a/drivers/net/ethernet/intel/igc/igc_main.c b/drivers/net/ethernet/intel/igc/igc_main.c index ee8e4615aba5..f406364e8797 100644 --- a/drivers/net/ethernet/intel/igc/igc_main.c +++ b/drivers/net/ethernet/intel/igc/igc_main.c @@ -27,6 +27,7 @@ #define IGC_XDP_PASS 0 #define IGC_XDP_CONSUMED BIT(0) #define IGC_XDP_TX BIT(1) +#define IGC_XDP_REDIRECT BIT(2) static int debug = -1; @@ -1720,8 +1721,8 @@ static bool igc_can_reuse_rx_page(struct igc_rx_buffer *rx_buffer) * the pagecnt_bias and page count so that we fully restock the * number of references the driver holds. */ - if (unlikely(!pagecnt_bias)) { - page_ref_add(page, USHRT_MAX); + if (unlikely(pagecnt_bias == 1)) { + page_ref_add(page, USHRT_MAX - 1); rx_buffer->pagecnt_bias = USHRT_MAX; } @@ -1862,7 +1863,8 @@ static bool igc_alloc_mapped_page(struct igc_ring *rx_ring, bi->dma = dma; bi->page = page; bi->page_offset = igc_rx_offset(rx_ring); - bi->pagecnt_bias = 1; + page_ref_add(page, USHRT_MAX - 1); + bi->pagecnt_bias = USHRT_MAX; return true; } @@ -2058,6 +2060,12 @@ static struct sk_buff *igc_xdp_run_prog(struct igc_adapter *adapter, else res = IGC_XDP_TX; break; + case XDP_REDIRECT: + if (xdp_do_redirect(adapter->netdev, xdp, prog) < 0) + res = IGC_XDP_CONSUMED; + else + res = IGC_XDP_REDIRECT; + break; default: bpf_warn_invalid_xdp_action(act); fallthrough; @@ -2099,6 +2107,9 @@ static void igc_finalize_xdp(struct igc_adapter *adapter, int status) igc_flush_tx_descriptors(ring); __netif_tx_unlock(nq); } + + if (status & IGC_XDP_REDIRECT) + xdp_do_flush(); } static int igc_clean_rx_irq(struct igc_q_vector *q_vector, const int budget) @@ -2167,6 +2178,7 @@ static int igc_clean_rx_irq(struct igc_q_vector *q_vector, const int budget) rx_buffer->pagecnt_bias++; break; case IGC_XDP_TX: + case IGC_XDP_REDIRECT: igc_rx_buffer_flip(rx_buffer, truesize); xdp_status |= xdp_res; break; @@ -5132,6 +5144,46 @@ static int igc_bpf(struct net_device *dev, struct netdev_bpf *bpf) } } +static int igc_xdp_xmit(struct net_device *dev, int num_frames, + struct xdp_frame **frames, u32 flags) +{ + struct igc_adapter *adapter = netdev_priv(dev); + int cpu = smp_processor_id(); + struct netdev_queue *nq; + struct igc_ring *ring; + int i, drops; + + if (unlikely(test_bit(__IGC_DOWN, &adapter->state))) + return -ENETDOWN; + + if (unlikely(flags & ~XDP_XMIT_FLAGS_MASK)) + return -EINVAL; + + ring = igc_xdp_get_tx_ring(adapter, cpu); + nq = txring_txq(ring); + + __netif_tx_lock(nq, cpu); + + drops = 0; + for (i = 0; i < num_frames; i++) { + int err; + struct xdp_frame *xdpf = frames[i]; + + err = igc_xdp_init_tx_descriptor(ring, xdpf); + if (err) { + xdp_return_frame_rx_napi(xdpf); + drops++; + } + } + + if (flags & XDP_XMIT_FLUSH) + igc_flush_tx_descriptors(ring); + + __netif_tx_unlock(nq); + + return num_frames - drops; +} + static const struct net_device_ops igc_netdev_ops = { .ndo_open = igc_open, .ndo_stop = igc_close, @@ -5146,6 +5198,7 @@ static const struct net_device_ops igc_netdev_ops = { .ndo_do_ioctl = igc_ioctl, .ndo_setup_tc = igc_setup_tc, .ndo_bpf = igc_bpf, + .ndo_xdp_xmit = igc_xdp_xmit, }; /* PCIe configuration access */