Netdev List
 help / color / mirror / Atom feed
* Re: [PATCH net-next 00/10] udp: implement GRO support
From: David Miller @ 2018-11-08  0:23 UTC (permalink / raw)
  To: pabeni; +Cc: netdev, willemb, steffen.klassert, subashab
In-Reply-To: <cover.1541588248.git.pabeni@redhat.com>

From: Paolo Abeni <pabeni@redhat.com>
Date: Wed,  7 Nov 2018 12:38:27 +0100

> This series implements GRO support for UDP sockets, as the RX counterpart
> of commit bec1f6f69736 ("udp: generate gso with UDP_SEGMENT").
> The core functionality is implemented by the second patch, introducing a new
> sockopt to enable UDP_GRO, while patch 3 implements support for passing the
> segment size to the user space via a new cmsg.
> UDP GRO performs a socket lookup for each ingress packets and aggregate datagram
> directed to UDP GRO enabled sockets with constant l4 tuple.
> 
> UDP GRO packets can land on non GRO-enabled sockets, e.g. due to iptables NAT
> rules, and that could potentially confuse existing applications.
> 
> The solution adopted here is to de-segment the GRO packet before enqueuing
> as needed. Since we must cope with packet reinsertion after de-segmentation,
> the relevant code is factored-out in ipv4 and ipv6 specific helpers and exposed
> to UDP usage.
> 
> While the current code can probably be improved, this safeguard ,implemented in
> the patches 4-7, allows future enachements to enable UDP GSO offload on more
> virtual devices eventually even on forwarded packets.
> 
> The last 4 for patches implement some performance and functional self-tests,
> re-using the existing udpgso infrastructure. The problematic scenario described
> above is explicitly tested.
> 
> This revision of the series try to address the feedback provided by Willem and
> Subash on previous iteration.

Series applied.

^ permalink raw reply

* Re: [PATCH bpf-next 3/3] bpftool: support loading flow dissector
From: Stanislav Fomichev @ 2018-11-08  0:40 UTC (permalink / raw)
  To: Jakub Kicinski
  Cc: Stanislav Fomichev, netdev, linux-kselftest, ast, daniel, shuah,
	quentin.monnet, guro, jiong.wang, bhole_prashant_q7,
	john.fastabend, jbenc, treeze.taeung, yhs, osk, sandipan
In-Reply-To: <20181107154155.4e7ca3b3@cakuba.netronome.com>

On 11/07, Jakub Kicinski wrote:
> On Wed, 7 Nov 2018 15:34:48 -0800, Stanislav Fomichev wrote:
> > On 11/07, Jakub Kicinski wrote:
> > > On Wed, 7 Nov 2018 15:13:33 -0800, Stanislav Fomichev wrote:  
> > > > On 11/07, Jakub Kicinski wrote:  
> > > > > On Wed,  7 Nov 2018 14:43:56 -0800, Stanislav Fomichev wrote:    
> > > > > > bpftool map update pinned /sys/fs/bpf/flow/jmp_table \
> > > > > >         key 0 0 0 0 \
> > > > > >         value pinned /sys/fs/bpf/flow/IP/0    
> > > > > 
> > > > > Where is that /0 coming from ?  Is that in source code?  I don't see
> > > > > libbpf adding it, maybe I'm missing something.    
> > > > libbpf adds that, that's a program instance:
> > > > https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/tools/lib/bpf/libbpf.c#n1744  
> > > 
> > > Ugh, I was looking at bpf_object__pin() which uses names :(
> > > 
> > > We never use this multi-instance thing, and I don't think bpftool ever
> > > will, so IMHO it'd be good if we just re-did the pinning loop in
> > > bpftool.  
> > I wonder whether I should just add special case to bpf_program__pin: don't
> > create a subdir when instances.nr == 1 (and just create a file pin for
> > single instance)? In that case I can continue to use libbpf and don't reinvent
> > the wheel. Any objections?
> 
> Mm.. I'm afraid libbpf needs to keep backward compatibility.  We'd have
> to add some way for the user (bpftool code) to request the instance ID
> does not appear, but (potential) existing users should keep seeing them.
> Perhaps others disagree.
AFAICT, nobody (seriously) uses bpf_object__pin in the kernel tree and I
have a feeling that the situation is the same outside of the kernel tree.
We can revert/work around if we break somebody, I just don't want to
reimplement the same code in bpftool while there is a possibility that
nobody is using that.

I'll post my proposal as v3, let's see whether other people have
the same objections.

Btw, did we officially commit to the libbpf api/abi somewhere? It always
felt to me like an internal and work-in-progress library.

^ permalink raw reply

* Aw: [PATCH] staging: net: ipv4: tcp_westwood: fixed warnings and checks
From: Lino Sanfilippo @ 2018-11-08 10:22 UTC (permalink / raw)
  To: Suraj Singh; +Cc: davem, kuznet, yoshfuji, netdev, linux-kernel, suraj1998
In-Reply-To: <1541670377-17483-1-git-send-email-suraj1998@gmail.com>

Hi,

> Gesendet: Donnerstag, 08. November 2018 um 10:46 Uhr
> Von: "Suraj Singh" <suraj1998@gmail.com>
> An: davem@davemloft.net
> Cc: kuznet@ms2.inr.ac.ru, yoshfuji@linux-ipv6.org, netdev@vger.kernel.org, linux-kernel@vger.kernel.org, suraj1998@gmail.com
> Betreff: [PATCH] staging: net: ipv4: tcp_westwood: fixed warnings and checks
>
> Fixed warnings and checks for TCP Westwood
> 
> Signed-off-by: Suraj Singh <suraj1998@gmail.com>
> ---


You use the prefix "staging" again in you subject line, which still is wrong. "staging" means that you
fix something from the staging area (see drivers/staging/ in the kernel sources. BTW: the staging area is a much
better starting point for first patches than the core parts of the network subsystem).
Also if you send a subsequent version of a patch you have to write the version number (e.g. v2) in the 
subject line. Have a look at other patch submissions on this mailing list for examples.

Regards,
Lino

^ permalink raw reply

* [PATCH][net-hns3-next] net: hns3: fix spelling mistake, "assertting" -> "asserting"
From: Colin King @ 2018-11-08 10:32 UTC (permalink / raw)
  To: Yisen Zhuang, Salil Mehta, David S . Miller, Peng Li, netdev
  Cc: kernel-janitors, linux-kernel

From: Colin Ian King <colin.king@canonical.com>

Trivial fix to spelling mistake in dev_err error message

Signed-off-by: Colin Ian King <colin.king@canonical.com>
---
 drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index 579945bdcc76..77980e54ad09 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -2504,7 +2504,7 @@ static int hclge_reset_prepare_wait(struct hclge_dev *hdev)
 		ret = hclge_func_reset_cmd(hdev, 0);
 		if (ret) {
 			dev_err(&hdev->pdev->dev,
-				"assertting function reset fail %d!\n", ret);
+				"asserting function reset fail %d!\n", ret);
 			return ret;
 		}
 
-- 
2.19.1

^ permalink raw reply related

* Re: Kernel 4.19 network performance - forwarding/routing normal users traffic
From: Paweł Staszewski @ 2018-11-08  0:59 UTC (permalink / raw)
  To: Jesper Dangaard Brouer; +Cc: David Ahern, netdev, Yoel Caspersen
In-Reply-To: <20181105211733.7468cc61@redhat.com>



W dniu 05.11.2018 o 21:17, Jesper Dangaard Brouer pisze:
> On Sun, 4 Nov 2018 01:24:03 +0100 Paweł Staszewski <pstaszewski@itcare.pl> wrote:
>
>> And today again after allpy patch for page allocator - reached again
>> 64/64 Gbit/s
>>
>> with only 50-60% cpu load
> Great.
>
>> today no slowpath hit for netwoking :)
>>
>> But again dropped pckt at 64GbitRX and 64TX ....
>> And as it should not be pcie express limit  -i think something more is
> Well, this does sounds like a PCIe bandwidth limit to me.
>
> See the PCIe BW here: https://en.wikipedia.org/wiki/PCI_Express
>
> You likely have PCIe v3, where 1-lane have 984.6 MBytes/s or 7.87 Gbit/s
> Thus,  x16-lanes have 15.75 GBytes or 126 Gbit/s.  It does say "in each
> direction", but you are also forwarding this RX->TX on both (dual) ports
> NIC that is sharing the same PCIe slot.
Network controller changed from 2-port 100G connectx4 to 2 separate 
cards 100G connectx5


    PerfTop:   92239 irqs/sec  kernel:99.4%  exact:  0.0% [4000Hz 
cycles],  (all, 56 CPUs)
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

      6.65%  [kernel]       [k] irq_entries_start
      5.57%  [kernel]       [k] tasklet_action_common.isra.21
      4.60%  [kernel]       [k] mlx5_eq_int
      4.04%  [kernel]       [k] mlx5e_skb_from_cqe_mpwrq_linear
      3.66%  [kernel]       [k] _raw_spin_lock_irqsave
      3.58%  [kernel]       [k] mlx5e_sq_xmit
      2.66%  [kernel]       [k] fib_table_lookup
      2.52%  [kernel]       [k] _raw_spin_lock
      2.51%  [kernel]       [k] build_skb
      2.50%  [kernel]       [k] _raw_spin_lock_irq
      2.04%  [kernel]       [k] try_to_wake_up
      1.83%  [kernel]       [k] queued_spin_lock_slowpath
      1.81%  [kernel]       [k] mlx5e_poll_tx_cq
      1.65%  [kernel]       [k] do_idle
      1.50%  [kernel]       [k] mlx5e_poll_rx_cq
      1.34%  [kernel]       [k] __sched_text_start
      1.32%  [kernel]       [k] cmd_exec
      1.30%  [kernel]       [k] cmd_work_handler
      1.16%  [kernel]       [k] vlan_do_receive
      1.15%  [kernel]       [k] memcpy_erms
      1.15%  [kernel]       [k] __dev_queue_xmit
      1.07%  [kernel]       [k] mlx5_cmd_comp_handler
      1.06%  [kernel]       [k] sched_ttwu_pending
      1.00%  [kernel]       [k] ipt_do_table
      0.98%  [kernel]       [k] ip_finish_output2
      0.92%  [kernel]       [k] pfifo_fast_dequeue
      0.88%  [kernel]       [k] mlx5e_handle_rx_cqe_mpwrq
      0.78%  [kernel]       [k] dev_gro_receive
      0.78%  [kernel]       [k] mlx5e_napi_poll
      0.76%  [kernel]       [k] mlx5e_post_rx_mpwqes
      0.70%  [kernel]       [k] process_one_work
      0.67%  [kernel]       [k] __netif_receive_skb_core
      0.65%  [kernel]       [k] __build_skb
      0.63%  [kernel]       [k] llist_add_batch
      0.62%  [kernel]       [k] tcp_gro_receive
      0.60%  [kernel]       [k] inet_gro_receive
      0.59%  [kernel]       [k] ip_route_input_rcu
      0.59%  [kernel]       [k] rcu_irq_exit
      0.56%  [kernel]       [k] napi_complete_done
      0.52%  [kernel]       [k] kmem_cache_alloc
      0.48%  [kernel]       [k] __softirqentry_text_start
      0.48%  [kernel]       [k] mlx5e_xmit
      0.47%  [kernel]       [k] __queue_work
      0.46%  [kernel]       [k] memset_erms
      0.46%  [kernel]       [k] dev_hard_start_xmit
      0.45%  [kernel]       [k] insert_work
      0.45%  [kernel]       [k] enqueue_task_fair
      0.44%  [kernel]       [k] __wake_up_common
      0.43%  [kernel]       [k] finish_task_switch
      0.43%  [kernel]       [k] kmem_cache_free_bulk
      0.42%  [kernel]       [k] ip_forward
      0.42%  [kernel]       [k] worker_thread
      0.41%  [kernel]       [k] schedule
      0.41%  [kernel]       [k] _raw_spin_unlock_irqrestore
      0.40%  [kernel]       [k] netif_skb_features
      0.40%  [kernel]       [k] queue_work_on
      0.40%  [kernel]       [k] pfifo_fast_enqueue
      0.39%  [kernel]       [k] vlan_dev_hard_start_xmit
      0.39%  [kernel]       [k] page_frag_free
      0.36%  [kernel]       [k] swiotlb_map_page
      0.36%  [kernel]       [k] update_cfs_rq_h_load
      0.35%  [kernel]       [k] validate_xmit_skb.isra.142
      0.35%  [kernel]       [k] dev_ifconf
      0.35%  [kernel]       [k] check_preempt_curr
      0.34%  [kernel]       [k] _raw_spin_trylock
      0.34%  [kernel]       [k] rcu_idle_exit
      0.33%  [kernel]       [k] ip_rcv_core.isra.20.constprop.25
      0.33%  [kernel]       [k] __qdisc_run
      0.33%  [kernel]       [k] skb_release_data
      0.32%  [kernel]       [k] native_sched_clock
      0.30%  [kernel]       [k] add_interrupt_randomness
      0.29%  [kernel]       [k] interrupt_entry
      0.28%  [kernel]       [k] skb_gro_receive
      0.26%  [kernel]       [k] read_tsc
      0.26%  [kernel]       [k] __get_xps_queue_idx
      0.26%  [kernel]       [k] inet_gifconf
      0.26%  [kernel]       [k] skb_segment
      0.25%  [kernel]       [k] __tasklet_schedule_common
      0.25%  [kernel]       [k] smpboot_thread_fn
      0.23%  [kernel]       [k] __update_load_avg_se
      0.22%  [kernel]       [k] tcp4_gro_receive


Not much traffic now:
   bwm-ng v0.6.1 (probing every 0.500s), press 'h' for help
   input: /proc/net/dev type: rate
   |         iface                   Rx Tx                Total
==============================================================================
          enp175s0:           6.95 Gb/s            4.20 Gb/s           
11.15 Gb/s
          enp216s0:           4.23 Gb/s            6.98 Gb/s           
11.21 Gb/s
------------------------------------------------------------------------------
             total:          11.18 Gb/s           11.18 Gb/s           
22.37 Gb/s

   bwm-ng v0.6.1 (probing every 1.000s), press 'h' for help
   input: /proc/net/dev type: rate
   |         iface                   Rx Tx                Total
==============================================================================
          enp175s0:       700264.50 P/s        923890.25 P/s 1624154.75 P/s
          enp216s0:       932598.81 P/s        708771.50 P/s 1641370.25 P/s
------------------------------------------------------------------------------
             total:      1632863.38 P/s       1632661.75 P/s 3265525.00 P/s






>
>
>> going on there - and hard to catch - cause perf top doestn chenged
>> besides there is no queued slowpath hit now
>>
>> I ordered now also intel cards to compare - but 3 weeks eta
>> Faster - cause 3 days - i will have mellanox connectx 5 - so can
>> separate traffic to two different x16 pcie busses
> I do think you need to separate traffic to two different x16 PCIe
> slots.  I have found that the ConnectX-5 is significantly faster
> packet-per-sec performance than ConnectX-4, but that is not your
> use-case (max BW). I've not tested these NICs for maximum
> _bidirectional_ bandwidth limits, I've only made sure I can do 100G
> unidirectional, which can hit some funny motherboard memory limits
> (remember to equip motherboard with 4 RAM blocks for full memory BW).
>
Yes memory channels are separated and there are 4 modules per cpu :)

^ permalink raw reply

* [PATCH bpf] tools/bpftool: copy uapi/linux/tc_act/tc_bpf.h to tools directory
From: Yonghong Song @ 2018-11-08  1:00 UTC (permalink / raw)
  To: ast, kafai, daniel, netdev, rong.a.chen, zhijianx.li; +Cc: kernel-team

Commit f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
added certain networking support to bpftool.
The implementation relies on a relatively recent uapi header file
linux/tc_act/tc_bpf.h on the host which contains the marco
definition of TCA_ACT_BPF_ID.

Unfortunately, this is not the case for all distributions.
See the email message below where rhel-7.2 does not have
an up-to-date linux/tc_act/tc_bpf.h.
  https://www.mail-archive.com/linux-kernel@vger.kernel.org/msg1799211.html

This patch fixed the issue by copying linux/tc_act/tc_bpf.h from
kernel include/uapi directory to tools/include/uapi directory so
building the bpftool does not depend on host system for this file.

Fixes: f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
Reported-by: kernel test robot <rong.a.chen@intel.com>
Signed-off-by: Yonghong Song <yhs@fb.com>
---
 tools/include/uapi/linux/tc_act/tc_bpf.h | 37 ++++++++++++++++++++++++
 1 file changed, 37 insertions(+)
 create mode 100644 tools/include/uapi/linux/tc_act/tc_bpf.h

diff --git a/tools/include/uapi/linux/tc_act/tc_bpf.h b/tools/include/uapi/linux/tc_act/tc_bpf.h
new file mode 100644
index 000000000000..6e89a5df49a4
--- /dev/null
+++ b/tools/include/uapi/linux/tc_act/tc_bpf.h
@@ -0,0 +1,37 @@
+/* SPDX-License-Identifier: GPL-2.0+ WITH Linux-syscall-note */
+/*
+ * Copyright (c) 2015 Jiri Pirko <jiri@resnulli.us>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ */
+
+#ifndef __LINUX_TC_BPF_H
+#define __LINUX_TC_BPF_H
+
+#include <linux/pkt_cls.h>
+
+#define TCA_ACT_BPF 13
+
+struct tc_act_bpf {
+	tc_gen;
+};
+
+enum {
+	TCA_ACT_BPF_UNSPEC,
+	TCA_ACT_BPF_TM,
+	TCA_ACT_BPF_PARMS,
+	TCA_ACT_BPF_OPS_LEN,
+	TCA_ACT_BPF_OPS,
+	TCA_ACT_BPF_FD,
+	TCA_ACT_BPF_NAME,
+	TCA_ACT_BPF_PAD,
+	TCA_ACT_BPF_TAG,
+	TCA_ACT_BPF_ID,
+	__TCA_ACT_BPF_MAX,
+};
+#define TCA_ACT_BPF_MAX (__TCA_ACT_BPF_MAX - 1)
+
+#endif
-- 
2.17.1

^ permalink raw reply related

* Re: Kernel 4.19 network performance - forwarding/routing normal users traffic
From: Paweł Staszewski @ 2018-11-08  1:13 UTC (permalink / raw)
  To: Jesper Dangaard Brouer; +Cc: David Ahern, netdev, Yoel Caspersen
In-Reply-To: <795357b6-04b8-dbc2-acfe-d561f10d4a2a@itcare.pl>



W dniu 08.11.2018 o 01:59, Paweł Staszewski pisze:
>
>
> W dniu 05.11.2018 o 21:17, Jesper Dangaard Brouer pisze:
>> On Sun, 4 Nov 2018 01:24:03 +0100 Paweł Staszewski 
>> <pstaszewski@itcare.pl> wrote:
>>
>>> And today again after allpy patch for page allocator - reached again
>>> 64/64 Gbit/s
>>>
>>> with only 50-60% cpu load
>> Great.
>>
>>> today no slowpath hit for netwoking :)
>>>
>>> But again dropped pckt at 64GbitRX and 64TX ....
>>> And as it should not be pcie express limit  -i think something more is
>> Well, this does sounds like a PCIe bandwidth limit to me.
>>
>> See the PCIe BW here: https://en.wikipedia.org/wiki/PCI_Express
>>
>> You likely have PCIe v3, where 1-lane have 984.6 MBytes/s or 7.87 Gbit/s
>> Thus,  x16-lanes have 15.75 GBytes or 126 Gbit/s.  It does say "in each
>> direction", but you are also forwarding this RX->TX on both (dual) ports
>> NIC that is sharing the same PCIe slot.
> Network controller changed from 2-port 100G connectx4 to 2 separate 
> cards 100G connectx5
>
>
>    PerfTop:   92239 irqs/sec  kernel:99.4%  exact:  0.0% [4000Hz 
> cycles],  (all, 56 CPUs)
> --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- 
>
>
>      6.65%  [kernel]       [k] irq_entries_start
>      5.57%  [kernel]       [k] tasklet_action_common.isra.21
>      4.60%  [kernel]       [k] mlx5_eq_int
>      4.04%  [kernel]       [k] mlx5e_skb_from_cqe_mpwrq_linear
>      3.66%  [kernel]       [k] _raw_spin_lock_irqsave
>      3.58%  [kernel]       [k] mlx5e_sq_xmit
>      2.66%  [kernel]       [k] fib_table_lookup
>      2.52%  [kernel]       [k] _raw_spin_lock
>      2.51%  [kernel]       [k] build_skb
>      2.50%  [kernel]       [k] _raw_spin_lock_irq
>      2.04%  [kernel]       [k] try_to_wake_up
>      1.83%  [kernel]       [k] queued_spin_lock_slowpath
>      1.81%  [kernel]       [k] mlx5e_poll_tx_cq
>      1.65%  [kernel]       [k] do_idle
>      1.50%  [kernel]       [k] mlx5e_poll_rx_cq
>      1.34%  [kernel]       [k] __sched_text_start
>      1.32%  [kernel]       [k] cmd_exec
>      1.30%  [kernel]       [k] cmd_work_handler
>      1.16%  [kernel]       [k] vlan_do_receive
>      1.15%  [kernel]       [k] memcpy_erms
>      1.15%  [kernel]       [k] __dev_queue_xmit
>      1.07%  [kernel]       [k] mlx5_cmd_comp_handler
>      1.06%  [kernel]       [k] sched_ttwu_pending
>      1.00%  [kernel]       [k] ipt_do_table
>      0.98%  [kernel]       [k] ip_finish_output2
>      0.92%  [kernel]       [k] pfifo_fast_dequeue
>      0.88%  [kernel]       [k] mlx5e_handle_rx_cqe_mpwrq
>      0.78%  [kernel]       [k] dev_gro_receive
>      0.78%  [kernel]       [k] mlx5e_napi_poll
>      0.76%  [kernel]       [k] mlx5e_post_rx_mpwqes
>      0.70%  [kernel]       [k] process_one_work
>      0.67%  [kernel]       [k] __netif_receive_skb_core
>      0.65%  [kernel]       [k] __build_skb
>      0.63%  [kernel]       [k] llist_add_batch
>      0.62%  [kernel]       [k] tcp_gro_receive
>      0.60%  [kernel]       [k] inet_gro_receive
>      0.59%  [kernel]       [k] ip_route_input_rcu
>      0.59%  [kernel]       [k] rcu_irq_exit
>      0.56%  [kernel]       [k] napi_complete_done
>      0.52%  [kernel]       [k] kmem_cache_alloc
>      0.48%  [kernel]       [k] __softirqentry_text_start
>      0.48%  [kernel]       [k] mlx5e_xmit
>      0.47%  [kernel]       [k] __queue_work
>      0.46%  [kernel]       [k] memset_erms
>      0.46%  [kernel]       [k] dev_hard_start_xmit
>      0.45%  [kernel]       [k] insert_work
>      0.45%  [kernel]       [k] enqueue_task_fair
>      0.44%  [kernel]       [k] __wake_up_common
>      0.43%  [kernel]       [k] finish_task_switch
>      0.43%  [kernel]       [k] kmem_cache_free_bulk
>      0.42%  [kernel]       [k] ip_forward
>      0.42%  [kernel]       [k] worker_thread
>      0.41%  [kernel]       [k] schedule
>      0.41%  [kernel]       [k] _raw_spin_unlock_irqrestore
>      0.40%  [kernel]       [k] netif_skb_features
>      0.40%  [kernel]       [k] queue_work_on
>      0.40%  [kernel]       [k] pfifo_fast_enqueue
>      0.39%  [kernel]       [k] vlan_dev_hard_start_xmit
>      0.39%  [kernel]       [k] page_frag_free
>      0.36%  [kernel]       [k] swiotlb_map_page
>      0.36%  [kernel]       [k] update_cfs_rq_h_load
>      0.35%  [kernel]       [k] validate_xmit_skb.isra.142
>      0.35%  [kernel]       [k] dev_ifconf
>      0.35%  [kernel]       [k] check_preempt_curr
>      0.34%  [kernel]       [k] _raw_spin_trylock
>      0.34%  [kernel]       [k] rcu_idle_exit
>      0.33%  [kernel]       [k] ip_rcv_core.isra.20.constprop.25
>      0.33%  [kernel]       [k] __qdisc_run
>      0.33%  [kernel]       [k] skb_release_data
>      0.32%  [kernel]       [k] native_sched_clock
>      0.30%  [kernel]       [k] add_interrupt_randomness
>      0.29%  [kernel]       [k] interrupt_entry
>      0.28%  [kernel]       [k] skb_gro_receive
>      0.26%  [kernel]       [k] read_tsc
>      0.26%  [kernel]       [k] __get_xps_queue_idx
>      0.26%  [kernel]       [k] inet_gifconf
>      0.26%  [kernel]       [k] skb_segment
>      0.25%  [kernel]       [k] __tasklet_schedule_common
>      0.25%  [kernel]       [k] smpboot_thread_fn
>      0.23%  [kernel]       [k] __update_load_avg_se
>      0.22%  [kernel]       [k] tcp4_gro_receive
>
>
> Not much traffic now:
>   bwm-ng v0.6.1 (probing every 0.500s), press 'h' for help
>   input: /proc/net/dev type: rate
>   |         iface                   Rx Tx                Total
> ============================================================================== 
>
>          enp175s0:           6.95 Gb/s            4.20 Gb/s           
> 11.15 Gb/s
>          enp216s0:           4.23 Gb/s            6.98 Gb/s           
> 11.21 Gb/s
> ------------------------------------------------------------------------------ 
>
>             total:          11.18 Gb/s           11.18 Gb/s           
> 22.37 Gb/s
>
>   bwm-ng v0.6.1 (probing every 1.000s), press 'h' for help
>   input: /proc/net/dev type: rate
>   |         iface                   Rx Tx                Total
> ============================================================================== 
>
>          enp175s0:       700264.50 P/s        923890.25 P/s 1624154.75 
> P/s
>          enp216s0:       932598.81 P/s        708771.50 P/s 1641370.25 
> P/s
> ------------------------------------------------------------------------------ 
>
>             total:      1632863.38 P/s       1632661.75 P/s 3265525.00 
> P/s
>
>
>
>
Also is that normal that some kworker procs takes 10%+ of cpu ?
below top

  2913 root      20   0       0      0      0 I  10.3  0.0   6:58.29 
kworker/u112:1-
     7 root      20   0       0      0      0 I   8.6  0.0   6:17.18 
kworker/u112:0-
10289 root      20   0       0      0      0 I   6.6  0.0   6:33.90 
kworker/u112:4-
  2939 root      20   0       0      0      0 R   3.6  0.0   7:37.68 
kworker/u112:2-
  4557 root      20   0       0      0      0 I   1.3  0.0   0:08.82 
kworker/45:4-ev
  6775 root      20   0       0      0      0 I   1.3  0.0   0:26.30 
kworker/50:4-ev
  6833 root      20   0       0      0      0 D   1.3  0.0   0:04.96 
kworker/15:0+ev
  6840 root      20   0       0      0      0 I   1.3  0.0   0:09.32 
kworker/55:2-ev
  6874 root      20   0       0      0      0 D   1.3  0.0   0:08.51 
kworker/53:0+ev
  7710 root      20   0       0      0      0 I   1.3  0.0   0:07.78 
kworker/14:1-ev
12075 root      20   0       0      0      0 I   1.3  0.0   1:19.22 
kworker/23:3-ev
31209 root      20   0       0      0      0 I   1.3  0.0   0:07.02 
kworker/20:1-ev
32351 root      20   0       0      0      0 R   1.3  0.0   0:06.99 
kworker/51:2+ev
39869 root      20   0       0      0      0 D   1.3  0.0   0:06.15 
kworker/42:0+ev
39959 root      20   0       0      0      0 I   1.3  0.0   0:16.23 
kworker/51:1-ev
42858 root      20   0       0      0      0 I   1.3  0.0   0:47.72 
kworker/27:2-ev
43281 root      20   0       0      0      0 I   1.3  0.0   0:14.99 
kworker/14:4-ev
43282 root      20   0       0      0      0 I   1.3  0.0   0:13.38 
kworker/16:1-ev
43389 root      20   0       0      0      0 D   1.3  0.0   0:08.92 
kworker/54:2+ev
45214 root      20   0       0      0      0 I   1.3  0.0   0:05.82 
kworker/55:0-ev
46894 root      20   0       0      0      0 I   1.3  0.0   0:04.11 
kworker/46:1-ev
47027 root      20   0       0      0      0 D   1.3  0.0   0:03.79 
kworker/47:1+ev
47129 root      20   0       0      0      0 D   1.3  0.0   0:03.15 
kworker/52:0+ev
47133 root      20   0       0      0      0 I   1.3  0.0   0:03.19 
kworker/49:1-ev
47179 root      20   0       0      0      0 I   1.3  0.0   0:02.83 
kworker/17:3-ev
48062 root      20   0       0      0      0 I   1.3  0.0   0:02.54 
kworker/44:1-ev
48158 root      20   0       0      0      0 I   1.3  0.0   0:02.17 
kworker/16:2-ev
48168 root      20   0       0      0      0 I   1.3  0.0   0:02.13 
kworker/27:3-ev
48247 root      20   0       0      0      0 I   1.3  0.0   0:01.83 
kworker/22:0-ev
48337 root      20   0       0      0      0 I   1.3  0.0   0:01.57 
kworker/15:1-ev
48345 root      20   0       0      0      0 I   1.3  0.0   0:01.49 
kworker/24:3-ev
49302 root      20   0       0      0      0 I   1.3  0.0   0:00.71 
kworker/54:1-ev
49366 root      20   0       0      0      0 I   1.3  0.0   0:00.38 
kworker/20:3-ev
49400 root      20   0       0      0      0 I   1.3  0.0   0:00.31 
kworker/26:2-ev
49430 root      20   0       0      0      0 I   1.3  0.0   0:00.21 
kworker/42:2-ev
49463 root      20   0       0      0      0 D   1.3  0.0   0:00.08 
kworker/50:2+ev
51698 root      20   0       0      0      0 D   1.3  0.0   0:14.85 
kworker/46:2+ev
54238 root      20   0       0      0      0 I   1.3  0.0   0:23.73 
kworker/52:1-ev
  2507 root      20   0       0      0      0 I   1.0  0.0   0:09.60 
kworker/44:2-ev
  4525 root      20   0       0      0      0 I   1.0  0.0   0:08.07 
kworker/26:1-ev
  4556 root      20   0       0      0      0 I   1.0  0.0   0:05.15 
kworker/48:0-ev
  4604 root      20   0       0      0      0 I   1.0  0.0   0:10.90 
kworker/19:0-ev
  5789 root      20   0       0      0      0 I   1.0  0.0   0:08.24 
kworker/18:0-ev
  6868 root      20   0       0      0      0 I   1.0  0.0   0:09.68 
kworker/47:0-ev
  6900 root      20   0       0      0      0 I   1.0  0.0   0:28.83 
kworker/18:1-ev
  7764 root      20   0       0      0      0 I   1.0  0.0   0:03.00 
kworker/49:2-ev
12045 root      20   0       0      0      0 I   1.0  0.0   1:16.98 
kworker/24:2-ev
32218 root      20   0       0      0      0 I   1.0  0.0   0:04.13 
kworker/45:2-ev
34082 root      20   0       0      0      0 I   1.0  0.0   0:06.29 
kworker/17:1-ev
39791 root      20   0       0      0      0 I   1.0  0.0   0:19.51 
kworker/21:4-ev
39973 root      20   0       0      0      0 I   1.0  0.0   0:17.12 
kworker/53:2-ev
43223 root      20   0       0      0      0 I   1.0  0.0   0:07.88 
kworker/25:0-ev
43295 root      20   0       0      0      0 I   1.0  0.0   0:10.89 
kworker/22:4-ev
46055 root      20   0       0      0      0 I   1.0  0.0   0:04.00 
kworker/21:2-ev
46077 root      20   0       0      0      0 I   1.0  0.0   0:04.62 
kworker/19:1-ev
47204 root      20   0       0      0      0 I   1.0  0.0   0:03.03 
kworker/25:2-ev
47989 root      20   0       0      0      0 I   1.0  0.0   0:02.65 
kworker/43:1-ev
49127 root      20   0       0      0      0 I   1.0  0.0   0:01.10 
kworker/48:2-ev
49317 root      20   0       0      0      0 I   1.0  0.0   0:00.56 
kworker/23:1-ev
54191 root      20   0       0      0      0 R   1.0  0.0   0:30.27 
kworker/43:2+ev
    81 root      20   0       0      0      0 S   0.7  0.0   0:50.27 
ksoftirqd/14
    87 root      20   0       0      0      0 S   0.7  0.0   1:02.92 
ksoftirqd/15
   102 root      20   0       0      0      0 S   0.7  0.0   0:29.78 
ksoftirqd/18
   117 root      20   0       0      0      0 S   0.7  0.0   0:30.73 
ksoftirqd/21
   127 root      20   0       0      0      0 S   0.7  0.0   0:24.45 
ksoftirqd/23
   137 root      20   0       0      0      0 S   0.7  0.0   0:24.94 
ksoftirqd/25
   142 root      20   0       0      0      0 S   0.7  0.0   0:21.74 
ksoftirqd/26
   222 root      20   0       0      0      0 S   0.7  0.0   0:27.83 
ksoftirqd/42
   227 root      20   0       0      0      0 S   0.7  0.0   0:25.35 
ksoftirqd/43
   242 root      20   0       0      0      0 S   0.7  0.0   0:21.40 
ksoftirqd/46
   267 root      20   0       0      0      0 S   0.7  0.0   0:08.62 
ksoftirqd/51
  5174 root      20   0       0      0      0 I   0.7  0.0   5:57.10 
kworker/u112:3-

>
>
>>
>>
>>> going on there - and hard to catch - cause perf top doestn chenged
>>> besides there is no queued slowpath hit now
>>>
>>> I ordered now also intel cards to compare - but 3 weeks eta
>>> Faster - cause 3 days - i will have mellanox connectx 5 - so can
>>> separate traffic to two different x16 pcie busses
>> I do think you need to separate traffic to two different x16 PCIe
>> slots.  I have found that the ConnectX-5 is significantly faster
>> packet-per-sec performance than ConnectX-4, but that is not your
>> use-case (max BW). I've not tested these NICs for maximum
>> _bidirectional_ bandwidth limits, I've only made sure I can do 100G
>> unidirectional, which can hit some funny motherboard memory limits
>> (remember to equip motherboard with 4 RAM blocks for full memory BW).
>>
> Yes memory channels are separated and there are 4 modules per cpu :)
>
>

^ permalink raw reply

* Re: [net 00/14][pull request] Intel Wired LAN Driver Updates 2018-11-07
From: David Miller @ 2018-11-08  1:14 UTC (permalink / raw)
  To: jeffrey.t.kirsher; +Cc: netdev, nhorman, sassmann
In-Reply-To: <20181107191631.5072-1-jeffrey.t.kirsher@intel.com>

From: Jeff Kirsher <jeffrey.t.kirsher@intel.com>
Date: Wed,  7 Nov 2018 11:16:17 -0800

> This series contains fixes to igb, i40e and ice drivers.

Pulled, thanks Jeff.

^ permalink raw reply

* Re: [PATCH bpf] tools/bpftool: copy uapi/linux/tc_act/tc_bpf.h to tools directory
From: Li Zhijian @ 2018-11-08  1:15 UTC (permalink / raw)
  To: Yonghong Song, ast, kafai, daniel, netdev, rong.a.chen; +Cc: kernel-team
In-Reply-To: <20181108010011.3982963-1-yhs@fb.com>

On 11/8/2018 9:00 AM, Yonghong Song wrote:
> Commit f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
> added certain networking support to bpftool.
> The implementation relies on a relatively recent uapi header file
> linux/tc_act/tc_bpf.h on the host which contains the marco
> definition of TCA_ACT_BPF_ID.
>
> Unfortunately, this is not the case for all distributions.
> See the email message below where rhel-7.2 does not have
> an up-to-date linux/tc_act/tc_bpf.h.
>    https://www.mail-archive.com/linux-kernel@vger.kernel.org/msg1799211.html

i have not tested this patch, but basing on the early commit
6f3bac08ff9 ("tools/bpf: bpftool: add net support")
i cooked up similar patch locally, but i noticed that it also requires an
up-to-date linux/pkt_cls.h as well to avoid compiling errors:

root@lkp-bdw-ep3 ~/linux-f6f3bac08f/tools/bpf/bpftool# make V=1
[...snip...]
gcc -O2 -W -Wall -Wextra -Wno-unused-parameter -Wshadow -Wno-missing-field-initializers -DPACKAGE='"bpftool"' -D__EXPORTED_HEADERS__ -I/root/linux-f6f3bac08f/kernel/bpf/ -I/root/linux-f6f3bac08f/tools/include -I/root/linux-f6f3bac08f/tools/include/uapi -I/root/linux-f6f3bac08f/tools/lib/bpf -I/root/linux-f6f3bac08f/tools/perf -DBPFTOOL_VERSION='"4.19.0-rc2"' -DCOMPAT_NEED_REALLOCARRAY   -c -MMD -o netlink_dumper.o netlink_dumper.c
make -C /root/linux-f6f3bac08f/tools/lib/bpf/ OUTPUT= libbpf.a
make[1]: Entering directory '/root/linux-f6f3bac08f/tools/lib/bpf'
netlink_dumper.c: In function 'do_bpf_filter_dump':
netlink_dumper.c:153:9: error: 'TCA_BPF_ID' undeclared (first use in this function)
   if (tb[TCA_BPF_ID])
          ^~~~~~~~~~
netlink_dumper.c:153:9: note: each undeclared identifier is reported only once for each function it appears in
netlink_dumper.c:155:9: error: 'TCA_BPF_TAG' undeclared (first use in this function)
   if (tb[TCA_BPF_TAG])
          ^~~~~~~~~~~
Makefile:96: recipe for target 'netlink_dumper.o' failed
make: *** [netlink_dumper.o] Error 1
make: *** Waiting for unfinished jobs....
make -f /root/linux-f6f3bac08f/tools/build/Makefile.build dir=. obj=libbpf
make[1]: Leaving directory '/root/linux-f6f3bac08f/tools/lib/bpf'

Thanks
Zhijian

>
> This patch fixed the issue by copying linux/tc_act/tc_bpf.h from
> kernel include/uapi directory to tools/include/uapi directory so
> building the bpftool does not depend on host system for this file.
>
> Fixes: f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
> Reported-by: kernel test robot <rong.a.chen@intel.com>
> Signed-off-by: Yonghong Song <yhs@fb.com>
> ---
>   tools/include/uapi/linux/tc_act/tc_bpf.h | 37 ++++++++++++++++++++++++
>   1 file changed, 37 insertions(+)
>   create mode 100644 tools/include/uapi/linux/tc_act/tc_bpf.h
>
> diff --git a/tools/include/uapi/linux/tc_act/tc_bpf.h b/tools/include/uapi/linux/tc_act/tc_bpf.h
> new file mode 100644
> index 000000000000..6e89a5df49a4
> --- /dev/null
> +++ b/tools/include/uapi/linux/tc_act/tc_bpf.h
> @@ -0,0 +1,37 @@
> +/* SPDX-License-Identifier: GPL-2.0+ WITH Linux-syscall-note */
> +/*
> + * Copyright (c) 2015 Jiri Pirko <jiri@resnulli.us>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + */
> +
> +#ifndef __LINUX_TC_BPF_H
> +#define __LINUX_TC_BPF_H
> +
> +#include <linux/pkt_cls.h>
> +
> +#define TCA_ACT_BPF 13
> +
> +struct tc_act_bpf {
> +	tc_gen;
> +};
> +
> +enum {
> +	TCA_ACT_BPF_UNSPEC,
> +	TCA_ACT_BPF_TM,
> +	TCA_ACT_BPF_PARMS,
> +	TCA_ACT_BPF_OPS_LEN,
> +	TCA_ACT_BPF_OPS,
> +	TCA_ACT_BPF_FD,
> +	TCA_ACT_BPF_NAME,
> +	TCA_ACT_BPF_PAD,
> +	TCA_ACT_BPF_TAG,
> +	TCA_ACT_BPF_ID,
> +	__TCA_ACT_BPF_MAX,
> +};
> +#define TCA_ACT_BPF_MAX (__TCA_ACT_BPF_MAX - 1)
> +
> +#endif

^ permalink raw reply

* Re: [PATCH] [stable, netdev 4.4+] lan78xx: make sure RX_ADDRL & RX_ADDRH regs are always up to date
From: Paolo Pisati @ 2018-11-08 11:01 UTC (permalink / raw)
  To: Sasha Levin
  Cc: Paolo Pisati, Woojung Huh, Microchip Linux Driver Support, netdev,
	stable, linux-usb, linux-kernel
In-Reply-To: <20181108001751.GA8097@sasha-vm>

On Wed, Nov 07, 2018 at 07:17:51PM -0500, Sasha Levin wrote:
> So why not just take 760db29bdc completely? It looks safer than taking a
> partial backport, and will make applying future patches easier.
> 
> I tried to do it and it doesn't look like there are any dependencies
> that would cause an issue.

Somehow i was convinced it didn't build on 4.4.x... can you pick it up?

commit 760db29bdc97b73ff60b091315ad787b1deb5cf5
Author: Phil Elwell <phil@raspberrypi.org>
Date:   Thu Apr 19 17:59:38 2018 +0100

    lan78xx: Read MAC address from DT if present
    
    There is a standard mechanism for locating and using a MAC address from
    the Device Tree. Use this facility in the lan78xx driver to support
    applications without programmed EEPROM or OTP. At the same time,
    regularise the handling of the different address sources.
    
    Signed-off-by: Phil Elwell <phil@raspberrypi.org>
    Signed-off-by: David S. Miller <davem@davemloft.net>
-- 
bye,
p.

^ permalink raw reply

* [Kernel][NET] Bug report on packet defragmenting
From: 배석진 @ 2018-11-08  1:29 UTC (permalink / raw)
  To: netdev@vger.kernel.org
In-Reply-To: <CGME20181108012927epcms1p47f719c1908da64a378690362901644ee@epcms1p4>

Hello,
This is bae working on Samsung Elec. 

We got the problem that fragmented SIP packet couldn't be deliverd to user layer.
And found that they were stoled at HOOK function, ipv6_defrag.

In condition with SMP and RPS.
After first fragmented packet, they have no further network header except ip.
But __skb_flow_dissect function using the port field to determine hash key, 'ports'.
So each packet get different hash key, and be sent to different core.
Although hash is different, selected cpu could be same. but it just lucky. [exam 2]

And addition, when those packets arrived with little time gap.
They became ran the ipv6_defrag hook simultaneously in each core.
So they each be treated to first fragmented packet.
And they can't merged to original packet, and can't be deliverd to upper. [exam 1]

If ipv6_defrag hook is not excuted simultaneously, then it's ok.
ipv6_defrag hook can handle that. [exam 3]

We'll skip 'ports' setting when the packet was fragmented.
Because of IPv6 SIP invite packet is usally fragmented, this problem is very often.



>From be74b56861cf76a16d0f2d054d468c584ed67cce Mon Sep 17 00:00:00 2001
From: soukjin bae <soukjin.bae@samsung.com>
Date: Thu, 8 Nov 2018 09:52:29 +0900
Subject: [PATCH] flow_dissector: don't refer port field in fragmented packet

After first fragmented packet, they have no further network header except ip.
So when try to refer port field in nexthdr, they got the garbage from payload.
Skip port set when the packet was fragmented.

Signed-off-by: soukjin bae <soukjin.bae@samsung.com>
---
 net/core/flow_dissector.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/net/core/flow_dissector.c b/net/core/flow_dissector.c
index 676f3ad629f9..928df25129ba 100644
--- a/net/core/flow_dissector.c
+++ b/net/core/flow_dissector.c
@@ -1166,8 +1166,8 @@ bool __skb_flow_dissect(const struct sk_buff *skb,
 		break;
 	}
 
-	if (dissector_uses_key(flow_dissector,
-			       FLOW_DISSECTOR_KEY_PORTS)) {
+	if (dissector_uses_key(flow_dissector, FLOW_DISSECTOR_KEY_PORTS)
+	    && !(key_control->flags & FLOW_DIS_IS_FRAGMENT)) {
 		key_ports = skb_flow_dissector_target(flow_dissector,
 						      FLOW_DISSECTOR_KEY_PORTS,
 						      target_container);
-- 
2.13.0



[exam 1]
# tcp dump #
<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:11.938345 2001:4430:5:401::53             2001:4430:140:a635::3cd:9f3             IPv6    396	    IPv6 fragment
0010   6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 05 88 50 2a 54 16  -> ipv6 hdr with fragment hdr
0040   5d 6a a0 da 01 14 26 5a 85 ba 51 9f 17 75 04 9c  -> fragmented payload area. ipv6_defrag using this area as port

<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:11.937654 2001:4430:5:401::53 7538        2001:4430:140:a635::3cd:9f3 6300        SIP/SDP 1480    Request: INVITE
0010   6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 00 01 50 2a 54 16  -> ipv6 hdr with fragment hdr
0040   00 00 c4 c3 00 00 00 06 da 4d d7 26 a1 d7 64 c6  -> UDP hdr, right value for port. but only just this packet can be refer.

# kernel log #
11-07 13:40:12.296 I[3:      swapper/3:    0] LNK-RX(1464): 6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01 ...  --> our NIC log when pkt rcv
11-07 13:40:12.297 I[3:      swapper/3:    0] __skb_flow_dissect: ports: c3c40000                                --> right value for port
11-07 13:40:12.297 I[3:      swapper/3:    0] get_rps_cpu: cpu = 2 (hash:2758499534)
11-07 13:40:12.297 I[3:      swapper/3:    0] LNK-RX(380): 6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01 ...
11-07 13:40:12.297 I[3:      swapper/3:    0] __skb_flow_dissect: ports: daa06a5d                                --> but at here...
11-07 13:40:12.298 I[3:      swapper/3:    0] get_rps_cpu: cpu = 1 (hash:791526712)                              --> so this pkt has different hash, cpu
11-07 13:40:12.298 I[2:      swapper/2:    0] ipv6_defrag+++
11-07 13:40:12.298 I[1:      swapper/1:    0] ipv6_defrag+++                                                     --> go into ipv6_defrag at same time
11-07 13:40:12.298 I[1:      swapper/1:    0] ipv6_defrag: EINPROGRESS
11-07 13:40:12.298 I[2:      swapper/2:    0] ipv6_defrag: EINPROGRESS                                           --> both packet was treated to first frag



[exam 2]
# tcp dump #
<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:13.947576 2001:4430:5:401::53             2001:4430:140:a635::3cd:9f3             IPv6    1480    IPv6 fragment
0010   6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 00 01 50 2a 54 1c
0040   00 00 c4 c3 00 00 00 07 2e bb 86 7f 97 4f 58 7c

<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:13.948379 2001:4430:5:401::53 7538        2001:4430:140:a635::3cd:9f3 6300        SIP/SDP 396     Request: INVITE
0010   6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 05 88 50 2a 54 1c
0040   24 fd 06 d4 b9 23 5b c4 49 9e 1f 3e be f5 12 67

# kernel log #
11-07 13:40:14.306 I[3:      swapper/3:    0] LNK-RX(1464): 6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01 ...
11-07 13:40:14.306 I[3:      swapper/3:    0] __skb_flow_dissect: ports: c3c40000
11-07 13:40:14.307 I[3:      swapper/3:    0] get_rps_cpu: cpu = 2 (hash:2758499534)
11-07 13:40:14.307 I[3:      swapper/3:    0] LNK-RX(380): 6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01 ...
11-07 13:40:14.307 I[3:      swapper/3:    0] __skb_flow_dissect: ports: d406fd24
11-07 13:40:14.308 I[3:      swapper/3:    0] get_rps_cpu: cpu = 2 (hash:2624600197)                             --> different hash, but same cpu by unhash.
11-07 13:40:14.308 I[2:      swapper/2:    0] ipv6_defrag+++
11-07 13:40:14.308 I[2:      swapper/2:    0] ipv6_defrag: EINPROGRESS
11-07 13:40:14.308 I[2:      swapper/2:    0] ipv6_defrag+++
11-07 13:40:14.309 I[2:      swapper/2:    0] UDP: __udp_enqueue_schedule_skb: qlen=1                            --> deliverd to upper


[exam 3]
# tcp dump #
<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:05.514191 2001:4430:5:401::53             2001:4430:140:a635::3cd:9f3             IPv6    1480    IPv6 fragment
0010   6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 00 01 50 2a 54 03
0040   00 00 c4 c3 00 00 00 03 27 e0 dd cc fe 77 a0 64

<TIME>          <Source>            <S.Port>    <Destination>               <D.Port>    <Proto> <Len>   <Info>
13:40:05.517187 2001:4430:5:401::53 7538        2001:4430:140:a635::3cd:9f3 6300        SIP/SDP 396     Request: INVITE
0010   6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01
0020   00 00 00 00 00 00 00 53 20 01 44 30 01 40 a6 35
0030   00 00 00 00 03 cd 09 f3 32 00 05 88 50 2a 54 03
0040   b8 d2 31 bd b3 d7 89 d2 d3 07 99 36 28 3c 37 a4

# kernel log #
11-07 13:40:05.872 I[3:      swapper/3:    0] LNK-RX(1464): 6b 80 00 00 05 90 2c 3d 20 01 44 30 00 05 04 01 ...
11-07 13:40:05.874 I[3:      swapper/3:    0] __skb_flow_dissect: ports: c3c40000
11-07 13:40:05.875 I[3:      swapper/3:    0] get_rps_cpu: cpu = 2 (hash:2758499534)
11-07 13:40:05.876 I[3:      swapper/3:    0] LNK-RX(380): 6b 80 00 00 01 54 2c 3d 20 01 44 30 00 05 04 01 ...
11-07 13:40:05.878 I[3:      swapper/3:    0] __skb_flow_dissect: ports: bd31d2b8
11-07 13:40:05.878 I[3:      swapper/3:    0] get_rps_cpu: cpu = 3 (hash:3167003083)                             --> different cpu
11-07 13:40:05.879 I[2:      swapper/2:    0] ipv6_defrag+++
11-07 13:40:05.879 I[2:      swapper/2:    0] ipv6_defrag: EINPROGRESS
11-07 13:40:05.881 I[3:    ksoftirqd/3:   33] ipv6_defrag+++                                                     --> but successfully handled by ipv6_defrag
11-07 13:40:05.883 I[3:    ksoftirqd/3:   33] UDP: __udp_enqueue_schedule_skb: qlen=1                            --> deliverd to upper

^ permalink raw reply related

* [PATCH net-next 0/7] net: sched: prepare for more Qdisc offloads
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski

Hi!

This series refactors the "switchdev" Qdisc offloads a little.  We have
a few Qdiscs which can be fully offloaded today to the forwarding plane
of switching devices.

First patch adds a helper for handing statistic dumps, the code seems
to be copy pasted between PRIO and RED.  Second patch removes unnecessary
parameter from RED offload function.  Third patch makes the MQ offload
use the dump helper which helps it behave much like PRIO and RED when
it comes to the TCQ_F_OFFLOADED flag.  Patch 4 adds a graft helper,
similar to the dump helper.

Patch 5 is unrelated to offloads, qdisc_graft() code seemed ripe for a
small refactor - no functional changes there.

Last two patches move the qdisc_put() call outside of the sch_tree_lock
section for RED and PRIO.  The child Qdiscs will get removed from the
hierarchy under the lock, but having the put (and potentially destroy)
called outside of the lock helps offload which may choose to sleep,
and it should generally lower the Qdisc change impact.

Jakub Kicinski (7):
  net: sched: add an offload dump helper
  net: sched: red: remove unnecessary red_dump_offload_stats parameter
  net: sched: set TCQ_F_OFFLOADED flag for MQ
  net: sched: add an offload graft helper
  net: sched: refactor grafting Qdiscs with a parent
  net: sched: red: delay destroying child qdisc on replace
  net: sched: prio: delay destroying child qdiscs on change

 include/net/sch_generic.h | 24 ++++++++++++
 net/sched/sch_api.c       | 78 ++++++++++++++++++++++++++++++++-------
 net/sched/sch_mq.c        |  9 ++---
 net/sched/sch_prio.c      | 47 ++++-------------------
 net/sched/sch_red.c       | 29 +++++----------
 5 files changed, 107 insertions(+), 80 deletions(-)

-- 
2.17.1

^ permalink raw reply

* [PATCH net-next 1/7] net: sched: add an offload dump helper
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

Qdisc dump operation of offload-capable qdiscs performs a few
extra steps which are identical among all the qdiscs.  Add
a helper to share this code.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 include/net/sch_generic.h | 12 ++++++++++++
 net/sched/sch_api.c       | 21 +++++++++++++++++++++
 net/sched/sch_prio.c      | 16 +---------------
 net/sched/sch_red.c       | 17 +----------------
 4 files changed, 35 insertions(+), 31 deletions(-)

diff --git a/include/net/sch_generic.h b/include/net/sch_generic.h
index 4d736427a4cb..af55c1c4edb1 100644
--- a/include/net/sch_generic.h
+++ b/include/net/sch_generic.h
@@ -579,6 +579,18 @@ void qdisc_put(struct Qdisc *qdisc);
 void qdisc_put_unlocked(struct Qdisc *qdisc);
 void qdisc_tree_reduce_backlog(struct Qdisc *qdisc, unsigned int n,
 			       unsigned int len);
+#ifdef CONFIG_NET_SCHED
+int qdisc_offload_dump_helper(struct Qdisc *q, enum tc_setup_type type,
+			      void *type_data);
+#else
+static inline int
+qdisc_offload_dump_helper(struct Qdisc *q, enum tc_setup_type type,
+			  void *type_data)
+{
+	q->flags &= ~TCQ_F_OFFLOADED;
+	return 0;
+}
+#endif
 struct Qdisc *qdisc_alloc(struct netdev_queue *dev_queue,
 			  const struct Qdisc_ops *ops,
 			  struct netlink_ext_ack *extack);
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c
index ca3b0f46de53..e534825d3d3a 100644
--- a/net/sched/sch_api.c
+++ b/net/sched/sch_api.c
@@ -810,6 +810,27 @@ void qdisc_tree_reduce_backlog(struct Qdisc *sch, unsigned int n,
 }
 EXPORT_SYMBOL(qdisc_tree_reduce_backlog);
 
+int qdisc_offload_dump_helper(struct Qdisc *sch, enum tc_setup_type type,
+			      void *type_data)
+{
+	struct net_device *dev = qdisc_dev(sch);
+	int err;
+
+	sch->flags &= ~TCQ_F_OFFLOADED;
+	if (!tc_can_offload(dev) || !dev->netdev_ops->ndo_setup_tc)
+		return 0;
+
+	err = dev->netdev_ops->ndo_setup_tc(dev, type, type_data);
+	if (err == -EOPNOTSUPP)
+		return 0;
+
+	if (!err)
+		sch->flags |= TCQ_F_OFFLOADED;
+
+	return err;
+}
+EXPORT_SYMBOL(qdisc_offload_dump_helper);
+
 static int tc_fill_qdisc(struct sk_buff *skb, struct Qdisc *q, u32 clid,
 			 u32 portid, u32 seq, u16 flags, int event)
 {
diff --git a/net/sched/sch_prio.c b/net/sched/sch_prio.c
index f8af98621179..4bdd04c30ead 100644
--- a/net/sched/sch_prio.c
+++ b/net/sched/sch_prio.c
@@ -251,7 +251,6 @@ static int prio_init(struct Qdisc *sch, struct nlattr *opt,
 
 static int prio_dump_offload(struct Qdisc *sch)
 {
-	struct net_device *dev = qdisc_dev(sch);
 	struct tc_prio_qopt_offload hw_stats = {
 		.command = TC_PRIO_STATS,
 		.handle = sch->handle,
@@ -263,21 +262,8 @@ static int prio_dump_offload(struct Qdisc *sch)
 			},
 		},
 	};
-	int err;
-
-	sch->flags &= ~TCQ_F_OFFLOADED;
-	if (!tc_can_offload(dev) || !dev->netdev_ops->ndo_setup_tc)
-		return 0;
-
-	err = dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_PRIO,
-					    &hw_stats);
-	if (err == -EOPNOTSUPP)
-		return 0;
-
-	if (!err)
-		sch->flags |= TCQ_F_OFFLOADED;
 
-	return err;
+	return qdisc_offload_dump_helper(sch, TC_SETUP_QDISC_PRIO, &hw_stats);
 }
 
 static int prio_dump(struct Qdisc *sch, struct sk_buff *skb)
diff --git a/net/sched/sch_red.c b/net/sched/sch_red.c
index 3ce6c0a2c493..d5e441194397 100644
--- a/net/sched/sch_red.c
+++ b/net/sched/sch_red.c
@@ -281,7 +281,6 @@ static int red_init(struct Qdisc *sch, struct nlattr *opt,
 
 static int red_dump_offload_stats(struct Qdisc *sch, struct tc_red_qopt *opt)
 {
-	struct net_device *dev = qdisc_dev(sch);
 	struct tc_red_qopt_offload hw_stats = {
 		.command = TC_RED_STATS,
 		.handle = sch->handle,
@@ -291,22 +290,8 @@ static int red_dump_offload_stats(struct Qdisc *sch, struct tc_red_qopt *opt)
 			.stats.qstats = &sch->qstats,
 		},
 	};
-	int err;
-
-	sch->flags &= ~TCQ_F_OFFLOADED;
-
-	if (!tc_can_offload(dev) || !dev->netdev_ops->ndo_setup_tc)
-		return 0;
-
-	err = dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_RED,
-					    &hw_stats);
-	if (err == -EOPNOTSUPP)
-		return 0;
-
-	if (!err)
-		sch->flags |= TCQ_F_OFFLOADED;
 
-	return err;
+	return qdisc_offload_dump_helper(sch, TC_SETUP_QDISC_RED, &hw_stats);
 }
 
 static int red_dump(struct Qdisc *sch, struct sk_buff *skb)
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 2/7] net: sched: red: remove unnecessary red_dump_offload_stats parameter
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

Offload dump helper does not use opt parameter, remove it.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 net/sched/sch_red.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/net/sched/sch_red.c b/net/sched/sch_red.c
index d5e441194397..2bf1d2fabc48 100644
--- a/net/sched/sch_red.c
+++ b/net/sched/sch_red.c
@@ -279,7 +279,7 @@ static int red_init(struct Qdisc *sch, struct nlattr *opt,
 	return red_change(sch, opt, extack);
 }
 
-static int red_dump_offload_stats(struct Qdisc *sch, struct tc_red_qopt *opt)
+static int red_dump_offload_stats(struct Qdisc *sch)
 {
 	struct tc_red_qopt_offload hw_stats = {
 		.command = TC_RED_STATS,
@@ -309,7 +309,7 @@ static int red_dump(struct Qdisc *sch, struct sk_buff *skb)
 	};
 	int err;
 
-	err = red_dump_offload_stats(sch, &opt);
+	err = red_dump_offload_stats(sch);
 	if (err)
 		goto nla_put_failure;
 
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 3/7] net: sched: set TCQ_F_OFFLOADED flag for MQ
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

PRIO and RED mark the qdisc with TCQ_F_OFFLOADED upon successful offload,
make MQ do the same.  The consistency will help with consistent
graft callback behaviour.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 net/sched/sch_mq.c | 9 +++------
 1 file changed, 3 insertions(+), 6 deletions(-)

diff --git a/net/sched/sch_mq.c b/net/sched/sch_mq.c
index f20f3a0f8424..1db5c1bf6ddd 100644
--- a/net/sched/sch_mq.c
+++ b/net/sched/sch_mq.c
@@ -38,9 +38,8 @@ static int mq_offload(struct Qdisc *sch, enum tc_mq_command cmd)
 	return dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_MQ, &opt);
 }
 
-static void mq_offload_stats(struct Qdisc *sch)
+static int mq_offload_stats(struct Qdisc *sch)
 {
-	struct net_device *dev = qdisc_dev(sch);
 	struct tc_mq_qopt_offload opt = {
 		.command = TC_MQ_STATS,
 		.handle = sch->handle,
@@ -50,8 +49,7 @@ static void mq_offload_stats(struct Qdisc *sch)
 		},
 	};
 
-	if (tc_can_offload(dev) && dev->netdev_ops->ndo_setup_tc)
-		dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_MQ, &opt);
+	return qdisc_offload_dump_helper(sch, TC_SETUP_QDISC_MQ, &opt);
 }
 
 static void mq_destroy(struct Qdisc *sch)
@@ -171,9 +169,8 @@ static int mq_dump(struct Qdisc *sch, struct sk_buff *skb)
 
 		spin_unlock_bh(qdisc_lock(qdisc));
 	}
-	mq_offload_stats(sch);
 
-	return 0;
+	return mq_offload_stats(sch);
 }
 
 static struct netdev_queue *mq_queue_get(struct Qdisc *sch, unsigned long cl)
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 4/7] net: sched: add an offload graft helper
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

Qdisc graft operation of offload-capable qdiscs performs a few
extra steps which are identical among all the qdiscs.  Add
a helper to share this code.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 include/net/sch_generic.h | 12 ++++++++++++
 net/sched/sch_api.c       | 29 +++++++++++++++++++++++++++++
 net/sched/sch_prio.c      | 27 +++------------------------
 3 files changed, 44 insertions(+), 24 deletions(-)

diff --git a/include/net/sch_generic.h b/include/net/sch_generic.h
index af55c1c4edb1..a8dd1fc141b6 100644
--- a/include/net/sch_generic.h
+++ b/include/net/sch_generic.h
@@ -582,6 +582,10 @@ void qdisc_tree_reduce_backlog(struct Qdisc *qdisc, unsigned int n,
 #ifdef CONFIG_NET_SCHED
 int qdisc_offload_dump_helper(struct Qdisc *q, enum tc_setup_type type,
 			      void *type_data);
+void qdisc_offload_graft_helper(struct net_device *dev, struct Qdisc *sch,
+				struct Qdisc *new, struct Qdisc *old,
+				enum tc_setup_type type, void *type_data,
+				struct netlink_ext_ack *extack);
 #else
 static inline int
 qdisc_offload_dump_helper(struct Qdisc *q, enum tc_setup_type type,
@@ -590,6 +594,14 @@ qdisc_offload_dump_helper(struct Qdisc *q, enum tc_setup_type type,
 	q->flags &= ~TCQ_F_OFFLOADED;
 	return 0;
 }
+
+static inline void
+qdisc_offload_graft_helper(struct net_device *dev, struct Qdisc *sch,
+			   struct Qdisc *new, struct Qdisc *old,
+			   enum tc_setup_type type, void *type_data,
+			   struct netlink_ext_ack *extack)
+{
+}
 #endif
 struct Qdisc *qdisc_alloc(struct netdev_queue *dev_queue,
 			  const struct Qdisc_ops *ops,
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c
index e534825d3d3a..4b3af41cc1d7 100644
--- a/net/sched/sch_api.c
+++ b/net/sched/sch_api.c
@@ -831,6 +831,35 @@ int qdisc_offload_dump_helper(struct Qdisc *sch, enum tc_setup_type type,
 }
 EXPORT_SYMBOL(qdisc_offload_dump_helper);
 
+void qdisc_offload_graft_helper(struct net_device *dev, struct Qdisc *sch,
+				struct Qdisc *new, struct Qdisc *old,
+				enum tc_setup_type type, void *type_data,
+				struct netlink_ext_ack *extack)
+{
+	bool any_qdisc_is_offloaded;
+	int err;
+
+	if (!tc_can_offload(dev) || !dev->netdev_ops->ndo_setup_tc)
+		return;
+
+	err = dev->netdev_ops->ndo_setup_tc(dev, type, type_data);
+
+	/* Don't report error if the graft is part of destroy operation. */
+	if (!err || !new || new == &noop_qdisc)
+		return;
+
+	/* Don't report error if the parent, the old child and the new
+	 * one are not offloaded.
+	 */
+	any_qdisc_is_offloaded = new->flags & TCQ_F_OFFLOADED;
+	any_qdisc_is_offloaded |= sch && sch->flags & TCQ_F_OFFLOADED;
+	any_qdisc_is_offloaded |= old && old->flags & TCQ_F_OFFLOADED;
+
+	if (any_qdisc_is_offloaded)
+		NL_SET_ERR_MSG(extack, "Offloading graft operation failed.");
+}
+EXPORT_SYMBOL(qdisc_offload_graft_helper);
+
 static int tc_fill_qdisc(struct sk_buff *skb, struct Qdisc *q, u32 clid,
 			 u32 portid, u32 seq, u16 flags, int event)
 {
diff --git a/net/sched/sch_prio.c b/net/sched/sch_prio.c
index 4bdd04c30ead..63a90c5055ee 100644
--- a/net/sched/sch_prio.c
+++ b/net/sched/sch_prio.c
@@ -295,43 +295,22 @@ static int prio_graft(struct Qdisc *sch, unsigned long arg, struct Qdisc *new,
 {
 	struct prio_sched_data *q = qdisc_priv(sch);
 	struct tc_prio_qopt_offload graft_offload;
-	struct net_device *dev = qdisc_dev(sch);
 	unsigned long band = arg - 1;
-	bool any_qdisc_is_offloaded;
-	int err;
 
 	if (new == NULL)
 		new = &noop_qdisc;
 
 	*old = qdisc_replace(sch, new, &q->queues[band]);
 
-	if (!tc_can_offload(dev))
-		return 0;
-
 	graft_offload.handle = sch->handle;
 	graft_offload.parent = sch->parent;
 	graft_offload.graft_params.band = band;
 	graft_offload.graft_params.child_handle = new->handle;
 	graft_offload.command = TC_PRIO_GRAFT;
 
-	err = dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_PRIO,
-					    &graft_offload);
-
-	/* Don't report error if the graft is part of destroy operation. */
-	if (err && new != &noop_qdisc) {
-		/* Don't report error if the parent, the old child and the new
-		 * one are not offloaded.
-		 */
-		any_qdisc_is_offloaded = sch->flags & TCQ_F_OFFLOADED;
-		any_qdisc_is_offloaded |= new->flags & TCQ_F_OFFLOADED;
-		if (*old)
-			any_qdisc_is_offloaded |= (*old)->flags &
-						   TCQ_F_OFFLOADED;
-
-		if (any_qdisc_is_offloaded)
-			NL_SET_ERR_MSG(extack, "Offloading graft operation failed.");
-	}
-
+	qdisc_offload_graft_helper(qdisc_dev(sch), sch, new, *old,
+				   TC_SETUP_QDISC_PRIO, &graft_offload,
+				   extack);
 	return 0;
 }
 
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 5/7] net: sched: refactor grafting Qdiscs with a parent
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

The code for grafting Qdiscs when there is a parent has two needless
indentation levels, and breaks the "keep the success path unindented"
guideline.  Refactor.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 net/sched/sch_api.c | 28 ++++++++++++++--------------
 1 file changed, 14 insertions(+), 14 deletions(-)

diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c
index 4b3af41cc1d7..f55bc50cd0a9 100644
--- a/net/sched/sch_api.c
+++ b/net/sched/sch_api.c
@@ -1007,7 +1007,6 @@ static int qdisc_graft(struct net_device *dev, struct Qdisc *parent,
 {
 	struct Qdisc *q = old;
 	struct net *net = dev_net(dev);
-	int err = 0;
 
 	if (parent == NULL) {
 		unsigned int i, num_q, ingress;
@@ -1062,28 +1061,29 @@ static int qdisc_graft(struct net_device *dev, struct Qdisc *parent,
 			dev_activate(dev);
 	} else {
 		const struct Qdisc_class_ops *cops = parent->ops->cl_ops;
+		unsigned long cl;
+		int err;
 
 		/* Only support running class lockless if parent is lockless */
 		if (new && (new->flags & TCQ_F_NOLOCK) &&
 		    parent && !(parent->flags & TCQ_F_NOLOCK))
 			new->flags &= ~TCQ_F_NOLOCK;
 
-		err = -EOPNOTSUPP;
-		if (cops && cops->graft) {
-			unsigned long cl = cops->find(parent, classid);
+		if (!cops || !cops->graft)
+			return -EOPNOTSUPP;
 
-			if (cl) {
-				err = cops->graft(parent, cl, new, &old,
-						  extack);
-			} else {
-				NL_SET_ERR_MSG(extack, "Specified class not found");
-				err = -ENOENT;
-			}
+		cl = cops->find(parent, classid);
+		if (!cl) {
+			NL_SET_ERR_MSG(extack, "Specified class not found");
+			return -ENOENT;
 		}
-		if (!err)
-			notify_and_destroy(net, skb, n, classid, old, new);
+
+		err = cops->graft(parent, cl, new, &old, extack);
+		if (err)
+			return err;
+		notify_and_destroy(net, skb, n, classid, old, new);
 	}
-	return err;
+	return 0;
 }
 
 static int qdisc_block_indexes_set(struct Qdisc *sch, struct nlattr **tca,
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 6/7] net: sched: red: delay destroying child qdisc on replace
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

Move destroying of the old child qdisc outside of the sch_tree_lock()
section.  This should improve the software qdisc replace but is even
more important for offloads.  Firstly calling offloads under a spin
lock is best avoided.  Secondly the destroy event of existing child
would have been sent to the offload device before the replace, causing
confusion.

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 net/sched/sch_red.c | 8 ++++++--
 1 file changed, 6 insertions(+), 2 deletions(-)

diff --git a/net/sched/sch_red.c b/net/sched/sch_red.c
index 2bf1d2fabc48..7682f7a618a1 100644
--- a/net/sched/sch_red.c
+++ b/net/sched/sch_red.c
@@ -193,10 +193,10 @@ static const struct nla_policy red_policy[TCA_RED_MAX + 1] = {
 static int red_change(struct Qdisc *sch, struct nlattr *opt,
 		      struct netlink_ext_ack *extack)
 {
+	struct Qdisc *old_child = NULL, *child = NULL;
 	struct red_sched_data *q = qdisc_priv(sch);
 	struct nlattr *tb[TCA_RED_MAX + 1];
 	struct tc_red_qopt *ctl;
-	struct Qdisc *child = NULL;
 	int err;
 	u32 max_P;
 
@@ -233,7 +233,7 @@ static int red_change(struct Qdisc *sch, struct nlattr *opt,
 	if (child) {
 		qdisc_tree_reduce_backlog(q->qdisc, q->qdisc->q.qlen,
 					  q->qdisc->qstats.backlog);
-		qdisc_put(q->qdisc);
+		old_child = q->qdisc;
 		q->qdisc = child;
 	}
 
@@ -252,7 +252,11 @@ static int red_change(struct Qdisc *sch, struct nlattr *opt,
 		red_start_of_idle_period(&q->vars);
 
 	sch_tree_unlock(sch);
+
 	red_offload(sch, true);
+
+	if (old_child)
+		qdisc_put(old_child);
 	return 0;
 }
 
-- 
2.17.1

^ permalink raw reply related

* [PATCH net-next 7/7] net: sched: prio: delay destroying child qdiscs on change
From: Jakub Kicinski @ 2018-11-08  1:33 UTC (permalink / raw)
  To: davem
  Cc: netdev, oss-drivers, jiri, xiyou.wangcong, jhs, nogah.frankel,
	yuvalm, Jakub Kicinski
In-Reply-To: <20181108013340.20983-1-jakub.kicinski@netronome.com>

Move destroying of the old child qdiscs outside of the sch_tree_lock()
section.  This should improve the software qdisc replace but is even
more important for offloads.  Calling offloads under a spin lock is
best avoided, and child's destroy would be called under sch_tree_lock().

Signed-off-by: Jakub Kicinski <jakub.kicinski@netronome.com>
Reviewed-by: John Hurley <john.hurley@netronome.com>
---
 net/sched/sch_prio.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/net/sched/sch_prio.c b/net/sched/sch_prio.c
index 63a90c5055ee..cdf68706e40f 100644
--- a/net/sched/sch_prio.c
+++ b/net/sched/sch_prio.c
@@ -220,7 +220,6 @@ static int prio_tune(struct Qdisc *sch, struct nlattr *opt,
 
 		qdisc_tree_reduce_backlog(child, child->q.qlen,
 					  child->qstats.backlog);
-		qdisc_put(child);
 	}
 
 	for (i = oldbands; i < q->bands; i++) {
@@ -230,6 +229,9 @@ static int prio_tune(struct Qdisc *sch, struct nlattr *opt,
 	}
 
 	sch_tree_unlock(sch);
+
+	for (i = q->bands; i < oldbands; i++)
+		qdisc_put(q->queues[i]);
 	return 0;
 }
 
-- 
2.17.1

^ permalink raw reply related

* Re: [Kernel][NET] Bug report on packet defragmenting
From: Eric Dumazet @ 2018-11-08  1:43 UTC (permalink / raw)
  To: soukjin.bae, netdev@vger.kernel.org
In-Reply-To: <20181108012927epcms1p47f719c1908da64a378690362901644ee@epcms1p4>



On 11/07/2018 05:29 PM, 배석진 wrote:

> If ipv6_defrag hook is not excuted simultaneously, then it's ok.
> ipv6_defrag hook can handle that. [exam 3]

This seems wrong.

This is the root cause, we should not try to work around it but fix it.

There is no guarantee that RSS/RPS/RFS can help here, packets can sit in per-cpu
backlogs long enough to reproduce the issue, if RX queues interrupts are spread
over many cpus.

^ permalink raw reply

* Re: [PATCH bpf] tools/bpftool: copy uapi/linux/tc_act/tc_bpf.h to tools directory
From: Yonghong Song @ 2018-11-08  1:47 UTC (permalink / raw)
  To: Li Zhijian, Alexei Starovoitov, Martin Lau, daniel@iogearbox.net,
	netdev@vger.kernel.org, rong.a.chen@intel.com
  Cc: Kernel Team
In-Reply-To: <149eb435-a9b5-da31-9f72-52168a9058f4@intel.com>



On 11/7/18 5:15 PM, Li Zhijian wrote:
> On 11/8/2018 9:00 AM, Yonghong Song wrote:
>> Commit f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
>> added certain networking support to bpftool.
>> The implementation relies on a relatively recent uapi header file
>> linux/tc_act/tc_bpf.h on the host which contains the marco
>> definition of TCA_ACT_BPF_ID.
>>
>> Unfortunately, this is not the case for all distributions.
>> See the email message below where rhel-7.2 does not have
>> an up-to-date linux/tc_act/tc_bpf.h.
>>    
>> https://urldefense.proofpoint.com/v2/url?u=https-3A__www.mail-2Darchive.com_linux-2Dkernel-40vger.kernel.org_msg1799211.html&d=DwICaQ&c=5VD0RTtNlTh3ycd41b3MUw&r=DA8e1B5r073vIqRrFz7MRA&m=BQIJZUzQfMmUkyvlAHMs7zygIFBysR_MlkAyHN59-7E&s=pVed3MjGDG_PMeBrhrqb3m57NRinnlcdL1QjAOj4iLA&e= 
>>
> 
> i have not tested this patch, but basing on the early commit
> 6f3bac08ff9 ("tools/bpf: bpftool: add net support")
> i cooked up similar patch locally, but i noticed that it also requires an
> up-to-date linux/pkt_cls.h as well to avoid compiling errors:

Thanks for testing. I will add linux/pkt_cls.h as well for the
version 2.

> 
> root@lkp-bdw-ep3 ~/linux-f6f3bac08f/tools/bpf/bpftool# make V=1
> [...snip...]
> gcc -O2 -W -Wall -Wextra -Wno-unused-parameter -Wshadow 
> -Wno-missing-field-initializers -DPACKAGE='"bpftool"' 
> -D__EXPORTED_HEADERS__ -I/root/linux-f6f3bac08f/kernel/bpf/ 
> -I/root/linux-f6f3bac08f/tools/include 
> -I/root/linux-f6f3bac08f/tools/include/uapi 
> -I/root/linux-f6f3bac08f/tools/lib/bpf 
> -I/root/linux-f6f3bac08f/tools/perf -DBPFTOOL_VERSION='"4.19.0-rc2"' 
> -DCOMPAT_NEED_REALLOCARRAY   -c -MMD -o netlink_dumper.o netlink_dumper.c
> make -C /root/linux-f6f3bac08f/tools/lib/bpf/ OUTPUT= libbpf.a
> make[1]: Entering directory '/root/linux-f6f3bac08f/tools/lib/bpf'
> netlink_dumper.c: In function 'do_bpf_filter_dump':
> netlink_dumper.c:153:9: error: 'TCA_BPF_ID' undeclared (first use in 
> this function)
>    if (tb[TCA_BPF_ID])
>           ^~~~~~~~~~
> netlink_dumper.c:153:9: note: each undeclared identifier is reported 
> only once for each function it appears in
> netlink_dumper.c:155:9: error: 'TCA_BPF_TAG' undeclared (first use in 
> this function)
>    if (tb[TCA_BPF_TAG])
>           ^~~~~~~~~~~
> Makefile:96: recipe for target 'netlink_dumper.o' failed
> make: *** [netlink_dumper.o] Error 1
> make: *** Waiting for unfinished jobs....
> make -f /root/linux-f6f3bac08f/tools/build/Makefile.build dir=. obj=libbpf
> make[1]: Leaving directory '/root/linux-f6f3bac08f/tools/lib/bpf'
> 
> Thanks
> Zhijian
> 
>>
>> This patch fixed the issue by copying linux/tc_act/tc_bpf.h from
>> kernel include/uapi directory to tools/include/uapi directory so
>> building the bpftool does not depend on host system for this file.
>>
>> Fixes: f6f3bac08ff9 ("tools/bpf: bpftool: add net support")
>> Reported-by: kernel test robot <rong.a.chen@intel.com>
>> Signed-off-by: Yonghong Song <yhs@fb.com>
>> ---
>>   tools/include/uapi/linux/tc_act/tc_bpf.h | 37 ++++++++++++++++++++++++
>>   1 file changed, 37 insertions(+)
>>   create mode 100644 tools/include/uapi/linux/tc_act/tc_bpf.h
>>
>> diff --git a/tools/include/uapi/linux/tc_act/tc_bpf.h 
>> b/tools/include/uapi/linux/tc_act/tc_bpf.h
>> new file mode 100644
>> index 000000000000..6e89a5df49a4
>> --- /dev/null
>> +++ b/tools/include/uapi/linux/tc_act/tc_bpf.h
>> @@ -0,0 +1,37 @@
>> +/* SPDX-License-Identifier: GPL-2.0+ WITH Linux-syscall-note */
>> +/*
>> + * Copyright (c) 2015 Jiri Pirko <jiri@resnulli.us>
>> + *
>> + * This program is free software; you can redistribute it and/or modify
>> + * it under the terms of the GNU General Public License as published by
>> + * the Free Software Foundation; either version 2 of the License, or
>> + * (at your option) any later version.
>> + */
>> +
>> +#ifndef __LINUX_TC_BPF_H
>> +#define __LINUX_TC_BPF_H
>> +
>> +#include <linux/pkt_cls.h>
>> +
>> +#define TCA_ACT_BPF 13
>> +
>> +struct tc_act_bpf {
>> +    tc_gen;
>> +};
>> +
>> +enum {
>> +    TCA_ACT_BPF_UNSPEC,
>> +    TCA_ACT_BPF_TM,
>> +    TCA_ACT_BPF_PARMS,
>> +    TCA_ACT_BPF_OPS_LEN,
>> +    TCA_ACT_BPF_OPS,
>> +    TCA_ACT_BPF_FD,
>> +    TCA_ACT_BPF_NAME,
>> +    TCA_ACT_BPF_PAD,
>> +    TCA_ACT_BPF_TAG,
>> +    TCA_ACT_BPF_ID,
>> +    __TCA_ACT_BPF_MAX,
>> +};
>> +#define TCA_ACT_BPF_MAX (__TCA_ACT_BPF_MAX - 1)
>> +
>> +#endif

^ permalink raw reply

* Re: [net-next PATCH] net: sched: cls_flower: Classify packets using port ranges
From: Nambiar, Amritha @ 2018-11-08  1:52 UTC (permalink / raw)
  To: Jiri Pirko
  Cc: netdev, davem, jakub.kicinski, sridhar.samudrala, jhs,
	xiyou.wangcong
In-Reply-To: <20181019085253.GF4558@nanopsycho.orion>

On 10/19/2018 1:52 AM, Jiri Pirko wrote:
> Thu, Oct 18, 2018 at 08:24:44PM CEST, amritha.nambiar@intel.com wrote:
>> On 10/18/2018 5:17 AM, Jiri Pirko wrote:
>>> Fri, Oct 12, 2018 at 03:53:30PM CEST, amritha.nambiar@intel.com wrote:
>>>> Added support in tc flower for filtering based on port ranges.
>>>> This is a rework of the RFC patch at:
>>>> https://patchwork.ozlabs.org/patch/969595/
>>>>
>>>> Example:
>>>> 1. Match on a port range:
>>>> -------------------------
>>>> $ tc filter add dev enp4s0 protocol ip parent ffff:\
>>>>  prio 1 flower ip_proto tcp dst_port range 20-30 skip_hw\
>>>>  action drop
>>>>
>>>> $ tc -s filter show dev enp4s0 parent ffff:
>>>> filter protocol ip pref 1 flower chain 0
>>>> filter protocol ip pref 1 flower chain 0 handle 0x1
>>>>  eth_type ipv4
>>>>  ip_proto tcp
>>>>  dst_port_min 20
>>>>  dst_port_max 30
>>>>  skip_hw
>>>>  not_in_hw
>>>>        action order 1: gact action drop
>>>>         random type none pass val 0
>>>>         index 1 ref 1 bind 1 installed 181 sec used 5 sec
>>>>        Action statistics:
>>>>        Sent 460 bytes 10 pkt (dropped 10, overlimits 0 requeues 0)
>>>>        backlog 0b 0p requeues 0
>>>>
>>>> 2. Match on IP address and port range:
>>>> --------------------------------------
>>>> $ tc filter add dev enp4s0 protocol ip parent ffff:\
>>>>  prio 1 flower dst_ip 192.168.1.1 ip_proto tcp dst_port range 100-200\
>>>>  skip_hw action drop
>>>>
>>>> $ tc -s filter show dev enp4s0 parent ffff:
>>>> filter protocol ip pref 1 flower chain 0 handle 0x2
>>>>  eth_type ipv4
>>>>  ip_proto tcp
>>>>  dst_ip 192.168.1.1
>>>>  dst_port_min 100
>>>>  dst_port_max 200
>>>>  skip_hw
>>>>  not_in_hw
>>>>        action order 1: gact action drop
>>>>         random type none pass val 0
>>>>         index 2 ref 1 bind 1 installed 28 sec used 6 sec
>>>>        Action statistics:
>>>>        Sent 460 bytes 10 pkt (dropped 10, overlimits 0 requeues 0)
>>>>        backlog 0b 0p requeues 0
>>>>
>>>> Signed-off-by: Amritha Nambiar <amritha.nambiar@intel.com>
>>>> ---
>>>> include/uapi/linux/pkt_cls.h |    5 ++
>>>> net/sched/cls_flower.c       |  134 ++++++++++++++++++++++++++++++++++++++++--
>>>> 2 files changed, 132 insertions(+), 7 deletions(-)
>>>>
>>>> diff --git a/include/uapi/linux/pkt_cls.h b/include/uapi/linux/pkt_cls.h
>>>> index 401d0c1..b569308 100644
>>>> --- a/include/uapi/linux/pkt_cls.h
>>>> +++ b/include/uapi/linux/pkt_cls.h
>>>> @@ -405,6 +405,11 @@ enum {
>>>> 	TCA_FLOWER_KEY_UDP_SRC,		/* be16 */
>>>> 	TCA_FLOWER_KEY_UDP_DST,		/* be16 */
>>>>
>>>> +	TCA_FLOWER_KEY_PORT_SRC_MIN,	/* be16 */
>>>> +	TCA_FLOWER_KEY_PORT_SRC_MAX,	/* be16 */
>>>> +	TCA_FLOWER_KEY_PORT_DST_MIN,	/* be16 */
>>>> +	TCA_FLOWER_KEY_PORT_DST_MAX,	/* be16 */
>>>> +
>>>> 	TCA_FLOWER_FLAGS,
>>>> 	TCA_FLOWER_KEY_VLAN_ID,		/* be16 */
>>>> 	TCA_FLOWER_KEY_VLAN_PRIO,	/* u8   */
>>>> diff --git a/net/sched/cls_flower.c b/net/sched/cls_flower.c
>>>> index 9aada2d..5f135f0 100644
>>>> --- a/net/sched/cls_flower.c
>>>> +++ b/net/sched/cls_flower.c
>>>> @@ -55,6 +55,9 @@ struct fl_flow_key {
>>>> 	struct flow_dissector_key_ip ip;
>>>> 	struct flow_dissector_key_ip enc_ip;
>>>> 	struct flow_dissector_key_enc_opts enc_opts;
>>>> +
>>>> +	struct flow_dissector_key_ports tp_min;
>>>> +	struct flow_dissector_key_ports tp_max;
>>>> } __aligned(BITS_PER_LONG / 8); /* Ensure that we can do comparisons as longs. */
>>>>
>>>> struct fl_flow_mask_range {
>>>> @@ -103,6 +106,11 @@ struct cls_fl_filter {
>>>> 	struct net_device *hw_dev;
>>>> };
>>>>
>>>> +enum fl_endpoint {
>>>> +	FLOWER_ENDPOINT_DST,
>>>> +	FLOWER_ENDPOINT_SRC
>>>> +};
>>>> +
>>>> static const struct rhashtable_params mask_ht_params = {
>>>> 	.key_offset = offsetof(struct fl_flow_mask, key),
>>>> 	.key_len = sizeof(struct fl_flow_key),
>>>> @@ -179,11 +187,86 @@ static void fl_clear_masked_range(struct fl_flow_key *key,
>>>> 	memset(fl_key_get_start(key, mask), 0, fl_mask_range(mask));
>>>> }
>>>>
>>>> +static int fl_range_compare_params(struct cls_fl_filter *filter,
>>>> +				   struct fl_flow_key *key,
>>>> +				   struct fl_flow_key *mkey,
>>>> +				   enum fl_endpoint endpoint)
>>>> +{
>>>> +	__be16 min_mask, max_mask, min_val, max_val;
>>>> +
>>>> +	if (endpoint == FLOWER_ENDPOINT_DST) {
>>>> +		min_mask = htons(filter->mask->key.tp_min.dst);
>>>> +		max_mask = htons(filter->mask->key.tp_max.dst);
>>>> +		min_val = htons(filter->key.tp_min.dst);
>>>> +		max_val = htons(filter->key.tp_max.dst);
>>>> +
>>>> +		if (min_mask && max_mask) {
>>>> +			if (htons(key->tp.dst) < min_val ||
>>>> +			    htons(key->tp.dst) > max_val)
>>>> +				return -1;
>>>> +
>>>> +			/* skb does not have min and max values */
>>>> +			mkey->tp_min.dst = filter->mkey.tp_min.dst;
>>>> +			mkey->tp_max.dst = filter->mkey.tp_max.dst;
>>>> +		}
>>>> +	} else {
>>>> +		min_mask = htons(filter->mask->key.tp_min.src);
>>>> +		max_mask = htons(filter->mask->key.tp_max.src);
>>>> +		min_val = htons(filter->key.tp_min.src);
>>>> +		max_val = htons(filter->key.tp_max.src);
>>>> +
>>>> +		if (min_mask && max_mask) {
>>>> +			if (htons(key->tp.src) < min_val ||
>>>> +			    htons(key->tp.src) > max_val)
>>>> +				return -1;
>>>> +
>>>> +			/* skb does not have min and max values */
>>>> +			mkey->tp_min.src = filter->mkey.tp_min.src;
>>>> +			mkey->tp_max.src = filter->mkey.tp_max.src;
>>>> +		}
>>>
>>> You basically have 2 functions in 1 here. Just have 2 functions:
>>> fl_port_range_dst_cmp()
>>> and
>>> fl_port_range_src_cmp()
>>>
>>> And avoid the "endpoint enum.
>>> Also, as you return -1 or 0, just make it bool.
>>>
>>
>> Makes sense. Will do.
>>
>>>
>>>> +	}
>>>> +	return 0;
>>>> +}
>>>> +
>>>> +static struct cls_fl_filter *fl_lookup_range(struct fl_flow_mask *mask,
>>>> +					     struct fl_flow_key *mkey,
>>>> +					     struct fl_flow_key *key)
>>>> +{
>>>> +	struct cls_fl_filter *filter, *f;
>>>> +	int ret;
>>>> +
>>>> +	list_for_each_entry_rcu(filter, &mask->filters, list) {
>>>> +		ret = fl_range_compare_params(filter, key, mkey,
>>>> +					      FLOWER_ENDPOINT_DST);
>>>> +		if (ret < 0)
>>>> +			continue;
>>>> +
>>>> +		ret = fl_range_compare_params(filter, key, mkey,
>>>> +					      FLOWER_ENDPOINT_SRC);
>>>> +		if (ret < 0)
>>>> +			continue;
>>>> +
>>>> +		f = rhashtable_lookup_fast(&mask->ht,
>>>> +					   fl_key_get_start(mkey, mask),
>>>> +					   mask->filter_ht_params);
>>>> +		if (f)
>>>> +			return f;
>>>> +	}
>>>> +	return NULL;
>>>> +}
>>>> +
>>>> static struct cls_fl_filter *fl_lookup(struct fl_flow_mask *mask,
>>>> -				       struct fl_flow_key *mkey)
>>>> +				       struct fl_flow_key *mkey,
>>>> +				       struct fl_flow_key *key, bool is_skb)
>>>> {
>>>> -	return rhashtable_lookup_fast(&mask->ht, fl_key_get_start(mkey, mask),
>>>> -				      mask->filter_ht_params);
>>>> +	if ((!(mask->key.tp_min.dst && mask->key.tp_max.dst) &&
>>>> +	     !(mask->key.tp_min.src && mask->key.tp_max.src)) || !is_skb) {
>>>
>>> Would be probably good to have a dedicated bit to check for and decide
>>> if you do normal/range lookup. This is fast path. 
>>>
>>
>> Will fix in v2.
>>
>>>
>>>> +		return  rhashtable_lookup_fast(&mask->ht,
>>>
>>> Remove double space   ^^
>>>
>>
>> Will fix in v2.
>>
>>>
>>>> +					       fl_key_get_start(mkey, mask),
>>>> +					       mask->filter_ht_params);
>>>> +	}
>>>> +	/* Classify based on range */
>>>> +	return fl_lookup_range(mask, mkey, key);
>>>> }
>>>>
>>>> static int fl_classify(struct sk_buff *skb, const struct tcf_proto *tp,
>>>> @@ -207,8 +290,8 @@ static int fl_classify(struct sk_buff *skb, const struct tcf_proto *tp,
>>>> 		skb_flow_dissect(skb, &mask->dissector, &skb_key, 0);
>>>>
>>>> 		fl_set_masked_key(&skb_mkey, &skb_key, mask);
>>>> +		f = fl_lookup(mask, &skb_mkey, &skb_key, true);
>>>>
>>>> -		f = fl_lookup(mask, &skb_mkey);
>>>> 		if (f && !tc_skip_sw(f->flags)) {
>>>> 			*res = f->res;
>>>> 			return tcf_exts_exec(skb, &f->exts, res);
>>>> @@ -909,6 +992,23 @@ static int fl_set_key(struct net *net, struct nlattr **tb,
>>>> 			       sizeof(key->arp.tha));
>>>> 	}
>>>>
>>>> +	if (key->basic.ip_proto == IPPROTO_TCP ||
>>>> +	    key->basic.ip_proto == IPPROTO_UDP ||
>>>> +	    key->basic.ip_proto == IPPROTO_SCTP) {
>>>> +		fl_set_key_val(tb, &key->tp_min.dst,
>>>> +			       TCA_FLOWER_KEY_PORT_DST_MIN, &mask->tp_min.dst,
>>>> +			       TCA_FLOWER_UNSPEC, sizeof(key->tp_min.dst));
>>>> +		fl_set_key_val(tb, &key->tp_max.dst,
>>>> +			       TCA_FLOWER_KEY_PORT_DST_MAX, &mask->tp_max.dst,
>>>> +			       TCA_FLOWER_UNSPEC, sizeof(key->tp_max.dst));
>>>> +		fl_set_key_val(tb, &key->tp_min.src,
>>>> +			       TCA_FLOWER_KEY_PORT_SRC_MIN, &mask->tp_min.src,
>>>> +			       TCA_FLOWER_UNSPEC, sizeof(key->tp_min.src));
>>>> +		fl_set_key_val(tb, &key->tp_max.src,
>>>> +			       TCA_FLOWER_KEY_PORT_SRC_MAX, &mask->tp_max.src,
>>>> +			       TCA_FLOWER_UNSPEC, sizeof(key->tp_max.src));
>>>> +	}
>>>> +
>>>> 	if (tb[TCA_FLOWER_KEY_ENC_IPV4_SRC] ||
>>>> 	    tb[TCA_FLOWER_KEY_ENC_IPV4_DST]) {
>>>> 		key->enc_control.addr_type = FLOW_DISSECTOR_KEY_IPV4_ADDRS;
>>>> @@ -1026,8 +1126,7 @@ static void fl_init_dissector(struct flow_dissector *dissector,
>>>> 			     FLOW_DISSECTOR_KEY_IPV4_ADDRS, ipv4);
>>>> 	FL_KEY_SET_IF_MASKED(mask, keys, cnt,
>>>> 			     FLOW_DISSECTOR_KEY_IPV6_ADDRS, ipv6);
>>>> -	FL_KEY_SET_IF_MASKED(mask, keys, cnt,
>>>> -			     FLOW_DISSECTOR_KEY_PORTS, tp);
>>>> +	FL_KEY_SET(keys, cnt, FLOW_DISSECTOR_KEY_PORTS, tp);
>>>> 	FL_KEY_SET_IF_MASKED(mask, keys, cnt,
>>>> 			     FLOW_DISSECTOR_KEY_IP, ip);
>>>> 	FL_KEY_SET_IF_MASKED(mask, keys, cnt,
>>>> @@ -1227,7 +1326,7 @@ static int fl_change(struct net *net, struct sk_buff *in_skb,
>>>> 		goto errout_idr;
>>>>
>>>> 	if (!tc_skip_sw(fnew->flags)) {
>>>> -		if (!fold && fl_lookup(fnew->mask, &fnew->mkey)) {
>>>> +		if (!fold && fl_lookup(fnew->mask, &fnew->mkey, NULL, false)) {
>>>
>>>
>>> I don't undestand why do you need the "is_skb" arg here. Could you
>>> please explain?
>>>
>>> Thanks!
>>>
>>
>> The reason to keep the 'is_skb' arg is because, fl_lookup is called in
>> two cases, one for skb classification and another for checking if a
>> filter exists every-time a new filter is added. In case of skb
>> classification, we need to go through the range-comparator to decide if
>> the skb's port-value falls within the range-filter's min and max limits.
>> In case of filter validation, the range-filter that we are trying to add
>> will have min and max values, and we are validating it against other
>> range-filters with min and max values. So, rhashtable lookup will
>> suffice here and there is no need to go through the range-comparator in
>> this case. In the above code, we are validating if a range-filter
>> exists, so 'is_skb' is false.
> 
> Got it. In that case, please just have a helper:
> static struct cls_fl_filter *__fl_lookup(struct fl_flow_mask *mask,
> 					 struct fl_flow_key *mkey)
> {
> 	return rhashtable_lookup_fast(&mask->ht, fl_key_get_start(mkey, mask),
> 				      mask->filter_ht_params);
> }
> 
> Call this helper from both fl_lookup() and fl_change()
> 

Alright. Will fix.

> 
>>
>>>
>>>> 			err = -EEXIST;
>>>> 			goto errout_mask;
>>>> 		}
>>>> @@ -1800,6 +1899,27 @@ static int fl_dump_key(struct sk_buff *skb, struct net *net,
>>>> 				  sizeof(key->arp.tha))))
>>>> 		goto nla_put_failure;
>>>>
>>>> +	if ((key->basic.ip_proto == IPPROTO_TCP ||
>>>> +	     key->basic.ip_proto == IPPROTO_UDP ||
> 
>>>> +	     key->basic.ip_proto == IPPROTO_SCTP) &&
>>>> +	     (fl_dump_key_val(skb, &key->tp_min.dst,
>>>> +			      TCA_FLOWER_KEY_PORT_DST_MIN,
>>>> +			      &mask->tp_min.dst, TCA_FLOWER_UNSPEC,
>>>> +			      sizeof(key->tp_min.dst)) ||
>>>> +	      fl_dump_key_val(skb, &key->tp_max.dst,
>>>> +			      TCA_FLOWER_KEY_PORT_DST_MAX,
>>>> +			      &mask->tp_max.dst, TCA_FLOWER_UNSPEC,
>>>> +			      sizeof(key->tp_max.dst)) ||
>>>> +	      fl_dump_key_val(skb, &key->tp_min.src,
>>>> +			      TCA_FLOWER_KEY_PORT_SRC_MIN,
>>>> +			      &mask->tp_min.src, TCA_FLOWER_UNSPEC,
>>>> +			      sizeof(key->tp_min.src)) ||
>>>> +	      fl_dump_key_val(skb, &key->tp_max.src,
>>>> +			      TCA_FLOWER_KEY_PORT_SRC_MAX,
>>>> +			      &mask->tp_max.src, TCA_FLOWER_UNSPEC,
>>>> +			      sizeof(key->tp_max.src))))
>>>> +		goto nla_put_failure;
>>>> +
>>>> 	if (key->enc_control.addr_type == FLOW_DISSECTOR_KEY_IPV4_ADDRS &&
>>>> 	    (fl_dump_key_val(skb, &key->enc_ipv4.src,
>>>> 			    TCA_FLOWER_KEY_ENC_IPV4_SRC, &mask->enc_ipv4.src,
>>>>

^ permalink raw reply

* [PATCH net-next] SUNRPC: drop pointless static qualifier in xdr_get_next_encode_buffer()
From: YueHaibing @ 2018-11-08  2:04 UTC (permalink / raw)
  To: Trond Myklebust, Anna Schumaker, J. Bruce Fields, David Miller,
	Jeff Layton
  Cc: YueHaibing, linux-nfs, netdev, kernel-janitors

There is no need to have the '__be32 *p' variable static since new value
always be assigned before use it.

Signed-off-by: YueHaibing <yuehaibing@huawei.com>
---
 net/sunrpc/xdr.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/net/sunrpc/xdr.c b/net/sunrpc/xdr.c
index 2bbb8d3..d80b156 100644
--- a/net/sunrpc/xdr.c
+++ b/net/sunrpc/xdr.c
@@ -546,7 +546,7 @@ void xdr_commit_encode(struct xdr_stream *xdr)
 static __be32 *xdr_get_next_encode_buffer(struct xdr_stream *xdr,
 		size_t nbytes)
 {
-	static __be32 *p;
+	__be32 *p;
 	int space_left;
 	int frag1bytes, frag2bytes;

^ permalink raw reply related

* Re: [PATCH 2/5] VSOCK: support fill data to mergeable rx buffer in host
From: jiangyiwen @ 2018-11-08  1:56 UTC (permalink / raw)
  To: Jason Wang, stefanha, stefanha; +Cc: netdev, kvm, virtualization
In-Reply-To: <76732898-8e4f-910a-aac5-ea4b635a1c15@redhat.com>

On 2018/11/7 21:32, Jason Wang wrote:
> 
> On 2018/11/7 下午3:11, jiangyiwen wrote:
>> On 2018/11/7 14:18, Jason Wang wrote:
>>> On 2018/11/6 下午2:30, jiangyiwen wrote:
>>>>> Seems duplicated with the one used by vhost-net.
>>>>>
>>>>> In packed virtqueue implementation, I plan to move this to vhost.c.
>>>>>
>>>> Yes, this code is full copied from vhost-net, if it can be packed into
>>>> vhost.c, it would be great.
>>>>
>>> If you try to reuse vhost-net, you don't even need to care about this:)
>>>
>>> Thanks
>>>
>>>
>>> .
>>>
>> Hi Jason,
>>
>> Thank your advice, I will consider your idea. But I don't know
>> what's stefan's suggestion? It seems that he doesn't care much
>> about this community.:(
> 
> 
> I think not. He is probably busy these days.
> 
> 
>>
>> I still hope this community can have some vitality.
>>
> 
> Let's wait for few more days for the possible comments from Stefan or Michael. But I do prefer to unify the virtio networking datapath which will be easier to be extended and maintained.
> 
> Thanks
> 
> 
> .
> 

Hi Jason,

Actually vsock use virtio-net as transport path should be a better idea,
I will try to consider the new idea.

Thanks,
Yiwen.

^ permalink raw reply

* RE:(2) [Kernel][NET] Bug report on packet defragmenting
From: 배석진 @ 2018-11-08  2:05 UTC (permalink / raw)
  To: Eric Dumazet, netdev@vger.kernel.org
In-Reply-To: <91b43bec-cb19-b94b-8ee3-26979e3a19d1@gmail.com>

 --------- Original Message ---------
Sender : Eric Dumazet <eric.dumazet@gmail.com>
Date   : 2018-11-08 10:44 (GMT+9)
Title  : Re: [Kernel][NET] Bug report on packet defragmenting
 
> On 11/07/2018 05:29 PM, 배석진 wrote:
>  
> > If ipv6_defrag hook is not excuted simultaneously, then it's ok.
> > ipv6_defrag hook can handle that. [exam 3]
>  
> This seems wrong.
>  
> This is the root cause, we should not try to work around it but fix it.
>  
> There is no guarantee that RSS/RPS/RFS can help here, packets can sit in per-cpu
> backlogs long enough to reproduce the issue, if RX queues interrupts are spread
> over many cpus.
 

Dear Dumazet,

Even if rx irq be spread to overal cpu, hash will be made by src/des address.
then they'll have a same hash and cpu. is it not enough?
Did you mean that we need total solution for all steering method? not just only RPS?

Best regards.



^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox