* Re: [PATCH 0/6] In-kernel QMI handling
From: Bjørn Mork @ 2017-08-08 11:02 UTC (permalink / raw)
To: Bjorn Andersson
Cc: David S. Miller, Andy Gross, David Brown, linux-arm-msm,
linux-soc, netdev, linux-kernel
In-Reply-To: <20170804145938.25427-1-bjorn.andersson@linaro.org>
Bjorn Andersson <bjorn.andersson@linaro.org> writes:
> This series starts by moving the common definitions of the QMUX protocol to the
> uapi header, as they are shared with clients - both in kernel and userspace.
>
> This series then introduces in-kernel helper functions for aiding the handling
> of QMI encoded messages in the kernel. QMI encoding is a wire-format used in
> exchanging messages between the majority of QRTR clients and services.
Interesting! I tried to add some QMI handling in the kernel a few years
ago, but was thankfully voted down. See
https://www.spinics.net/lists/netdev/msg183101.html and the following
discussion. I am convinced that was the right decision, for the client
side at least. The protocol is just too extensive and ever-growing to be
implemented in the kernel. We would be catching up forever.
Note that I had very limited knowledge of the protocol at the time I
wrote that driver. Still have, in fact :-)
Bjørn
^ permalink raw reply
* Performance comparision for 10G ethernet no vlans vs 10G ethernet traffic on one vlan
From: Paweł Staszewski @ 2017-08-08 10:53 UTC (permalink / raw)
To: netdev
Hi
Wondering why there is such a big difference when testing forwarding
host with forwarding traffic on vlan and without vlan.
Kernel used: 4.12.4
UDP stream ~10Mpps - random destination from network 172.16.0.0/12 +
random udp port
Forwarding performance with 8x RSS queues (no vlan on TX device enp216s0f1)
ip config:
RX NIC
7: enp216s0f0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state
UP group default qlen 8192
link/ether 0c:c4:7a:ea:21:44 brd ff:ff:ff:ff:ff:ff
inet 10.0.0.1/30 scope global enp216s0f0
valid_lft forever preferred_lft forever
inet6 fe80::ec4:7aff:feea:2144/64 scope link
valid_lft forever preferred_lft forever
TX NIC
8: enp216s0f1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state
UP group default qlen 8192
link/ether 0c:c4:7a:ea:21:45 brd ff:ff:ff:ff:ff:ff
inet 10.0.0.5/30 scope global enp216s0f1
valid_lft forever preferred_lft forever
inet6 fe80::ec4:7aff:feea:2145/64 scope link
valid_lft forever preferred_lft forever
enp216s0f0: 9772859.00 P/s 0.00 P/s 9772859.00 P/s
enp216s0f1: 0.00 P/s 9772883.00 P/s 9772883.00 P/s
------------------------------------------------------------------------------
total: 9772863.00 P/s 9772886.00 P/s 19545750.00
P/s
mpstat -P ALL 1 10
Average: CPU %usr %nice %sys %iowait %irq %soft %steal
%guest %gnice %idle
Average: all 0.00 0.00 0.00 0.00 0.00 11.89 0.00
0.00 0.00 88.11
Average: 0 0.00 0.00 0.00 0.00 0.00 0.10 0.00
0.00 0.00 99.90
Average: 1 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 2 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 3 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 4 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 5 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 6 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 7 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 8 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 9 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 10 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 11 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 12 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 13 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 14 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 15 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 16 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 17 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 18 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 19 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 20 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 21 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 22 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 23 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 24 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 25 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 26 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 27 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 28 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 29 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 30 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 31 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 32 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 33 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 34 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 35 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 36 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 37 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 38 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 39 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 40 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 41 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 42 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 43 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 44 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 45 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 46 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 47 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 48 0.00 0.00 0.00 0.00 0.00 84.10 0.00
0.00 0.00 15.90
Average: 49 0.00 0.00 0.00 0.00 0.00 83.20 0.00
0.00 0.00 16.80
Average: 50 0.00 0.00 0.00 0.00 0.00 81.98 0.00
0.00 0.00 18.02
Average: 51 0.00 0.00 0.00 0.00 0.00 80.80 0.00
0.00 0.00 19.20
Average: 52 0.00 0.00 0.00 0.00 0.00 82.20 0.00
0.00 0.00 17.80
Average: 53 0.00 0.00 0.00 0.00 0.00 85.30 0.00
0.00 0.00 14.70
Average: 54 0.00 0.00 0.00 0.00 0.00 85.30 0.00
0.00 0.00 14.70
Average: 55 0.00 0.00 0.00 0.00 0.00 82.88 0.00
0.00 0.00 17.12
PerfTop: 55080 irqs/sec kernel:99.8% exact: 0.0% [4000Hz
cycles], (all, 56 CPUs)
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
21.93% [kernel] [k] do_raw_spin_lock
7.22% [kernel] [k] fib_table_lookup
6.79% [kernel] [k] acpi_processor_ffh_cstate_enter
5.46% [kernel] [k] ixgbe_poll
4.98% [kernel] [k] netif_receive_skb_internal
2.90% [kernel] [k] __build_skb
2.82% [kernel] [k] ipt_do_table
2.44% [kernel] [k] ixgbe_xmit_frame_ring
2.42% [kernel] [k] ip_rcv
2.31% [kernel] [k] get_rps_cpu
1.98% [kernel] [k] ip_finish_output2
1.87% [kernel] [k] __dev_queue_xmit
1.82% [kernel] [k] __netif_receive_skb_core
1.57% [kernel] [k] ip_route_input_noref
1.39% [kernel] [k] kmem_cache_alloc
1.29% [kernel] [k] ip_forward
1.27% [kernel] [k] irq_entries_start
1.27% [kernel] [k] skb_release_data
1.15% [kernel] [k] netif_skb_features
1.14% [kernel] [k] sch_direct_xmit
1.12% [kernel] [k] page_frag_free
0.99% [kernel] [k] __local_bh_enable_ip
0.78% [kernel] [k] dev_gro_receive
0.77% [kernel] [k] fib_validate_source
0.71% [kernel] [k] ip_rcv_finish
0.71% [kernel] [k] get_dma_ops
0.70% [kernel] [k] __netdev_pick_tx
0.68% [kernel] [k] dev_hard_start_xmit
0.66% [kernel] [k] deliver_ptype_list_skb
0.52% [kernel] [k] ixgbe_alloc_rx_buffers
0.51% [kernel] [k] netdev_pick_tx
0.48% [kernel] [k] cpuidle_enter_state
0.48% [kernel] [k] eth_type_trans
0.47% [kernel] [k] nf_hook_slow
0.46% [kernel] [k] build_skb
0.44% [kernel] [k] is_swiotlb_buffer
And scenario with one vlan added to enp216s0f1 (vlan tag 1000)
ip config
RX NIC
7: enp216s0f0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state
UP group default qlen 8192
link/ether 0c:c4:7a:ea:21:44 brd ff:ff:ff:ff:ff:ff
inet 10.0.0.1/30 scope global enp216s0f0
valid_lft forever preferred_lft forever
inet6 fe80::ec4:7aff:feea:2144/64 scope link
valid_lft forever preferred_lft forever
TX NIC with assigned vlan 1000
8: enp216s0f1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state
UP group default qlen 8192
link/ether 0c:c4:7a:ea:21:45 brd ff:ff:ff:ff:ff:ff
inet6 fe80::ec4:7aff:feea:2145/64 scope link
valid_lft forever preferred_lft forever
10: vlan1000@enp216s0f1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500
qdisc noqueue state UP group default qlen 1000
link/ether 0c:c4:7a:ea:21:45 brd ff:ff:ff:ff:ff:ff
inet 10.0.0.5/30 scope global vlan1000
valid_lft forever preferred_lft forever
inet6 fe80::ec4:7aff:feea:2145/64 scope link
valid_lft forever preferred_lft forever
bwm-ng v0.6.1 (probing every 0.500s), press 'h' for help
input: /proc/net/dev type: rate
\ iface Rx Tx Total
==============================================================================
enp24s0f3: 61.88 P/s 7.98 P/s
69.86 P/s
lo: 0.00 P/s 0.00 P/s
0.00 P/s
vlan1000: 0.00 P/s 6309299.50 P/s 6309299.50 P/s
enp216s0f0: 6308918.50 P/s 0.00 P/s 6308918.50 P/s
enp216s0f1: 0.00 P/s 6308912.50 P/s 6308912.50 P/s
------------------------------------------------------------------------------
total: 6308980.00 P/s 12618220.00 P/s 18927200.00 P/s
pps drops from 9.7Mpps to 6.3Mpps
Cpu load rises to 100% cpu on all 8x Cores where RSS from NIC's are bind
Average: CPU %usr %nice %sys %iowait %irq %soft %steal
%guest %gnice %idle
Average: all 0.01 0.00 0.01 0.00 0.00 14.29
0.00 0.00 0.00 85.70
Average: 0 0.10 0.00 0.30 0.00 0.00 0.10 0.00
0.00 0.00 99.50
Average: 1 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 2 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 3 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 4 0.00 0.00 0.10 0.00 0.00 0.00 0.00
0.00 0.00 99.90
Average: 5 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 6 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 7 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 8 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 9 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 10 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 11 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 12 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 13 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 14 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 15 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 16 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 17 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 18 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 19 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 20 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 21 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 22 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 23 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 24 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 25 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 26 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 27 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 28 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 29 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 30 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 31 0.20 0.00 0.10 0.00 0.00 0.00 0.00
0.00 0.00 99.70
Average: 32 0.00 0.00 0.10 0.00 0.00 0.00 0.00
0.00 0.00 99.90
Average: 33 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 34 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 35 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 36 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 37 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 38 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 39 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 40 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 41 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 42 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 43 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 44 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 45 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 46 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 47 0.00 0.00 0.00 0.00 0.00 0.00 0.00
0.00 0.00 100.00
Average: 48 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 49 0.00 0.00 0.10 0.00 0.00 99.90
0.00 0.00 0.00 0.00
Average: 50 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 51 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 52 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 53 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 54 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
Average: 55 0.00 0.00 0.00 0.00 0.00 100.00
0.00 0.00 0.00 0.00
And perf top:
PerfTop: 38413 irqs/sec kernel:99.7% exact: 0.0% [4000Hz
cycles], (all, 56 CPUs)
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
11.96% [kernel] [k] do_raw_spin_lock
9.62% [kernel] [k] dst_release
9.19% [kernel] [k] skb_dst_force
8.15% [kernel] [k] rt_cache_valid
7.00% [kernel] [k] ip_finish_output2
6.17% [kernel] [k] fib_table_lookup
3.59% [kernel] [k] ixgbe_poll
3.32% [kernel] [k] eth_type_trans
2.59% [kernel] [k] dev_gro_receive
2.05% [kernel] [k] __build_skb
1.99% [kernel] [k] ixgbe_xmit_frame_ring
1.82% [kernel] [k] ip_rcv
1.79% [kernel] [k] acpi_processor_ffh_cstate_enter
1.64% [kernel] [k] __dev_queue_xmit
1.59% [kernel] [k] netif_skb_features
1.24% [kernel] [k] ipt_do_table
1.12% [kernel] [k] __netif_receive_skb_core
1.08% [kernel] [k] dev_hard_start_xmit
1.06% [kernel] [k] ip_route_input_noref
0.98% [kernel] [k] ip_forward
0.87% [kernel] [k] skb_release_data
0.82% [kernel] [k] sch_direct_xmit
0.77% [kernel] [k] inet_gro_receive
0.71% [kernel] [k] __local_bh_enable_ip
0.64% [kernel] [k] kmem_cache_alloc
0.63% [kernel] [k] page_frag_free
0.60% [kernel] [k] netdev_pick_tx
0.58% [kernel] [k] validate_xmit_skb
0.57% [kernel] [k] deliver_ptype_list_skb
0.49% [kernel] [k] ip_rcv_finish
0.49% [kernel] [k] vlan_dev_hard_start_xmit
0.49% [kernel] [k] get_dma_ops
0.48% [kernel] [k] eth_header
0.48% [kernel] [k] fib_validate_source
0.42% [kernel] [k] skb_network_protocol
0.41% [kernel] [k] neigh_connected_output
0.40% [kernel] [k] swiotlb_map_page
0.38% [kernel] [k] build_skb
0.37% [kernel] [k] ixgbe_alloc_rx_buffers
0.32% [kernel] [k] ip_output
0.31% [kernel] [k] __netdev_pick_tx
0.31% [kernel] [k] nf_hook_slow
0.28% [kernel] [k] ip_finish_output
0.28% [kernel] [k] is_swiotlb_buffer
0.27% [kernel] [k] udp4_gro_receive
0.27% [kernel] [k] validate_xmit_skb_list
0.26% [kernel] [k] virt_to_head_page
ethtool:
ethtool -k enp216s0f1
Features for enp216s0f1:
rx-checksumming: on
tx-checksumming: on
tx-checksum-ipv4: off [fixed]
tx-checksum-ip-generic: on
tx-checksum-ipv6: off [fixed]
tx-checksum-fcoe-crc: off [fixed]
tx-checksum-sctp: on
scatter-gather: on
tx-scatter-gather: on
tx-scatter-gather-fraglist: off [fixed]
tcp-segmentation-offload: on
tx-tcp-segmentation: on
tx-tcp-ecn-segmentation: off [fixed]
tx-tcp-mangleid-segmentation: off
tx-tcp6-segmentation: on
udp-fragmentation-offload: off [fixed]
generic-segmentation-offload: on
generic-receive-offload: on
large-receive-offload: off
rx-vlan-offload: on
tx-vlan-offload: on
ntuple-filters: on
receive-hashing: on
highdma: on [fixed]
rx-vlan-filter: on
vlan-challenged: off [fixed]
tx-lockless: off [fixed]
netns-local: off [fixed]
tx-gso-robust: off [fixed]
tx-fcoe-segmentation: off [fixed]
tx-gre-segmentation: on
tx-gre-csum-segmentation: on
tx-ipxip4-segmentation: on
tx-ipxip6-segmentation: on
tx-udp_tnl-segmentation: on
tx-udp_tnl-csum-segmentation: on
tx-gso-partial: on
tx-sctp-segmentation: off [fixed]
tx-esp-segmentation: off [fixed]
fcoe-mtu: off [fixed]
tx-nocache-copy: off
loopback: off [fixed]
rx-fcs: off [fixed]
rx-all: off
tx-vlan-stag-hw-insert: off [fixed]
rx-vlan-stag-hw-parse: off [fixed]
rx-vlan-stag-filter: off [fixed]
l2-fwd-offload: off
hw-tc-offload: off
esp-hw-offload: off [fixed]
esp-tx-csum-hw-offload: off [fixed]
ethtool -k enp216s0f0
Features for enp216s0f0:
rx-checksumming: on
tx-checksumming: on
tx-checksum-ipv4: off [fixed]
tx-checksum-ip-generic: on
tx-checksum-ipv6: off [fixed]
tx-checksum-fcoe-crc: off [fixed]
tx-checksum-sctp: on
scatter-gather: on
tx-scatter-gather: on
tx-scatter-gather-fraglist: off [fixed]
tcp-segmentation-offload: on
tx-tcp-segmentation: on
tx-tcp-ecn-segmentation: off [fixed]
tx-tcp-mangleid-segmentation: off
tx-tcp6-segmentation: on
udp-fragmentation-offload: off [fixed]
generic-segmentation-offload: on
generic-receive-offload: on
large-receive-offload: off
rx-vlan-offload: on
tx-vlan-offload: on
ntuple-filters: on
receive-hashing: on
highdma: on [fixed]
rx-vlan-filter: on
vlan-challenged: off [fixed]
tx-lockless: off [fixed]
netns-local: off [fixed]
tx-gso-robust: off [fixed]
tx-fcoe-segmentation: off [fixed]
tx-gre-segmentation: on
tx-gre-csum-segmentation: on
tx-ipxip4-segmentation: on
tx-ipxip6-segmentation: on
tx-udp_tnl-segmentation: on
tx-udp_tnl-csum-segmentation: on
tx-gso-partial: on
tx-sctp-segmentation: off [fixed]
tx-esp-segmentation: off [fixed]
fcoe-mtu: off [fixed]
tx-nocache-copy: off
loopback: off [fixed]
rx-fcs: off [fixed]
rx-all: off
tx-vlan-stag-hw-insert: off [fixed]
rx-vlan-stag-hw-parse: off [fixed]
rx-vlan-stag-filter: off [fixed]
l2-fwd-offload: off
hw-tc-offload: off
esp-hw-offload: off [fixed]
esp-tx-csum-hw-offload: off [fixed]
ethtool -i enp216s0f0
driver: ixgbe
version: 5.0.0-k
firmware-version: 0x800006da
expansion-rom-version:
bus-info: 0000:d8:00.0
supports-statistics: yes
supports-test: yes
supports-eeprom-access: yes
supports-register-dump: yes
supports-priv-flags: yes
ethtool -i enp216s0f1
driver: ixgbe
version: 5.0.0-k
firmware-version: 0x800006da
expansion-rom-version:
bus-info: 0000:d8:00.1
supports-statistics: yes
supports-test: yes
supports-eeprom-access: yes
supports-register-dump: yes
supports-priv-flags: yes
BR
Paweł
^ permalink raw reply
* Re: qmi_wwan: Null pointer dereference when removing driver
From: Bjørn Mork @ 2017-08-08 10:35 UTC (permalink / raw)
To: Nathaniel Roach; +Cc: netdev, Daniele Palmas
In-Reply-To: <0d39998a-dfa9-48c5-0c7f-19354f16a7c0@gmail.com>
[-- Attachment #1: Type: text/plain, Size: 5259 bytes --]
Nathaniel Roach <nroach44@gmail.com> writes:
> Unsure at which point was added, but issue not present in stock debian 4.11 kernel.
>
> Running on a Thinkpad X220 with coreboot.
>
> I'm building from upstream. When I attempt to remove the qmi_wwan module (which also happens pre-suspend) the rmmod process gets killed, and the following shows in dmesg:
>
> [ 59.979791] usb 2-1.4: USB disconnect, device number 4
> [ 59.980102] qmi_wwan 2-1.4:1.6 wwp0s29u1u4i6: unregister 'qmi_wwan' usb-0000:00:1d.0-1.4, WWAN/QMI device
> [ 60.006821] BUG: unable to handle kernel NULL pointer dereference at 00000000000000e0
> [ 60.006879] IP: qmi_wwan_disconnect+0x25/0xc0 [qmi_wwan]
> [ 60.006911] PGD 0
> [ 60.006911] P4D 0
> [ 60.006957] Oops: 0000 [#1] SMP
> [ 60.006978] Modules linked in: fuse(E) ccm(E) rfcomm(E) cmac(E) bnep(E) qmi_wwan(E) cdc_wdm(E) cdc_ether(E) usbnet(E) mii(E) btusb(E) btrtl(E) btbcm(E) btintel(E) bluetooth(E) joydev(E) xpad(E) ecdh_generic(E) ff_memless(E) binfmt_misc(E) snd_hda_codec_hdmi(E) snd_hda_codec_conexant(E) snd_hda_codec_generic(E) arc4(E) iTCO_wdt(E) iTCO_vendor_support(E) intel_rapl(E) x86_pkg_temp_thermal(E) kvm_intel(E) kvm(E) irqbypass(E) crct10dif_pclmul(E) crc32_pclmul(E) crc32c_intel(E) ghash_clmulni_intel(E) aesni_intel(E) iwlmvm(E) aes_x86_64(E) crypto_simd(E) mac80211(E) cryptd(E) glue_helper(E) snd_hda_intel(E) snd_hda_codec(E) iwlwifi(E) snd_hwdep(E) psmouse(E) snd_hda_core(E) snd_pcm(E) serio_raw(E) sdhci_pci(E) pcspkr(E) snd_timer(E) ehci_pci(E) e1000e(E) i2c_i801(E) ehci_hcd(E) snd(E) sg(E) i915(E) lpc_ich(E)
> [ 60.007366] ptp(E) usbcore(E) cfg80211(E) mfd_core(E) pps_core(E) shpchp(E) ac(E) battery(E) tpm_tis(E) tpm_tis_core(E) evdev(E) tpm(E) parport_pc(E) ppdev(E) lp(E) parport(E) ip_tables(E) x_tables(E) autofs4(E)
> [ 60.007474] CPU: 2 PID: 33 Comm: kworker/2:1 Tainted: G E 4.12.3-nr44-normandy-r1500619820+ #1
> [ 60.007524] Hardware name: LENOVO 4291LR7/4291LR7, BIOS CBET4000 4.6-810-g50522254fb 07/21/2017
> [ 60.007580] Workqueue: usb_hub_wq hub_event [usbcore]
> [ 60.007609] task: ffff8c882b716040 task.stack: ffffb8e800d84000
> [ 60.007644] RIP: 0010:qmi_wwan_disconnect+0x25/0xc0 [qmi_wwan]
> [ 60.007678] RSP: 0018:ffffb8e800d87b38 EFLAGS: 00010246
> [ 60.007711] RAX: 0000000000000000 RBX: 0000000000000000 RCX: 0000000000000000
> [ 60.007752] RDX: 0000000000000001 RSI: ffff8c8824f3f1d0 RDI: ffff8c8824ef6400
> [ 60.007792] RBP: ffff8c8824ef6400 R08: 0000000000000000 R09: 0000000000000000
> [ 60.007833] R10: ffffb8e800d87780 R11: 0000000000000011 R12: ffffffffc07ea0e8
> [ 60.007874] R13: ffff8c8824e2e000 R14: ffff8c8824e2e098 R15: 0000000000000000
> [ 60.007915] FS: 0000000000000000(0000) GS:ffff8c8835300000(0000) knlGS:0000000000000000
> [ 60.007960] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
> [ 60.007994] CR2: 00000000000000e0 CR3: 0000000229ca5000 CR4: 00000000000406e0
> [ 60.008035] Call Trace:
> [ 60.008065] ? usb_unbind_interface+0x71/0x270 [usbcore]
> [ 60.008101] ? device_release_driver_internal+0x154/0x210
> [ 60.008135] ? qmi_wwan_unbind+0x6d/0xc0 [qmi_wwan]
> [ 60.008168] ? usbnet_disconnect+0x6c/0xf0 [usbnet]
> [ 60.008194] ? qmi_wwan_disconnect+0x87/0xc0 [qmi_wwan]
> [ 60.008232] ? usb_unbind_interface+0x71/0x270 [usbcore]
> [ 60.008264] ? device_release_driver_internal+0x154/0x210
> [ 60.008296] ? bus_remove_device+0xf5/0x160
> [ 60.008324] ? device_del+0x1dc/0x310
> [ 60.008355] ? usb_remove_ep_devs+0x1b/0x30 [usbcore]
> [ 60.008393] ? usb_disable_device+0x93/0x250 [usbcore]
> [ 60.008430] ? usb_disconnect+0x90/0x260 [usbcore]
> [ 60.008468] ? hub_event+0x1d9/0x14a0 [usbcore]
> [ 60.008500] ? process_one_work+0x175/0x370
> [ 60.008528] ? worker_thread+0x4a/0x380
> [ 60.008555] ? kthread+0xfc/0x130
> [ 60.008579] ? process_one_work+0x370/0x370
> [ 60.008606] ? kthread_park+0x60/0x60
> [ 60.008631] ? ret_from_fork+0x22/0x30
> [ 60.008656] Code: 66 0f 1f 44 00 00 66 66 66 66 90 55 48 89 fd 53 48 83 ec 10 48 8b 9f c8 00 00 00 65 48 8b 04 25 28 00 00 00 48 89 44 24 08 31 c0 <f6> 83 e0 00 00 00 02 74 51 e8 0d b3 2b cd 85 c0 74 67 48 8b bb
> [ 60.011925] RIP: qmi_wwan_disconnect+0x25/0xc0 [qmi_wwan] RSP: ffffb8e800d87b38
> [ 60.013564] CR2: 00000000000000e0
> [ 60.022125] ---[ end trace e536b59f45bc0f25 ]---
> [ 60.025385] IPv6: ADDRCONF(NETDEV_UP): wlp2s0: link is not ready
>
> If I attempt a second rmmod, the process hangs. If I attempt it on 4.11.x it works as expected:
>
> [ 16.897783] fuse init (API version 7.26)
> [ 68.073552] usbcore: deregistering interface driver qmi_wwan
> [ 68.075808] qmi_wwan 2-1.4:1.6 wwp0s29u1u4i6: unregister 'qmi_wwan' usb-0000:00:1d.0-1.4, WWAN/QMI device
> [ 72.431403] e1000e: enp0s25 NIC Link is Down
>
> So I'm pretty certain it's not coreboot causing the issue.
Thanks a lot for the report! Just one question: Does your modem have
separate control and data interfaces? If so, then I believe the
attached patch will fix the issue. Are you able to test it?
If the modem use the more common cobined interface model. then I need to
investigate this further..
Bjørn
[-- Attachment #2: 0001-qmi_wwan-fix-NULL-deref-on-disconnect.patch --]
[-- Type: text/x-diff, Size: 3310 bytes --]
>From c6ca53a5aaf6ce6a2733f75363119444adbe5d82 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Bj=C3=B8rn=20Mork?= <bjorn@mork.no>
Date: Tue, 8 Aug 2017 12:17:25 +0200
Subject: [RFT] qmi_wwan: fix NULL deref on disconnect
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
qmi_wwan_disconnect is called twice when disconnecting devices with
separate control and data interfaces. The first invocation will set
the interface data to NULL to flag that disconnect has been handled.
But the matching NULL check was left out when qmi_wwan_disconnect
was added, resulting in this oops:
usb 2-1.4: USB disconnect, device number 4
qmi_wwan 2-1.4:1.6 wwp0s29u1u4i6: unregister 'qmi_wwan' usb-0000:00:1d.0-1.4, WWAN/QMI device
BUG: unable to handle kernel NULL pointer dereference at 00000000000000e0
IP: qmi_wwan_disconnect+0x25/0xc0 [qmi_wwan]
PGD 0
P4D 0
Oops: 0000 [#1] SMP
Modules linked in: <stripped irrelevant module list>
CPU: 2 PID: 33 Comm: kworker/2:1 Tainted: G E 4.12.3-nr44-normandy-r1500619820+ #1
Hardware name: LENOVO 4291LR7/4291LR7, BIOS CBET4000 4.6-810-g50522254fb 07/21/2017
Workqueue: usb_hub_wq hub_event [usbcore]
task: ffff8c882b716040 task.stack: ffffb8e800d84000
RIP: 0010:qmi_wwan_disconnect+0x25/0xc0 [qmi_wwan]
RSP: 0018:ffffb8e800d87b38 EFLAGS: 00010246
RAX: 0000000000000000 RBX: 0000000000000000 RCX: 0000000000000000
RDX: 0000000000000001 RSI: ffff8c8824f3f1d0 RDI: ffff8c8824ef6400
RBP: ffff8c8824ef6400 R08: 0000000000000000 R09: 0000000000000000
R10: ffffb8e800d87780 R11: 0000000000000011 R12: ffffffffc07ea0e8
R13: ffff8c8824e2e000 R14: ffff8c8824e2e098 R15: 0000000000000000
FS: 0000000000000000(0000) GS:ffff8c8835300000(0000) knlGS:0000000000000000
CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
CR2: 00000000000000e0 CR3: 0000000229ca5000 CR4: 00000000000406e0
Call Trace:
? usb_unbind_interface+0x71/0x270 [usbcore]
? device_release_driver_internal+0x154/0x210
? qmi_wwan_unbind+0x6d/0xc0 [qmi_wwan]
? usbnet_disconnect+0x6c/0xf0 [usbnet]
? qmi_wwan_disconnect+0x87/0xc0 [qmi_wwan]
? usb_unbind_interface+0x71/0x270 [usbcore]
? device_release_driver_internal+0x154/0x210
Reported-by: Nathaniel Roach <nroach44@gmail.com>
Fixes: c6adf77953bc ("net: usb: qmi_wwan: add qmap mux protocol support")
Cc: Daniele Palmas <dnlplm@gmail.com>
Signed-off-by: Bjørn Mork <bjorn@mork.no>
---
drivers/net/usb/qmi_wwan.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/drivers/net/usb/qmi_wwan.c b/drivers/net/usb/qmi_wwan.c
index ff6f39fe6c00..8c3733608271 100644
--- a/drivers/net/usb/qmi_wwan.c
+++ b/drivers/net/usb/qmi_wwan.c
@@ -1341,10 +1341,14 @@ static int qmi_wwan_probe(struct usb_interface *intf,
static void qmi_wwan_disconnect(struct usb_interface *intf)
{
struct usbnet *dev = usb_get_intfdata(intf);
- struct qmi_wwan_state *info = (void *)&dev->data;
+ struct qmi_wwan_state *info;
struct list_head *iter;
struct net_device *ldev;
+ /* called twice if separate control and data intf */
+ if (!dev)
+ return;
+ info = (void *)&dev->data;
if (info->flags & QMI_WWAN_FLAG_MUX) {
if (!rtnl_trylock()) {
restart_syscall();
--
2.11.0
^ permalink raw reply related
* Re: [PATCH v3 net-next 3/5] sock: ULP infrastructure
From: John Fastabend @ 2017-08-08 10:16 UTC (permalink / raw)
To: Tom Herbert, netdev; +Cc: rohit, davejwatson
In-Reply-To: <20170807172818.31855-4-tom@quantonium.net>
On 08/07/2017 10:28 AM, Tom Herbert wrote:
> Generalize the TCP ULP infrastructure recently introduced to support
> kTLS. This adds a SO_ULP socket option and creates new fields in
> sock structure for ULP ops and ULP data. Also, the interface allows
> additional per ULP parameters to be set so that a ULP can be pushed
> and operations started in one shot.
>
> Signed-off-by: Tom Herbert <tom@quantonium.net>
> ---
I think this generalization should not get committed until it has a user.
I see you posted the socktap stuff but that is just an RFC for now.
[...]
> +
> +static inline void ulp_get_available(char *buf, size_t len)
> +{
Do we need to check len field or is len == 0 invalid?
> + *buf = '\0';
> +}
> +
> +static inline void ulp_cleanup(struct sock *sk)
> +{
> +}
> +
[...]
Rest looks OK I'll take a closer look tomorrow at this and the RFC user.
Thanks,
John
^ permalink raw reply
* Re: [PATCH v3 net-next 1/5] proto_ops: Fixes to adding locked version of sendmsg/page
From: John Fastabend @ 2017-08-08 9:55 UTC (permalink / raw)
To: Tom Herbert, netdev; +Cc: rohit, davejwatson
In-Reply-To: <20170807172818.31855-2-tom@quantonium.net>
On 08/07/2017 10:28 AM, Tom Herbert wrote:
> Fixes for two issues pointed out by John Fastabend.
>
> Fixes: 306b13eb3cf9515a ("proto_ops: Add locked held versions of sendmsg and sendpage")
> Reported-by: John Fastabend <john.fastabend@gmail.com>
> Signed-off-by: Tom Herbert <tom@quantonium.net>
> ---
This is the same patch as the one in my RFC series so its an ack from me.
Acked-by: John Fastabend <john.fastabend@gmail.com>
^ permalink raw reply
* [PATCH][next] net: phy: mdio-bcm-unimac: fix unsigned wrap-around when decrementing timeout
From: Colin King @ 2017-08-08 9:52 UTC (permalink / raw)
To: Andrew Lunn, Florian Fainelli, netdev; +Cc: kernel-janitors, linux-kernel
From: Colin Ian King <colin.king@canonical.com>
Change post-decrement compare to pre-decrement to avoid an
unsigned integer wrap-around on timeout. This leads to the following
!timeout check to never to be true so -ETIMEDOUT is never returned.
Detected by CoverityScan, CID#1452623 ("Logically dead code")
Fixes: 69a60b0579a4 ("net: phy: mdio-bcm-unimac: factor busy polling loop")
Signed-off-by: Colin Ian King <colin.king@canonical.com>
---
drivers/net/phy/mdio-bcm-unimac.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/phy/mdio-bcm-unimac.c b/drivers/net/phy/mdio-bcm-unimac.c
index 89425ca48412..73c5267a11fd 100644
--- a/drivers/net/phy/mdio-bcm-unimac.c
+++ b/drivers/net/phy/mdio-bcm-unimac.c
@@ -71,7 +71,7 @@ static int unimac_mdio_poll(void *wait_func_data)
return 0;
usleep_range(1000, 2000);
- } while (timeout--);
+ } while (--timeout);
if (!timeout)
return -ETIMEDOUT;
--
2.11.0
^ permalink raw reply related
* [PATCH net] ppp: fix xmit recursion detection on ppp channels
From: Guillaume Nault @ 2017-08-08 9:43 UTC (permalink / raw)
To: netdev; +Cc: Gao Feng, Liu Jianying, David Miller, linux-ppp, Paul Mackerras
Commit e5dadc65f9e0 ("ppp: Fix false xmit recursion detect with two ppp
devices") dropped the xmit_recursion counter incrementation in
ppp_channel_push() and relied on ppp_xmit_process() for this task.
But __ppp_channel_push() can also send packets directly (using the
.start_xmit() channel callback), in which case the xmit_recursion
counter isn't incremented anymore. If such packets get routed back to
the parent ppp unit, ppp_xmit_process() won't notice the recursion and
will call ppp_channel_push() on the same channel, effectively creating
the deadlock situation that the xmit_recursion mechanism was supposed
to prevent.
This patch re-introduces the xmit_recursion counter incrementation in
ppp_channel_push(). Since the xmit_recursion variable is now part of
the parent ppp unit, incrementation is skipped if the channel doesn't
have any. This is fine because only packets routed through the parent
unit may enter the channel recursively.
Finally, we have to ensure that pch->ppp is not going to be modified
while executing ppp_channel_push(). Instead of taking this lock only
while calling ppp_xmit_process(), we now have to hold it for the full
ppp_channel_push() execution. This respects the ppp locks ordering
which requires locking ->upl before ->downl.
Fixes: e5dadc65f9e0 ("ppp: Fix false xmit recursion detect with two ppp devices")
Signed-off-by: Guillaume Nault <g.nault@alphalink.fr>
---
drivers/net/ppp/ppp_generic.c | 18 ++++++++++--------
1 file changed, 10 insertions(+), 8 deletions(-)
diff --git a/drivers/net/ppp/ppp_generic.c b/drivers/net/ppp/ppp_generic.c
index bd4303944e44..a404552555d4 100644
--- a/drivers/net/ppp/ppp_generic.c
+++ b/drivers/net/ppp/ppp_generic.c
@@ -1915,21 +1915,23 @@ static void __ppp_channel_push(struct channel *pch)
spin_unlock(&pch->downl);
/* see if there is anything from the attached unit to be sent */
if (skb_queue_empty(&pch->file.xq)) {
- read_lock(&pch->upl);
ppp = pch->ppp;
if (ppp)
- ppp_xmit_process(ppp);
- read_unlock(&pch->upl);
+ __ppp_xmit_process(ppp);
}
}
static void ppp_channel_push(struct channel *pch)
{
- local_bh_disable();
-
- __ppp_channel_push(pch);
-
- local_bh_enable();
+ read_lock_bh(&pch->upl);
+ if (pch->ppp) {
+ (*this_cpu_ptr(pch->ppp->xmit_recursion))++;
+ __ppp_channel_push(pch);
+ (*this_cpu_ptr(pch->ppp->xmit_recursion))--;
+ } else {
+ __ppp_channel_push(pch);
+ }
+ read_unlock_bh(&pch->upl);
}
/*
--
2.14.0
^ permalink raw reply related
* [PATCH] net: phy: Use tab for indentation in Kconfig
From: Michal Simek @ 2017-08-08 9:32 UTC (permalink / raw)
To: linux-kernel, monstr; +Cc: netdev, Andrew Lunn, Florian Fainelli
Using tabs instead of space for indentaion
Signed-off-by: Michal Simek <michal.simek@xilinx.com>
---
drivers/net/phy/Kconfig | 42 +++++++++++++++++++++---------------------
1 file changed, 21 insertions(+), 21 deletions(-)
diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
index 928fd892f167..5d8cce3fab57 100644
--- a/drivers/net/phy/Kconfig
+++ b/drivers/net/phy/Kconfig
@@ -5,7 +5,7 @@
menuconfig MDIO_DEVICE
tristate "MDIO bus device drivers"
help
- MDIO devices and driver infrastructure code.
+ MDIO devices and driver infrastructure code.
config MDIO_BUS
tristate
@@ -107,11 +107,11 @@ config MDIO_HISI_FEMAC
Hisilicon SoC that have an Fast Ethernet MAC.
config MDIO_MOXART
- tristate "MOXA ART MDIO interface support"
- depends on ARCH_MOXART
- help
- This driver supports the MDIO interface found in the network
- interface units of the MOXA ART SoC
+ tristate "MOXA ART MDIO interface support"
+ depends on ARCH_MOXART
+ help
+ This driver supports the MDIO interface found in the network
+ interface units of the MOXA ART SoC
config MDIO_OCTEON
tristate "Octeon and some ThunderX SOCs MDIO buses"
@@ -172,7 +172,7 @@ config LED_TRIGGER_PHY
state change will trigger the events, for consumption by an
LED class driver. There are triggers for each link speed currently
supported by the phy, and are of the form:
- <mii bus id>:<phy>:<speed>
+ <mii bus id>:<phy>:<speed>
Where speed is in the form:
<Speed in megabits>Mbps or <Speed in gigabits>Gbps
@@ -186,9 +186,9 @@ config AMD_PHY
Currently supports the am79c874
config AQUANTIA_PHY
- tristate "Aquantia PHYs"
- ---help---
- Currently supports the Aquantia AQ1202, AQ2104, AQR105, AQR405
+ tristate "Aquantia PHYs"
+ ---help---
+ Currently supports the Aquantia AQ1202, AQ2104, AQR105, AQR405
config AT803X_PHY
tristate "AT803X PHYs"
@@ -352,21 +352,21 @@ config STE10XP
This is the driver for the STe100p and STe101p PHYs.
config TERANETICS_PHY
- tristate "Teranetics PHYs"
- ---help---
- Currently supports the Teranetics TN2020
+ tristate "Teranetics PHYs"
+ ---help---
+ Currently supports the Teranetics TN2020
config VITESSE_PHY
- tristate "Vitesse PHYs"
- ---help---
- Currently supports the vsc8244
+ tristate "Vitesse PHYs"
+ ---help---
+ Currently supports the vsc8244
config XILINX_GMII2RGMII
- tristate "Xilinx GMII2RGMII converter driver"
- ---help---
- This driver support xilinx GMII to RGMII IP core it provides
- the Reduced Gigabit Media Independent Interface(RGMII) between
- Ethernet physical media devices and the Gigabit Ethernet controller.
+ tristate "Xilinx GMII2RGMII converter driver"
+ ---help---
+ This driver support xilinx GMII to RGMII IP core it provides
+ the Reduced Gigabit Media Independent Interface(RGMII) between
+ Ethernet physical media devices and the Gigabit Ethernet controller.
endif # PHYLIB
--
1.9.1
^ permalink raw reply related
* [PATCH net] rds: Reintroduce statistics counting
From: Håkon Bugge @ 2017-08-08 9:13 UTC (permalink / raw)
To: Santosh Shilimkar, David S . Miller
Cc: netdev-u79uwXL29TY76Z2rM5mHXA, linux-rdma-u79uwXL29TY76Z2rM5mHXA,
rds-devel-N0ozoZBvEnrZJqsBc5GL+g,
linux-kernel-u79uwXL29TY76Z2rM5mHXA,
knut.omang-QHcLZuEGTsvQT0dZR+AlfA,
wei.lin-guay-QHcLZuEGTsvQT0dZR+AlfA
In commit 7e3f2952eeb1 ("rds: don't let RDS shutdown a connection
while senders are present"), refilling the receive queue was removed
from rds_ib_recv(), along with the increment of
s_ib_rx_refill_from_thread.
Commit 73ce4317bf98 ("RDS: make sure we post recv buffers")
re-introduces filling the receive queue from rds_ib_recv(), but does
not add the statistics counter. rds_ib_recv() was later renamed to
rds_ib_recv_path().
This commit reintroduces the statistics counting of
s_ib_rx_refill_from_thread and s_ib_rx_refill_from_cq.
Signed-off-by: Håkon Bugge <haakon.bugge-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
Reviewed-by: Knut Omang <knut.omang-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
Reviewed-by: Wei Lin Guay <wei.lin.guay-QHcLZuEGTsvQT0dZR+AlfA@public.gmane.org>
---
net/rds/ib_recv.c | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/net/rds/ib_recv.c b/net/rds/ib_recv.c
index e10624a..9722bf8 100644
--- a/net/rds/ib_recv.c
+++ b/net/rds/ib_recv.c
@@ -1015,8 +1015,10 @@ void rds_ib_recv_cqe_handler(struct rds_ib_connection *ic,
if (rds_ib_ring_empty(&ic->i_recv_ring))
rds_ib_stats_inc(s_ib_rx_ring_empty);
- if (rds_ib_ring_low(&ic->i_recv_ring))
+ if (rds_ib_ring_low(&ic->i_recv_ring)) {
rds_ib_recv_refill(conn, 0, GFP_NOWAIT);
+ rds_ib_stats_inc(s_ib_rx_refill_from_cq);
+ }
}
int rds_ib_recv_path(struct rds_conn_path *cp)
@@ -1029,6 +1031,7 @@ int rds_ib_recv_path(struct rds_conn_path *cp)
if (rds_conn_up(conn)) {
rds_ib_attempt_ack(ic);
rds_ib_recv_refill(conn, 0, GFP_KERNEL);
+ rds_ib_stats_inc(s_ib_rx_refill_from_thread);
}
return ret;
--
2.9.3
--
To unsubscribe from this list: send the line "unsubscribe linux-rdma" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply related
* Re: [RFC PATCH 2/2] bpf: Initialise mod[] in bpf_trace_printk
From: Daniel Borkmann @ 2017-08-08 8:46 UTC (permalink / raw)
To: James Hogan, Alexei Starovoitov
Cc: linux-kernel, Steven Rostedt, Ingo Molnar, netdev
In-Reply-To: <20170807222514.24292-3-james.hogan@imgtec.com>
On 08/08/2017 12:25 AM, James Hogan wrote:
> In bpf_trace_printk(), the elements in mod[] are left uninitialised, but
> they are then incremented to track the width of the formats. Zero
> initialise the array just in case the memory contains non-zero values on
> entry.
>
> Fixes: 9c959c863f82 ("tracing: Allow BPF programs to call bpf_trace_printk()")
> Signed-off-by: James Hogan <james.hogan@imgtec.com>
> Cc: Alexei Starovoitov <ast@kernel.org>
> Cc: Daniel Borkmann <daniel@iogearbox.net>
> Cc: Steven Rostedt <rostedt@goodmis.org>
> Cc: Ingo Molnar <mingo@redhat.com>
> Cc: netdev@vger.kernel.org
> ---
> When I checked (on MIPS32), the elements tended to have the value zero
> anyway (does BPF zero the stack or something clever?), so this is a
> purely theoretical fix.
> ---
> kernel/trace/bpf_trace.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/kernel/trace/bpf_trace.c b/kernel/trace/bpf_trace.c
> index 32dcbe1b48f2..86a52857d941 100644
> --- a/kernel/trace/bpf_trace.c
> +++ b/kernel/trace/bpf_trace.c
> @@ -129,7 +129,7 @@ BPF_CALL_5(bpf_trace_printk, char *, fmt, u32, fmt_size, u64, arg1,
> u64, arg2, u64, arg3)
> {
> bool str_seen = false;
> - int mod[3] = {};
> + int mod[3] = { 0, 0, 0 };
I'm probably missing something, but is the behavior of gcc wrt
above initializers different on mips (it zeroes just fine on x86
at least)? If yes, we'd probably need a cocci script to also check
rest of the kernel given this is used in a number of places. Hm,
could you elaborate?
> int fmt_cnt = 0;
> u64 unsafe_addr;
> char buf[64];
>
^ permalink raw reply
* [PATCH net] tcp: fastopen: tcp_connect() must refresh the route
From: Eric Dumazet @ 2017-08-08 8:41 UTC (permalink / raw)
To: David Miller; +Cc: netdev, Wei Wang, Yuchung Cheng, Dmitry Vyukov
From: Eric Dumazet <edumazet@google.com>
With new TCP_FASTOPEN_CONNECT socket option, there is a possibility
to call tcp_connect() while socket sk_dst_cache is either NULL
or invalid.
+0 socket(..., SOCK_STREAM, IPPROTO_TCP) = 4
+0 fcntl(4, F_SETFL, O_RDWR|O_NONBLOCK) = 0
+0 setsockopt(4, SOL_TCP, TCP_FASTOPEN_CONNECT, [1], 4) = 0
+0 connect(4, ..., ...) = 0
<< sk->sk_dst_cache becomes obsolete, or even set to NULL >>
+1 sendto(4, ..., 1000, MSG_FASTOPEN, ..., ...) = 1000
We need to refresh the route otherwise bad things can happen,
especially when syzkaller is running on the host :/
Fixes: 19f6d3f3c8422 ("net/tcp-fastopen: Add new API support")
Reported-by: Dmitry Vyukov <dvyukov@google.com>
Signed-off-by: Eric Dumazet <edumazet@google.com>
Cc: Wei Wang <weiwan@google.com>
Cc: Yuchung Cheng <ycheng@google.com>
---
net/ipv4/tcp_output.c | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c
index 276406a83a37..b7661a68d498 100644
--- a/net/ipv4/tcp_output.c
+++ b/net/ipv4/tcp_output.c
@@ -3436,6 +3436,10 @@ int tcp_connect(struct sock *sk)
int err;
tcp_call_bpf(sk, BPF_SOCK_OPS_TCP_CONNECT_CB);
+
+ if (inet_csk(sk)->icsk_af_ops->rebuild_header(sk))
+ return -EHOSTUNREACH; /* Routing failure or similar. */
+
tcp_connect_init(sk);
if (unlikely(tp->repair)) {
^ permalink raw reply related
* Re: [PATCHv3 net] net: sched: set xt_tgchk_param par.net properly in ipt_init_target
From: Jiri Pirko @ 2017-08-08 8:24 UTC (permalink / raw)
To: Xin Long; +Cc: network dev, davem, Cong Wang
In-Reply-To: <7aa6e3f47ea0feb6f348b4de20fc6503e8c8e25b.1502177125.git.lucien.xin@gmail.com>
Tue, Aug 08, 2017 at 09:25:25AM CEST, lucien.xin@gmail.com wrote:
>Now xt_tgchk_param par in ipt_init_target is a local varibale,
>par.net is not initialized there. Later when xt_check_target
>calls target's checkentry in which it may access par.net, it
>would cause kernel panic.
>
>Jaroslav found this panic when running:
>
> # ip link add TestIface type dummy
> # tc qd add dev TestIface ingress handle ffff:
> # tc filter add dev TestIface parent ffff: u32 match u32 0 0 \
> action xt -j CONNMARK --set-mark 4
>
>This patch is to pass net param into ipt_init_target and set
>par.net with it properly in there.
>
>v1->v2:
> As Wang Cong pointed, I missed ipt_net_id != xt_net_id, so fix
> it by also passing net_id to __tcf_ipt_init.
>v2->v3:
> Missed the fixes tag, so add it.
>
>Fixes: ecb2421b5ddf ("netfilter: add and use nf_ct_netns_get/put")
>Reported-by: Jaroslav Aster <jaster@redhat.com>
>Signed-off-by: Xin Long <lucien.xin@gmail.com>
Acked-by: Jiri Pirko <jiri@mellanox.com>
^ permalink raw reply
* Re: [PATCH v3] iwlwifi: Demote messages about fw flags size to info
From: Coelho, Luciano @ 2017-08-08 8:21 UTC (permalink / raw)
To: linuxwifi, kvalo@codeaurora.org, jprvita@gmail.com,
Berg, Johannes, Grumbach, Emmanuel
Cc: linux-wireless@vger.kernel.org, linux@endlessm.com,
netdev@vger.kernel.org, jprvita@endlessm.com,
linux-kernel@vger.kernel.org
In-Reply-To: <20170803144728.32305-1-jprvita@endlessm.com>
On Thu, 2017-08-03 at 07:47 -0700, João Paulo Rechi Vita wrote:
> These messages are not reporting a real error, just the fact that the
> firmware knows about more flags than the driver.
>
> Currently these messages are presented to the user during boot if there
> is no bootsplash covering the console, even when booting the kernel with
> "quiet".
>
> Demoting it to the warn level helps having a clean boot process.
>
> Signed-off-by: João Paulo Rechi Vita <jprvita@endlessm.com>
> ---
>
> v2 changes:
> - Set to warn level instead of info
>
> v3 changes:
> - Fix commit message typo
Thanks, João Paulo! I pushed this to our internal tree and it will
eventually reach the mainline following our normal upstreaming process.
--
Cheers,
Luca.
^ permalink raw reply
* Re: [PATCH] ip/link_vti6.c: Fix local/remote any handling
From: Christian Langrock @ 2017-08-08 7:53 UTC (permalink / raw)
To: Stephen Hemminger; +Cc: netdev
In-Reply-To: <20170807081225.7cd10477@xeon-e3>
[-- Attachment #1.1.1: Type: text/plain, Size: 1908 bytes --]
This seems to be the better solution, at least because i missed the case
where the function is called to alter a VTI.
BR,
Christian
Am 07.08.2017 um 17:12 schrieb Stephen Hemminger:
> On Mon, 7 Aug 2017 08:41:23 +0200
> Christian Langrock <christian.langrock@secunet.com> wrote:
>
>> According to the IPv4 behavior of 'ip' it should be possible to omit the
>> arguments for local and remote address.
>> Without this patch omitting these parameters would lead to
>> uninitialized memory being interpreted as IPv6 addresses.
>>
>> Signed-off-by: Christian Langrock <christian.langrock@secunet.com>
> I don't like extra flag values. Why not just:
>
> diff --git a/ip/link_vti6.c b/ip/link_vti6.c
> index be4e33cee606..6ea1fc2306ce 100644
> --- a/ip/link_vti6.c
> +++ b/ip/link_vti6.c
> @@ -59,8 +59,8 @@ static int vti6_parse_opt(struct link_util *lu, int argc, char **argv,
> struct rtattr *tb[IFLA_MAX + 1];
> struct rtattr *linkinfo[IFLA_INFO_MAX+1];
> struct rtattr *vtiinfo[IFLA_VTI_MAX + 1];
> - struct in6_addr saddr;
> - struct in6_addr daddr;
> + struct in6_addr saddr = IN6ADDR_ANY_INIT;
> + struct in6_addr daddr = IN6ADDR_ANY_INIT;
> unsigned int ikey = 0;
> unsigned int okey = 0;
> unsigned int link = 0;
> @@ -195,8 +195,11 @@ get_failed:
>
> addattr32(n, 1024, IFLA_VTI_IKEY, ikey);
> addattr32(n, 1024, IFLA_VTI_OKEY, okey);
> - addattr_l(n, 1024, IFLA_VTI_LOCAL, &saddr, sizeof(saddr));
> - addattr_l(n, 1024, IFLA_VTI_REMOTE, &daddr, sizeof(daddr));
> +
> + if (memcmp(&saddr, &in6addr_any, sizeof(in6addr_any)))
> + addattr_l(n, 1024, IFLA_VTI_LOCAL, &saddr, sizeof(saddr));
> + if (memcmp(&daddr, &in6addr_any, sizeof(in6addr_any)))
> + addattr_l(n, 1024, IFLA_VTI_REMOTE, &daddr, sizeof(daddr));
> addattr32(n, 1024, IFLA_VTI_FWMARK, fwmark);
> if (link)
> addattr32(n, 1024, IFLA_VTI_LINK, link);
[-- Attachment #1.1.2: 0x82EB6B5E.asc --]
[-- Type: application/pgp-keys, Size: 1758 bytes --]
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 473 bytes --]
^ permalink raw reply
* Re: [RFC net-next] net: xfrm: support setting an output mark.
From: Steffen Klassert @ 2017-08-08 7:51 UTC (permalink / raw)
To: Lorenzo Colitti
Cc: netdev@vger.kernel.org, David Miller, Jamal Hadi Salim, herbert,
Nathan Harold, Jonathan Basseri
In-Reply-To: <CAKD1Yr2YXYed+vVgcyYo4XLAFXGjwwdSRucOmg+z2PVZD_A06Q@mail.gmail.com>
On Mon, Aug 07, 2017 at 10:34:37PM +0900, Lorenzo Colitti wrote:
> On Mon, Aug 7, 2017 at 8:16 PM, Steffen Klassert
> <steffen.klassert@secunet.com> wrote:
> > > XFRMA_OFFLOAD_DEV, /* struct xfrm_state_offload */
> > > + XFRMA_OUTPUT_MARK, /* __u32 */
> > > __XFRMA_MAX
> >
> > Hm, why don't you use the existing xfrm_mark for this?
> > Having two different marks on one SA seems to be a bit odd.
>
> I think using a separate mark is conceptually cleaner and much more flexible.
>
> The existing xfrm_mark is constrained to match the mark of the socket
> that sends the packet (or the unencrypted packet that is transformed).
> Specifically (at least if I'm reading the code correctly),
> xfrm_policy_match requires:
>
> (fl->flowi_mark & pol->mark.m) == pol->mark.v
>
> and xfrm_state_find requires:
>
> (mark & x->mark.m) == x->mark.v
>
> so basically the SA mark is a subset of the bits of the policy mark,
> which is a subset of the bits of sk_mark.
>
> On systems using mark-based routing (or at least on Android [1]), the
> mark decides how a packet is routed, and in order for things to work
> properly the routing of an IPsec tunnel should depend only on the
> tunnel configuration and not on the mark of any socket or any packet
> that is routed through that tunnel. The mark might select which tunnel
> to go through, and the output mark would decide how the tunnel packets
> are routed.
I thought you can just split the 32 bit mark into two 16 bit marks
by setting an appropriate mask at the xfrm and the routing mark.
But this has the drawback that the socket needs to know how possibly
tunneled packets should be routed.
>
> A real use case is IWLAN [2], which is used to connect to 3GPP
> networks over wifi. The phone has the same IP addresses on the
> cellular interface and on an IPsec tunnel to a carrier gateway (PDG).
> On Android, a socket connected on the carrier network through a native
> interface such as LTE will have the socket mark that's specific to the
> carrier network. If the device then hands over the carrier connection
> to the IPsec tunnel over wifi, the socket will still have the mark of
> the LTE interface. If we used xfrm_mark, then the tunneled packets
> themselves will be routed on LTE instead of being routed on wifi. That
> obviously defeats the purpose.
>
> Using XFRM_OUTPUT_MARK makes this much cleaner: the socket can
> continue to be marked with the carrier network's mark, and it's the
> IPsec tunnel itself that is bound to the wifi network using the mark
> in the SA.
So we transform the packet and may 'transform' the mark on the packet
too. This could make sense, but we have to point out the differences
between the xfrm_mark and the output_mark on the SA very explicit.
^ permalink raw reply
* [PATCHv3 net] net: sched: set xt_tgchk_param par.net properly in ipt_init_target
From: Xin Long @ 2017-08-08 7:25 UTC (permalink / raw)
To: network dev; +Cc: davem, Jiri Pirko, Cong Wang
Now xt_tgchk_param par in ipt_init_target is a local varibale,
par.net is not initialized there. Later when xt_check_target
calls target's checkentry in which it may access par.net, it
would cause kernel panic.
Jaroslav found this panic when running:
# ip link add TestIface type dummy
# tc qd add dev TestIface ingress handle ffff:
# tc filter add dev TestIface parent ffff: u32 match u32 0 0 \
action xt -j CONNMARK --set-mark 4
This patch is to pass net param into ipt_init_target and set
par.net with it properly in there.
v1->v2:
As Wang Cong pointed, I missed ipt_net_id != xt_net_id, so fix
it by also passing net_id to __tcf_ipt_init.
v2->v3:
Missed the fixes tag, so add it.
Fixes: ecb2421b5ddf ("netfilter: add and use nf_ct_netns_get/put")
Reported-by: Jaroslav Aster <jaster@redhat.com>
Signed-off-by: Xin Long <lucien.xin@gmail.com>
---
net/sched/act_ipt.c | 20 ++++++++++----------
1 file changed, 10 insertions(+), 10 deletions(-)
diff --git a/net/sched/act_ipt.c b/net/sched/act_ipt.c
index 36f0ced..94ba5cf 100644
--- a/net/sched/act_ipt.c
+++ b/net/sched/act_ipt.c
@@ -36,8 +36,8 @@ static struct tc_action_ops act_ipt_ops;
static unsigned int xt_net_id;
static struct tc_action_ops act_xt_ops;
-static int ipt_init_target(struct xt_entry_target *t, char *table,
- unsigned int hook)
+static int ipt_init_target(struct net *net, struct xt_entry_target *t,
+ char *table, unsigned int hook)
{
struct xt_tgchk_param par;
struct xt_target *target;
@@ -49,6 +49,7 @@ static int ipt_init_target(struct xt_entry_target *t, char *table,
return PTR_ERR(target);
t->u.kernel.target = target;
+ par.net = net;
par.table = table;
par.entryinfo = NULL;
par.target = target;
@@ -91,10 +92,11 @@ static const struct nla_policy ipt_policy[TCA_IPT_MAX + 1] = {
[TCA_IPT_TARG] = { .len = sizeof(struct xt_entry_target) },
};
-static int __tcf_ipt_init(struct tc_action_net *tn, struct nlattr *nla,
+static int __tcf_ipt_init(struct net *net, unsigned int id, struct nlattr *nla,
struct nlattr *est, struct tc_action **a,
const struct tc_action_ops *ops, int ovr, int bind)
{
+ struct tc_action_net *tn = net_generic(net, id);
struct nlattr *tb[TCA_IPT_MAX + 1];
struct tcf_ipt *ipt;
struct xt_entry_target *td, *t;
@@ -159,7 +161,7 @@ static int __tcf_ipt_init(struct tc_action_net *tn, struct nlattr *nla,
if (unlikely(!t))
goto err2;
- err = ipt_init_target(t, tname, hook);
+ err = ipt_init_target(net, t, tname, hook);
if (err < 0)
goto err3;
@@ -193,18 +195,16 @@ static int tcf_ipt_init(struct net *net, struct nlattr *nla,
struct nlattr *est, struct tc_action **a, int ovr,
int bind)
{
- struct tc_action_net *tn = net_generic(net, ipt_net_id);
-
- return __tcf_ipt_init(tn, nla, est, a, &act_ipt_ops, ovr, bind);
+ return __tcf_ipt_init(net, ipt_net_id, nla, est, a, &act_ipt_ops, ovr,
+ bind);
}
static int tcf_xt_init(struct net *net, struct nlattr *nla,
struct nlattr *est, struct tc_action **a, int ovr,
int bind)
{
- struct tc_action_net *tn = net_generic(net, xt_net_id);
-
- return __tcf_ipt_init(tn, nla, est, a, &act_xt_ops, ovr, bind);
+ return __tcf_ipt_init(net, xt_net_id, nla, est, a, &act_xt_ops, ovr,
+ bind);
}
static int tcf_ipt(struct sk_buff *skb, const struct tc_action *a,
--
2.1.0
^ permalink raw reply related
* Re: [PATCHv2 net] net: sched: set xt_tgchk_param par.net properly in ipt_init_target
From: Xin Long @ 2017-08-08 6:34 UTC (permalink / raw)
To: Jiri Pirko; +Cc: network dev, davem, Cong Wang
In-Reply-To: <20170808053021.GB1853@nanopsycho>
On Tue, Aug 8, 2017 at 5:30 PM, Jiri Pirko <jiri@resnulli.us> wrote:
> Tue, Aug 08, 2017 at 04:13:27AM CEST, lucien.xin@gmail.com wrote:
>>Now xt_tgchk_param par in ipt_init_target is a local varibale,
>>par.net is not initialized there. Later when xt_check_target
>>calls target's checkentry in which it may access par.net, it
>>would cause kernel panic.
>>
>>Jaroslav found this panic when running:
>>
>> # ip link add TestIface type dummy
>> # tc qd add dev TestIface ingress handle ffff:
>> # tc filter add dev TestIface parent ffff: u32 match u32 0 0 \
>> action xt -j CONNMARK --set-mark 4
>>
>>This patch is to pass net param into ipt_init_target and set
>>par.net with it properly in there.
>>
>>v1->v2:
>> As Wang Cong pointed, I missed ipt_net_id != xt_net_id, so fix
>> it by also passing net_id to __tcf_ipt_init.
>>
>>Reported-by: Jaroslav Aster <jaster@redhat.com>
>>Signed-off-by: Xin Long <lucien.xin@gmail.com>
>
> Fixes what? You need to have "Fixes" tag for net patches.
Fixes: ecb2421b5ddf ("netfilter: add and use nf_ct_netns_get/put")
Thanks, I will repost
^ permalink raw reply
* Re: [PATCH] net: Reduce skb_warn_bad_offload() noise.
From: Willem de Bruijn @ 2017-08-08 6:29 UTC (permalink / raw)
To: Tonghao Zhang
Cc: Eric Dumazet, Linux Kernel Network Developers, Eric Dumazet,
Willem de Bruijn, Pravin B Shelar
In-Reply-To: <CAMDZJNUyaXnVp7jAH-E_d-X__zikoa=-3ypHo64aOnqra7TbRw@mail.gmail.com>
> In a case, there is also warn info. The test topo is shown as below.
Thanks for testing the patch, Tonghao.
> The warn info is shown as below [1]. If we change the CHECKSUM_NONE to
> CHECKSUM_UNNECESSARY in the udp4_ufo_fragment().
> and we should add a check in skb_needs_check() when outputting a packet.
>
> diff --git a/net/core/dev.c b/net/core/dev.c
> index 416137c..8fe12a7 100644
> --- a/net/core/dev.c
> +++ b/net/core/dev.c
> @@ -2670,6 +2670,7 @@ static inline bool skb_needs_check(struct
> sk_buff *skb, bool tx_path)
> {
> if (tx_path)
> return skb->ip_summed != CHECKSUM_PARTIAL &&
> + skb->ip_summed != CHECKSUM_UNNECESSARY &&
> skb->ip_summed != CHECKSUM_NONE;
Good catch. Only, the CHECKSUM_NONE case was added specifically to
work around this UFO issue on the tx path in commit 6e7bc478c9a0
("net: skb_needs_check() accepts CHECKSUM_NONE for tx"). If we change
the value generated by UFO, we can remove that statement, so
+ skb->ip_summed != CHECKSUM_UNNECESSARY;
- skb->ip_summed != CHECKSUM_NONE;
Else the entire check becomes a NOOP. These are the only three valid
states on tx. With very few codepaths generating CHECKSUM_UNNECESSARY
to begin with, it arguably already is practically a NOOP. I need to
look more closely what the statement is intended to protect against,
before we relax it even further.
The patch will need the same UFO change in ipv6_ufo_fragment.
I also had to verify that it is indeed correct to use
CHECKSUM_UNNECESSARY for this case. It is not commonly used as alias
for CHECKSUM_NONE on the tx path. And indeed does not carry the exact
same meaning. It was defined as "no need to checksum" on tx for
protocols that skb_checksum_help does not support:
http://patchwork.ozlabs.org/patch/146567/
Given that, it should be fine to use in this case.
^ permalink raw reply
* Re: [PATCH] ip/link_vti*.c: Fix output for ikey/okey
From: Christian Langrock @ 2017-08-08 6:24 UTC (permalink / raw)
To: Stephen Hemminger; +Cc: netdev
In-Reply-To: <20170807153815.7acf5b93@xeon-e3>
[-- Attachment #1.1: Type: text/plain, Size: 3189 bytes --]
Using hex values sounds reasonable.
BR,
Christian
Updated Patch:
Subject: [PATCH] ip/link_vti*.c: Fix output for ikey/okey
ikey and okey are normal u32 values. There's no reason to print them as
IPv4/IPv6 addresses. Instead print them as hex values.
Signed-off-by: Christian Langrock <christian.langrock@secunet.com>
---
ip/link_vti.c | 10 ++++------
ip/link_vti6.c | 10 ++++------
2 files changed, 8 insertions(+), 12 deletions(-)
diff --git a/ip/link_vti.c b/ip/link_vti.c
index d5242ac..f87623b 100644
--- a/ip/link_vti.c
+++ b/ip/link_vti.c
@@ -244,14 +244,12 @@ static void vti_print_opt(struct link_util *lu,
FILE *f, struct rtattr *tb[])
fprintf(f, "dev %u ", link);
}
- if (tb[IFLA_VTI_IKEY]) {
- inet_ntop(AF_INET, RTA_DATA(tb[IFLA_VTI_IKEY]), s2,
sizeof(s2));
- fprintf(f, "ikey %s ", s2);
+ if (tb[IFLA_VTI_IKEY] && rta_getattr_u32(tb[IFLA_VTI_IKEY])) {
+ fprintf(f, "ikey 0x%x ",
ntohl(rta_getattr_u32(tb[IFLA_VTI_IKEY])));
}
- if (tb[IFLA_VTI_OKEY]) {
- inet_ntop(AF_INET, RTA_DATA(tb[IFLA_VTI_OKEY]), s2,
sizeof(s2));
- fprintf(f, "okey %s ", s2);
+ if (tb[IFLA_VTI_OKEY] && rta_getattr_u32(tb[IFLA_VTI_OKEY])) {
+ fprintf(f, "okey 0x%x ",
ntohl(rta_getattr_u32(tb[IFLA_VTI_OKEY])));
}
if (tb[IFLA_VTI_FWMARK] && rta_getattr_u32(tb[IFLA_VTI_FWMARK])) {
diff --git a/ip/link_vti6.c b/ip/link_vti6.c
index 220b7df..6ae87dd 100644
--- a/ip/link_vti6.c
+++ b/ip/link_vti6.c
@@ -247,14 +247,12 @@ static void vti6_print_opt(struct link_util *lu,
FILE *f, struct rtattr *tb[])
fprintf(f, "dev %u ", link);
}
- if (tb[IFLA_VTI_IKEY]) {
- inet_ntop(AF_INET, RTA_DATA(tb[IFLA_VTI_IKEY]), s2,
sizeof(s2));
- fprintf(f, "ikey %s ", s2);
+ if (tb[IFLA_VTI_IKEY] && rta_getattr_u32(tb[IFLA_VTI_IKEY])) {
+ fprintf(f, "ikey %u ",
ntohl(rta_getattr_u32(tb[IFLA_VTI_IKEY])));
}
- if (tb[IFLA_VTI_OKEY]) {
- inet_ntop(AF_INET, RTA_DATA(tb[IFLA_VTI_OKEY]), s2,
sizeof(s2));
- fprintf(f, "okey %s ", s2);
+ if (tb[IFLA_VTI_OKEY] && rta_getattr_u32(tb[IFLA_VTI_OKEY])) {
+ fprintf(f, "okey %u ",
ntohl(rta_getattr_u32(tb[IFLA_VTI_OKEY])));
}
if (tb[IFLA_VTI_FWMARK] && rta_getattr_u32(tb[IFLA_VTI_FWMARK])) {
--
2.7.4
Am 08.08.2017 um 00:38 schrieb Stephen Hemminger:
> On Mon, 7 Aug 2017 11:59:28 +0200
> Christian Langrock <christian.langrock@secunet.com> wrote:
>
>> ikey and okey are normal u32 values. There's no reason to print them as
>> IPv4/IPv6 addresses.
>>
>> Signed-off-by: Christian Langrock <christian.langrock@secunet.com>
> Changing output format breaks scripts that parse output.
> But on the other hand, the VTI code breaks the assumption that ip command
> output should be the same as input.
>
> More likely the original output format was done to match Cisco output.
>
>
> Why not print in hex like fwmark?
>
>
>
>
>
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 473 bytes --]
^ permalink raw reply related
* Re: [PATCH 0/6] In-kernel QMI handling
From: Marcel Holtmann @ 2017-08-08 6:15 UTC (permalink / raw)
To: Bjorn Andersson
Cc: Dan Williams, David S. Miller, Andy Gross, David Brown,
linux-arm-msm, linux-soc, Netdev list, linux-kernel
In-Reply-To: <20170808044507.GJ29306@minitux>
Hi Bjorn,
>>>>> This series starts by moving the common definitions of the QMUX
>>>>> protocol to the
>>>>> uapi header, as they are shared with clients - both in kernel and
>>>>> userspace.
>>>>>
>>>>> This series then introduces in-kernel helper functions for aiding the
>>>>> handling
>>>>> of QMI encoded messages in the kernel. QMI encoding is a wire-format
>>>>> used in
>>>>> exchanging messages between the majority of QRTR clients and
>>>>> services.
>>>>
>>>> This raises a few red-flags for me.
>>>
>>> I'm glad it does. In discussions with the responsible team within
>>> Qualcomm I've highlighted a number of concerns about enabling this
>>> support in the kernel. Together we're continuously looking into what
>>> should be pushed out to user space, and trying to not introduce
>>> unnecessary new users.
>>>
>>>> So far, we've kept almost everything QMI related in userspace and
>>>> handled all QMI control-channel messages from libraries like libqmi or
>>>> uqmi via the cdc-wdm driver and the "rmnet" interface via the qmi_wwan
>>>> driver. The kernel drivers just serve as the transport.
>>>>
>>>
>>> The path that was taken to support the MSM-style devices was to
>>> implement net/qrtr, which exposes a socket interface to abstract the
>>> physical transports (QMUX or IPCROUTER in Qualcomm terminology).
>>>
>>> As I share you view on letting the kernel handle the transportation only
>>> the task of keeping track of registered services (service id -> node and
>>> port mapping) was done in a user space process and so far we've only
>>> ever have to deal with QMI encoded messages in various user space tools.
>>
>> I think that the transport and multiplexing can be in the kernel as
>> long as it is done as proper subsystem. Similar to Phonet or CAIF.
>> Meaning it should have a well defined socket interface that can be
>> easily used from userspace, but also a clean in-kernel interface
>> handling.
>>
>
> In a mobile Qualcomm device there's a few different components involved
> here: message routing, QMUX protocol and QMI-encoding.
>
> The downstream Qualcomm kernel implements the two first in the
> IPCROUTER, upstream this is split between the kernel net/qrtr and a user
> space service-register implementing the QMUX protocol for knowing where
> services are located.
as long as all of QMUX moves into the kernel and userspace doesn’t need to know about QMUX anymore, that would be good. The cross termination of QMUX in kernel space and userspace is a really bad idea. It is even worse if userspace has to do service registration. That is just a recipe for disaster.
One extra thing to keep in mind is that all the USB dongle should register with such a new QMI subsystem. And have their network interfaces being proper children of the QMI node. And please do not forget QMI passthrough via MBIM. Just saying we move some QMUX code into the kernel is not enough. It really needs to be a proper subsystem with a proper hierarchy of the child devices.
> The common encoding of messages passed between endpoints of the message
> routing is QMI, which is made an affair totally that of each client.
>
>> If Qualcomm is supportive of this effort and is willing to actually
>> assist and/or open some of the specs or interface descriptions, then
>> this is a good thing. Service registration and cleanup is really done
>> best in the kernel. Same applies to multiplexing. Trying to do
>> multiplexing in userspace is always cumbersome and leads to overhead
>> that is of no gain. For example within oFono, we had to force
>> everything to go via oFono since it was the only sane way of handling
>> it. Other approaches were error prone and full of race conditions. You
>> need a central entity that can clean up.
>>
>
> The current upstream solution depends on a collaboration between
> net/qrtr and the user space service register for figuring out whom to
> send messages to. After that muxing et al is handled by the socket
> interface and service registry does not need to be involved.
>
> Qualcomm is very supporting of this solution and we're collaborating on
> transitioning "downstream" to use this implementation.
It would be good if someone looks into oFono and makes sure that it works there as well. I would prefer at least some initial patches to proof-point the kernel APIs. oFono is a full telephony stack. So if you can make that one work, then you are most likely on the right track.
>> For the definition of an UAPI to share some code, I am actually not
>> sure that is such a good idea. For example the QMI code in oFono
>> follows a way simpler approach. And I am not convinced that all the
>> macros are actually beneficial. For example, the whole netlink macros
>> are pretty cumbersome. Adding some Documentation/qmi.txt on how the
>> wire format looks like and what is expected seems to be a way better
>> approach.
>>
>
> The socket interface provided by the kernel expects some knowledge of
> the QMUX protocol, for service management. The majority of this
> knowledge is already public, but I agree that it would be good to gather
> this in a document. The common data structure for the control message is
> what I've put in the uapi, as this is used by anyone dealing with
> control messages.
>
> When it comes to the QMI-encoded messages these are application
> specific, just like e.g. protobuf definitions are application specific.
That is fine, but what I like to see is at least a documentation that clearly documents the boundaries and examples on how the socket interface is suppose to use. For example using DMS to get the model id etc. would be a simple enough example that could be easily added.
> As the core infrastructure is becoming available upstream and boards
> like the DB410c and DB820c aim to be supported by open solutions we will
> have a natural place to discuss publication of at least some of the
> application level protocols.
I would really welcome public documentation of it. That would be great.
Regards
Marcel
^ permalink raw reply
* [PATCH net-next] cxgb4: Clear On FLASH config file after a FW upgrade
From: Ganesh Goudar @ 2017-08-08 5:50 UTC (permalink / raw)
To: netdev, davem
Cc: nirranjan, indranil, venkatesh, leedom, Arjun Vynipadath,
Ganesh Goudar
From: Arjun Vynipadath <arjun@chelsio.com>
Because Firmware and the Firmware Configuration File need to be
in sync; clear out any On-FLASH Firmware Configuration File when new
Firmware is loaded. This will avoid difficult to diagnose and fix
problems with a mis-matched Firmware Configuration File which prevents the
adapter from being initialized.
Original work by: Casey Leedom <leedom@chelsio.com>
Signed-off-by: Arjun Vynipadath <arjun@chelsio.com>
Signed-off-by: Ganesh Goudar <ganeshgr@chelsio.com>
---
drivers/net/ethernet/chelsio/cxgb4/cxgb4.h | 1 +
drivers/net/ethernet/chelsio/cxgb4/t4_hw.c | 70 ++++++++++++++++++++++++++++++
2 files changed, 71 insertions(+)
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h b/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
index 1978abb..daa3775 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
+++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
@@ -1405,6 +1405,7 @@ int t4_fw_upgrade(struct adapter *adap, unsigned int mbox,
int t4_fl_pkt_align(struct adapter *adap);
unsigned int t4_flash_cfg_addr(struct adapter *adapter);
int t4_check_fw_version(struct adapter *adap);
+int t4_load_cfg(struct adapter *adapter, const u8 *cfg_data, unsigned int size);
int t4_get_fw_version(struct adapter *adapter, u32 *vers);
int t4_get_bs_version(struct adapter *adapter, u32 *vers);
int t4_get_tp_version(struct adapter *adapter, u32 *vers);
diff --git a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
index 24087c8..fff8fba 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
+++ b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
@@ -6664,6 +6664,17 @@ int t4_fw_upgrade(struct adapter *adap, unsigned int mbox,
goto out;
/*
+ * If there was a Firmware Configuration File stored in FLASH,
+ * there's a good chance that it won't be compatible with the new
+ * Firmware. In order to prevent difficult to diagnose adapter
+ * initialization issues, we clear out the Firmware Configuration File
+ * portion of the FLASH . The user will need to re-FLASH a new
+ * Firmware Configuration File which is compatible with the new
+ * Firmware if that's desired.
+ */
+ (void)t4_load_cfg(adap, NULL, 0);
+
+ /*
* Older versions of the firmware don't understand the new
* PCIE_FW.HALT flag and so won't know to perform a RESET when they
* restart. So for newly loaded older firmware we'll have to do the
@@ -8896,6 +8907,65 @@ void t4_idma_monitor(struct adapter *adapter,
}
/**
+ * t4_load_cfg - download config file
+ * @adap: the adapter
+ * @cfg_data: the cfg text file to write
+ * @size: text file size
+ *
+ * Write the supplied config text file to the card's serial flash.
+ */
+int t4_load_cfg(struct adapter *adap, const u8 *cfg_data, unsigned int size)
+{
+ int ret, i, n, cfg_addr;
+ unsigned int addr;
+ unsigned int flash_cfg_start_sec;
+ unsigned int sf_sec_size = adap->params.sf_size / adap->params.sf_nsec;
+
+ cfg_addr = t4_flash_cfg_addr(adap);
+ if (cfg_addr < 0)
+ return cfg_addr;
+
+ addr = cfg_addr;
+ flash_cfg_start_sec = addr / SF_SEC_SIZE;
+
+ if (size > FLASH_CFG_MAX_SIZE) {
+ dev_err(adap->pdev_dev, "cfg file too large, max is %u bytes\n",
+ FLASH_CFG_MAX_SIZE);
+ return -EFBIG;
+ }
+
+ i = DIV_ROUND_UP(FLASH_CFG_MAX_SIZE, /* # of sectors spanned */
+ sf_sec_size);
+ ret = t4_flash_erase_sectors(adap, flash_cfg_start_sec,
+ flash_cfg_start_sec + i - 1);
+ /* If size == 0 then we're simply erasing the FLASH sectors associated
+ * with the on-adapter Firmware Configuration File.
+ */
+ if (ret || size == 0)
+ goto out;
+
+ /* this will write to the flash up to SF_PAGE_SIZE at a time */
+ for (i = 0; i < size; i += SF_PAGE_SIZE) {
+ if ((size - i) < SF_PAGE_SIZE)
+ n = size - i;
+ else
+ n = SF_PAGE_SIZE;
+ ret = t4_write_flash(adap, addr, n, cfg_data);
+ if (ret)
+ goto out;
+
+ addr += SF_PAGE_SIZE;
+ cfg_data += SF_PAGE_SIZE;
+ }
+
+out:
+ if (ret)
+ dev_err(adap->pdev_dev, "config file %s failed %d\n",
+ (size == 0 ? "clear" : "download"), ret);
+ return ret;
+}
+
+/**
* t4_set_vf_mac - Set MAC address for the specified VF
* @adapter: The adapter
* @vf: one of the VFs instantiated by the specified PF
--
2.1.0
^ permalink raw reply related
* Re: [PATCHv2 net] net: sched: set xt_tgchk_param par.net properly in ipt_init_target
From: Jiri Pirko @ 2017-08-08 5:30 UTC (permalink / raw)
To: Xin Long; +Cc: network dev, davem, Cong Wang
In-Reply-To: <5ac3422182618f34f24d0c52cfa8f922ea7c397e.1502158407.git.lucien.xin@gmail.com>
Tue, Aug 08, 2017 at 04:13:27AM CEST, lucien.xin@gmail.com wrote:
>Now xt_tgchk_param par in ipt_init_target is a local varibale,
>par.net is not initialized there. Later when xt_check_target
>calls target's checkentry in which it may access par.net, it
>would cause kernel panic.
>
>Jaroslav found this panic when running:
>
> # ip link add TestIface type dummy
> # tc qd add dev TestIface ingress handle ffff:
> # tc filter add dev TestIface parent ffff: u32 match u32 0 0 \
> action xt -j CONNMARK --set-mark 4
>
>This patch is to pass net param into ipt_init_target and set
>par.net with it properly in there.
>
>v1->v2:
> As Wang Cong pointed, I missed ipt_net_id != xt_net_id, so fix
> it by also passing net_id to __tcf_ipt_init.
>
>Reported-by: Jaroslav Aster <jaster@redhat.com>
>Signed-off-by: Xin Long <lucien.xin@gmail.com>
Fixes what? You need to have "Fixes" tag for net patches.
^ permalink raw reply
* Re: [Patch net-next] net_sched: get rid of some forward declarations
From: Jiri Pirko @ 2017-08-08 5:28 UTC (permalink / raw)
To: Cong Wang; +Cc: netdev, Jamal Hadi Salim
In-Reply-To: <20170807222650.16561-1-xiyou.wangcong@gmail.com>
Tue, Aug 08, 2017 at 12:26:50AM CEST, xiyou.wangcong@gmail.com wrote:
>If we move up tcf_fill_node() we can get rid of these
>forward declarations.
>
>Also, move down tfilter_notify_chain() to group them together.
>
>Reported-by: Jamal Hadi Salim <jhs@mojatatu.com>
>Cc: Jamal Hadi Salim <jhs@mojatatu.com>
>Signed-off-by: Cong Wang <xiyou.wangcong@gmail.com>
Acked-by: Jiri Pirko <jiri@mellanox.com>
^ permalink raw reply
* Re: [PATCH] net: Reduce skb_warn_bad_offload() noise.
From: Tonghao Zhang @ 2017-08-08 5:26 UTC (permalink / raw)
To: Willem de Bruijn
Cc: Eric Dumazet, Linux Kernel Network Developers, Eric Dumazet,
Willem de Bruijn, Pravin B Shelar
In-Reply-To: <CAMDZJNVRqbByUfa5Oc_=xs+O_BJ4ehUJUSz9Y+wCPwj6kQGtLA@mail.gmail.com>
Hi Willem
In a case, there is also warn info. The test topo is shown as below.
VM01: veth1 and eth0 in the VM01 are inserted to ovs br0.
veth0(IP: 172.16.34.100/24) —— veth1--br0--eth0
iperf3 -c 172.168.100.13 -i 1 -P 10 -t 10 -u -b 1000M -l 10K
VM02
eth0(IP: 172.16.34.200/24)
iperf3 -s
The warn info is shown as below [1]. If we change the CHECKSUM_NONE to
CHECKSUM_UNNECESSARY in the udp4_ufo_fragment().
and we should add a check in skb_needs_check() when outputting a packet.
diff --git a/net/core/dev.c b/net/core/dev.c
index 416137c..8fe12a7 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2670,6 +2670,7 @@ static inline bool skb_needs_check(struct
sk_buff *skb, bool tx_path)
{
if (tx_path)
return skb->ip_summed != CHECKSUM_PARTIAL &&
+ skb->ip_summed != CHECKSUM_UNNECESSARY &&
skb->ip_summed != CHECKSUM_NONE;
return skb->ip_summed == CHECKSUM_NONE;
diff --git a/net/ipv4/udp_offload.c b/net/ipv4/udp_offload.c
index 7812501..0932c85 100644
--- a/net/ipv4/udp_offload.c
+++ b/net/ipv4/udp_offload.c
@@ -235,7 +235,7 @@ static struct sk_buff *udp4_ufo_fragment(struct
sk_buff *skb,
if (uh->check == 0)
uh->check = CSUM_MANGLED_0;
- skb->ip_summed = CHECKSUM_NONE;
+ skb->ip_summed = CHECKSUM_UNNECESSARY;
/* If there is no outer header we can fake a checksum offload
* due to the fact that we have already done the checksum in
[1]:
[ 1291.596232] vmxnet3: caps=(0x0000006000214ba9, 0x0000000000000000)
len=10282 data_len=10240 gso_size=1480 gso_type=2 ip_summed=1
[ 1291.596239] ------------[ cut here ]------------
[ 1291.596242] WARNING: CPU: 1 PID: 2203 at net/core/dev.c:2564
skb_warn_bad_offload+0xd3/0xde
[ 1291.596242] Modules linked in: veth udp_tunnel gre openvswitch
nf_conntrack_ipv6 nf_nat_ipv6 nf_conntrack_ipv4 nf_defrag_ipv4
nf_nat_ipv4 nf_defrag_ipv6 nf_nat nf_conntrack cfg80211 rfkill ext4
jbd2 mbcache sb_edac coretemp crct10dif_pclmul crc32_pclmul
ghash_clmulni_intel pcbc aesni_intel crypto_simd glue_helper ppdev
vmw_balloon cryptd vmw_vmci sg i2c_piix4 pcspkr parport_pc parport
shpchp ip_tables xfs libcrc32c sd_mod ata_generic pata_acpi vmwgfx
drm_kms_helper syscopyarea sysfillrect sysimgblt fb_sys_fops ttm drm
crc32c_intel serio_raw vmxnet3 ata_piix mptspi libata
scsi_transport_spi mptscsih mptbase i2c_core floppy dm_mirror
dm_region_hash dm_log dm_mod
[ 1291.596280] CPU: 1 PID: 2203 Comm: iperf3 Tainted: G W
4.12.0+ #1
[ 1291.596280] Hardware name: VMware, Inc. VMware Virtual
Platform/440BX Desktop Reference Platform, BIOS 6.00 09/21/2015
[ 1291.596281] task: ffff8be36f5e9680 task.stack: ffffb6c840d44000
[ 1291.596283] RIP: 0010:skb_warn_bad_offload+0xd3/0xde
[ 1291.596284] RSP: 0018:ffff8be3796438c8 EFLAGS: 00010246
[ 1291.596285] RAX: 0000000000000074 RBX: ffff8be363ff9f00 RCX: 0000000000000006
[ 1291.596286] RDX: 0000000000000000 RSI: 0000000000000086 RDI: ffff8be37964e0a0
[ 1291.596287] RBP: ffff8be3796438f0 R08: 0000000000000000 R09: 0000000000000bf2
[ 1291.596287] R10: 0000000000000004 R11: 0000000000000bf1 R12: ffff8be3660f0000
[ 1291.596288] R13: 0000000000000001 R14: 0000000000000000 R15: ffff8be3660f0000
[ 1291.596289] FS: 00007f8d93bdb740(0000) GS:ffff8be379640000(0000)
knlGS:0000000000000000
[ 1291.596290] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[ 1291.596291] CR2: 0000555f94a6e0c8 CR3: 000000012b84a000 CR4: 00000000001406e0
[ 1291.596296] Call Trace:
[ 1291.596297] <IRQ>
[ 1291.596300] __skb_gso_segment+0x15d/0x170
[ 1291.596301] validate_xmit_skb+0x12d/0x2b0
[ 1291.596303] validate_xmit_skb_list+0x42/0x70
[ 1291.596306] sch_direct_xmit+0xd0/0x1b0
[ 1291.596308] __dev_queue_xmit+0x42e/0x630
[ 1291.596310] ? hrtimer_interrupt+0xd2/0x1a0
[ 1291.596312] dev_queue_xmit+0x10/0x20
[ 1291.596315] ovs_vport_send+0xc2/0x150 [openvswitch]
[ 1291.596318] do_output+0x53/0xf0 [openvswitch]
[ 1291.596322] do_execute_actions+0x9bc/0x9d0 [openvswitch]
[ 1291.596324] ? __bpf_prog_run+0x385/0x1310
[ 1291.596327] ovs_execute_actions+0x40/0x120 [openvswitch]
[ 1291.596330] ovs_dp_process_packet+0x84/0x120 [openvswitch]
[ 1291.596333] ? ovs_ct_update_key+0x9a/0xe0 [openvswitch]
[ 1291.596336] ovs_vport_receive+0x73/0xd0 [openvswitch]
[ 1291.596339] ? handle_irq_event_percpu+0x54/0x80
[ 1291.596340] ? handle_irq_event+0x46/0x60
[ 1291.596342] ? handle_edge_irq+0x8d/0x130
[ 1291.596344] ? handle_irq+0xab/0x120
[ 1291.596346] ? irq_exit+0x77/0xf0
[ 1291.596348] ? do_IRQ+0x51/0xd0
[ 1291.596352] netdev_frame_hook+0xd3/0x160 [openvswitch]
[ 1291.596355] __netif_receive_skb_core+0x1da/0x9e0
[ 1291.596358] ? vport_netdev_free+0x30/0x30 [openvswitch]
[ 1291.596360] ? kfree_skbmem+0x5a/0x60
[ 1291.596361] ? consume_skb+0x34/0x90
[ 1291.596363] __netif_receive_skb+0x18/0x60
[ 1291.596365] process_backlog+0x95/0x140
[ 1291.596367] net_rx_action+0x26c/0x3b0
[ 1291.596369] __do_softirq+0xc9/0x269
[ 1291.596371] do_softirq_own_stack+0x1c/0x30
[ 1291.596372] </IRQ>
[ 1291.596374] do_softirq+0x50/0x60
[ 1291.596375] __local_bh_enable_ip+0x5a/0x70
[ 1291.596377] ip_finish_output2+0x15e/0x390
[ 1291.596380] ip_finish_output+0x136/0x1e0
[ 1291.596382] ip_output+0x76/0xe0
[ 1291.596384] ? ip_fragment.constprop.53+0x80/0x80
[ 1291.596386] ip_local_out+0x35/0x40
[ 1291.596387] ip_send_skb+0x19/0x40
[ 1291.596390] udp_send_skb+0x172/0x280
[ 1291.596391] udp_sendmsg+0x2cf/0xa60
[ 1291.596393] ? ip_reply_glue_bits+0x50/0x50
[ 1291.596396] ? sock_has_perm+0x75/0x90
[ 1291.596398] inet_sendmsg+0x31/0xb0
[ 1291.596399] sock_sendmsg+0x38/0x50
[ 1291.596401] sock_write_iter+0x85/0xf0
[ 1291.596403] __vfs_write+0xe3/0x160
[ 1291.596405] vfs_write+0xb2/0x1b0
[ 1291.596407] ? syscall_trace_enter+0x1d0/0x2b0
[ 1291.596408] SyS_write+0x55/0xc0
[ 1291.596411] do_syscall_64+0x67/0x150
[ 1291.596412] entry_SYSCALL64_slow_path+0x25/0x25
[ 1291.596413] RIP: 0033:0x7f8d931cdc60
[ 1291.596414] RSP: 002b:00007ffc0790e9c8 EFLAGS: 00000246 ORIG_RAX:
0000000000000001
[ 1291.596415] RAX: ffffffffffffffda RBX: 0000000000002800 RCX: 00007f8d931cdc60
[ 1291.596417] RDX: 0000000000002800 RSI: 00007f8d93bc9000 RDI: 0000000000000012
[ 1291.596417] RBP: 00007f8d93bc9000 R08: 0000000000000000 R09: 000000000000003d
[ 1291.596418] R10: 0000000000000001 R11: 0000000000000246 R12: 0000000000000012
[ 1291.596419] R13: 0000000000002800 R14: 0000000000000001 R15: 00007ffc0790ea40
[ 1291.596420] Code: 8d 94 24 d0 00 00 00 48 0f 44 ce 4d 85 e4 44 89
54 24 08 48 0f 44 d6 89 3c 24 48 89 c6 48 c7 c7 80 65 ac 8f 31 c0 e8
a7 bd a5 ff <0f> ff 48 83 c4 18 5b 41 5c 5d c3 55 48 89 f2 31 c0 89 fe
48 c7
[ 1291.596447] ---[ end trace b66534f41f98ceda ]---
On Tue, Aug 8, 2017 at 7:44 AM, Tonghao Zhang <xiangxia.m.yue@gmail.com> wrote:
> That is fine to me. I have tested it. Thanks.
>
> On Mon, Aug 7, 2017 at 12:42 PM, Willem de Bruijn
> <willemdebruijn.kernel@gmail.com> wrote:
>>> The openvswitch kernel module calls the __skb_gso_segment()(and sets
>>> tx_path = false) when passing packets to userspace. The UFO will set
>>> the ip_summed to CHECKSUM_NONE. There are a lot of warn logs. The warn
>>> log is shown as below. I guess we should revert the patch.
>>
>> Indeed, the software UFO code computes the checksum and
>> sets ip_summed to CHECKSUM_NONE, as is correct on the
>> egress path.
>>
>> Commit 6e7bc478c9a0 ("net: skb_needs_check() accepts
>> CHECKSUM_NONE for tx") revised the tx_path case in
>> skb_needs_check to avoid the warning exactly for the UFO case.
>>
>> We cannot just make an exception for CHECKSUM_NONE in the
>> !tx_path case, as the entire statement then becomes false:
>>
>> return skb->ip_summed == CHECKSUM_NONE;
>>
>> Since on egress CHECKSUM_UNNECESSARY is equivalent to
>> CHECKSUM_NONE, it should be fine to update the UFO code
>> to set that, instead:
>>
>> @@ -235,7 +235,7 @@ static struct sk_buff *udp4_ufo_fragment(struct
>> sk_buff *skb,
>> if (uh->check == 0)
>> uh->check = CSUM_MANGLED_0;
>>
>> - skb->ip_summed = CHECKSUM_NONE;
>> + skb->ip_summed = CHECKSUM_UNNECESSARY;
^ permalink raw reply related
* [PATCH net-next] openvswitch: add NSH support
From: Yi Yang @ 2017-08-08 4:59 UTC (permalink / raw)
To: netdev; +Cc: dev, jbenc, davem, Yi Yang
OVS master and 2.8 branch has merged NSH userspace
patch series, this patch is to enable NSH support
in kernel data path in order that OVS can support
NSH in 2.8 release in compat mode by porting this.
Signed-off-by: Yi Yang <yi.y.yang@intel.com>
---
drivers/net/vxlan.c | 7 ++
include/net/nsh.h | 126 ++++++++++++++++++++++++++++++
include/uapi/linux/openvswitch.h | 33 ++++++++
net/openvswitch/actions.c | 165 +++++++++++++++++++++++++++++++++++++++
net/openvswitch/flow.c | 41 ++++++++++
net/openvswitch/flow.h | 1 +
net/openvswitch/flow_netlink.c | 54 ++++++++++++-
7 files changed, 426 insertions(+), 1 deletion(-)
create mode 100644 include/net/nsh.h
diff --git a/drivers/net/vxlan.c b/drivers/net/vxlan.c
index dbca067..843714c 100644
--- a/drivers/net/vxlan.c
+++ b/drivers/net/vxlan.c
@@ -27,6 +27,7 @@
#include <net/net_namespace.h>
#include <net/netns/generic.h>
#include <net/vxlan.h>
+#include <net/nsh.h>
#if IS_ENABLED(CONFIG_IPV6)
#include <net/ip6_tunnel.h>
@@ -1267,6 +1268,9 @@ static bool vxlan_parse_gpe_hdr(struct vxlanhdr *unparsed,
case VXLAN_GPE_NP_IPV6:
*protocol = htons(ETH_P_IPV6);
break;
+ case VXLAN_GPE_NP_NSH:
+ *protocol = htons(ETH_P_NSH);
+ break;
case VXLAN_GPE_NP_ETHERNET:
*protocol = htons(ETH_P_TEB);
break;
@@ -1806,6 +1810,9 @@ static int vxlan_build_gpe_hdr(struct vxlanhdr *vxh, u32 vxflags,
case htons(ETH_P_IPV6):
gpe->next_protocol = VXLAN_GPE_NP_IPV6;
return 0;
+ case htons(ETH_P_NSH):
+ gpe->next_protocol = VXLAN_GPE_NP_NSH;
+ return 0;
case htons(ETH_P_TEB):
gpe->next_protocol = VXLAN_GPE_NP_ETHERNET;
return 0;
diff --git a/include/net/nsh.h b/include/net/nsh.h
new file mode 100644
index 0000000..96477a1
--- /dev/null
+++ b/include/net/nsh.h
@@ -0,0 +1,126 @@
+#ifndef __NET_NSH_H
+#define __NET_NSH_H 1
+
+
+/*
+ * Network Service Header:
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * |Ver|O|C|R|R|R|R|R|R| Length | MD Type | Next Proto |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | Service Path ID | Service Index |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * | |
+ * ~ Mandatory/Optional Context Header ~
+ * | |
+ * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+ * Ver = The version field is used to ensure backward compatibility
+ * going forward with future NSH updates. It MUST be set to 0x0
+ * by the sender, in this first revision of NSH.
+ *
+ * O = OAM. when set to 0x1 indicates that this packet is an operations
+ * and management (OAM) packet. The receiving SFF and SFs nodes
+ * MUST examine the payload and take appropriate action.
+ *
+ * C = context. Indicates that a critical metadata TLV is present.
+ *
+ * Length : total length, in 4-byte words, of NSH including the Base
+ * Header, the Service Path Header and the optional variable
+ * TLVs.
+ * MD Type: indicates the format of NSH beyond the mandatory Base Header
+ * and the Service Path Header.
+ *
+ * Next Protocol: indicates the protocol type of the original packet. A
+ * new IANA registry will be created for protocol type.
+ *
+ * Service Path Identifier (SPI): identifies a service path.
+ * Participating nodes MUST use this identifier for Service
+ * Function Path selection.
+ *
+ * Service Index (SI): provides location within the SFP.
+ *
+ * [0] https://tools.ietf.org/html/draft-ietf-sfc-nsh-13
+ */
+
+/**
+ * struct nsh_md1_ctx - Keeps track of NSH context data
+ * @nshc<1-4>: NSH Contexts.
+ */
+struct nsh_md1_ctx {
+ __be32 c[4];
+};
+
+struct nsh_md2_tlv {
+ __be16 md_class;
+ u8 type;
+ u8 length;
+ u8 md_value[];
+};
+
+struct nsh_hdr {
+ __be16 ver_flags_len;
+ u8 md_type;
+ u8 next_proto;
+ __be32 path_hdr;
+ union {
+ struct nsh_md1_ctx md1;
+ struct nsh_md2_tlv md2[0];
+ };
+};
+
+/* Masking NSH header fields. */
+#define NSH_VER_MASK 0xc000
+#define NSH_VER_SHIFT 14
+#define NSH_FLAGS_MASK 0x3fc0
+#define NSH_FLAGS_SHIFT 6
+#define NSH_LEN_MASK 0x003f
+#define NSH_LEN_SHIFT 0
+
+#define NSH_SPI_MASK 0xffffff00
+#define NSH_SPI_SHIFT 8
+#define NSH_SI_MASK 0x000000ff
+#define NSH_SI_SHIFT 0
+
+#define NSH_DST_PORT 4790 /* UDP Port for NSH on VXLAN. */
+#define ETH_P_NSH 0x894F /* Ethertype for NSH. */
+
+/* NSH Base Header Next Protocol. */
+#define NSH_P_IPV4 0x01
+#define NSH_P_IPV6 0x02
+#define NSH_P_ETHERNET 0x03
+#define NSH_P_NSH 0x04
+#define NSH_P_MPLS 0x05
+
+/* MD Type Registry. */
+#define NSH_M_TYPE1 0x01
+#define NSH_M_TYPE2 0x02
+#define NSH_M_EXP1 0xFE
+#define NSH_M_EXP2 0xFF
+
+/* NSH Metadata Length. */
+#define NSH_M_TYPE1_MDLEN 16
+
+/* NSH Base Header Length */
+#define NSH_BASE_HDR_LEN 8
+
+/* NSH MD Type 1 header Length. */
+#define NSH_M_TYPE1_LEN 24
+
+static inline u16
+nsh_hdr_len(const struct nsh_hdr *nsh)
+{
+ return 4 * (ntohs(nsh->ver_flags_len) & NSH_LEN_MASK) >> NSH_LEN_SHIFT;
+}
+
+static inline struct nsh_md1_ctx *
+nsh_md1_ctx(struct nsh_hdr *nsh)
+{
+ return &nsh->md1;
+}
+
+static inline struct nsh_md2_tlv *
+nsh_md2_ctx(struct nsh_hdr *nsh)
+{
+ return nsh->md2;
+}
+
+#endif /* __NET_NSH_H */
diff --git a/include/uapi/linux/openvswitch.h b/include/uapi/linux/openvswitch.h
index 156ee4c..b9c072c 100644
--- a/include/uapi/linux/openvswitch.h
+++ b/include/uapi/linux/openvswitch.h
@@ -333,6 +333,7 @@ enum ovs_key_attr {
OVS_KEY_ATTR_CT_LABELS, /* 16-octet connection tracking label */
OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV4, /* struct ovs_key_ct_tuple_ipv4 */
OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV6, /* struct ovs_key_ct_tuple_ipv6 */
+ OVS_KEY_ATTR_NSH, /* struct ovs_key_nsh */
#ifdef __KERNEL__
OVS_KEY_ATTR_TUNNEL_INFO, /* struct ip_tunnel_info */
@@ -491,6 +492,15 @@ struct ovs_key_ct_tuple_ipv6 {
__u8 ipv6_proto;
};
+struct ovs_key_nsh {
+ __u8 flags;
+ __u8 mdtype;
+ __u8 np;
+ __u8 pad;
+ __be32 path_hdr;
+ __be32 c[4];
+};
+
/**
* enum ovs_flow_attr - attributes for %OVS_FLOW_* commands.
* @OVS_FLOW_ATTR_KEY: Nested %OVS_KEY_ATTR_* attributes specifying the flow
@@ -769,6 +779,25 @@ struct ovs_action_push_eth {
struct ovs_key_ethernet addresses;
};
+#define OVS_ENCAP_NSH_MAX_MD_LEN 16
+/*
+ * struct ovs_action_encap_nsh - %OVS_ACTION_ATTR_ENCAP_NSH
+ * @flags: NSH header flags.
+ * @mdtype: NSH metadata type.
+ * @mdlen: Length of NSH metadata in bytes.
+ * @np: NSH next_protocol: Inner packet type.
+ * @path_hdr: NSH service path id and service index.
+ * @metadata: NSH metadata for MD type 1 or 2
+ */
+struct ovs_action_encap_nsh {
+ __u8 flags;
+ __u8 mdtype;
+ __u8 mdlen;
+ __u8 np;
+ __be32 path_hdr;
+ __u8 metadata[OVS_ENCAP_NSH_MAX_MD_LEN];
+};
+
/**
* enum ovs_action_attr - Action types.
*
@@ -806,6 +835,8 @@ struct ovs_action_push_eth {
* packet.
* @OVS_ACTION_ATTR_POP_ETH: Pop the outermost Ethernet header off the
* packet.
+ * @OVS_ACTION_ATTR_ENCAP_NSH: encap NSH action to push NSH header.
+ * @OVS_ACTION_ATTR_DECAP_NSH: decap NSH action to remove NSH header.
*
* Only a single header can be set with a single %OVS_ACTION_ATTR_SET. Not all
* fields within a header are modifiable, e.g. the IPv4 protocol and fragment
@@ -835,6 +866,8 @@ enum ovs_action_attr {
OVS_ACTION_ATTR_TRUNC, /* u32 struct ovs_action_trunc. */
OVS_ACTION_ATTR_PUSH_ETH, /* struct ovs_action_push_eth. */
OVS_ACTION_ATTR_POP_ETH, /* No argument. */
+ OVS_ACTION_ATTR_ENCAP_NSH, /* struct ovs_action_encap_nsh. */
+ OVS_ACTION_ATTR_DECAP_NSH, /* No argument. */
__OVS_ACTION_ATTR_MAX, /* Nothing past this will be accepted
* from userspace. */
diff --git a/net/openvswitch/actions.c b/net/openvswitch/actions.c
index e461067..6ba67e1 100644
--- a/net/openvswitch/actions.c
+++ b/net/openvswitch/actions.c
@@ -38,6 +38,7 @@
#include <net/dsfield.h>
#include <net/mpls.h>
#include <net/sctp/checksum.h>
+#include <net/nsh.h>
#include "datapath.h"
#include "flow.h"
@@ -380,6 +381,114 @@ static int push_eth(struct sk_buff *skb, struct sw_flow_key *key,
return 0;
}
+static int encap_nsh(struct sk_buff *skb, struct sw_flow_key *key,
+ const struct ovs_action_encap_nsh *encap)
+{
+ struct nsh_hdr *nsh;
+ size_t length = NSH_BASE_HDR_LEN + encap->mdlen;
+ u8 next_proto;
+
+ if (key->mac_proto == MAC_PROTO_ETHERNET) {
+ next_proto = NSH_P_ETHERNET;
+ } else {
+ switch (ntohs(skb->protocol)) {
+ case ETH_P_IP:
+ next_proto = NSH_P_IPV4;
+ break;
+ case ETH_P_IPV6:
+ next_proto = NSH_P_IPV6;
+ break;
+ case ETH_P_NSH:
+ next_proto = NSH_P_NSH;
+ break;
+ default:
+ return -ENOTSUPP;
+ }
+ }
+
+ /* Add the NSH header */
+ if (skb_cow_head(skb, length) < 0)
+ return -ENOMEM;
+
+ skb_push(skb, length);
+ nsh = (struct nsh_hdr *)(skb->data);
+ nsh->ver_flags_len = htons((encap->flags << NSH_FLAGS_SHIFT) |
+ (length >> 2));
+ nsh->next_proto = next_proto;
+ nsh->path_hdr = encap->path_hdr;
+ nsh->md_type = encap->mdtype;
+ switch (nsh->md_type) {
+ case NSH_M_TYPE1:
+ nsh->md1 = *(struct nsh_md1_ctx *)encap->metadata;
+ break;
+ case NSH_M_TYPE2: {
+ /* The MD2 metadata in encap is already padded to 4 bytes. */
+ size_t len = DIV_ROUND_UP(encap->mdlen, 4) * 4;
+
+ memcpy(nsh->md2, encap->metadata, len);
+ break;
+ }
+ default:
+ return -ENOTSUPP;
+ }
+
+ if (!skb->inner_protocol)
+ skb_set_inner_protocol(skb, skb->protocol);
+
+ skb->protocol = htons(ETH_P_NSH);
+ key->eth.type = htons(ETH_P_NSH);
+ skb_reset_mac_header(skb);
+ skb_reset_mac_len(skb);
+
+ /* safe right before invalidate_flow_key */
+ key->mac_proto = MAC_PROTO_NONE;
+ invalidate_flow_key(key);
+ return 0;
+}
+
+static int decap_nsh(struct sk_buff *skb, struct sw_flow_key *key)
+{
+ struct nsh_hdr *nsh = (struct nsh_hdr *)(skb->data);
+ size_t length;
+ u16 inner_proto;
+
+ if (ovs_key_mac_proto(key) != MAC_PROTO_NONE ||
+ skb->protocol != htons(ETH_P_NSH)) {
+ return -EINVAL;
+ }
+
+ switch (nsh->next_proto) {
+ case NSH_P_ETHERNET:
+ inner_proto = htons(ETH_P_TEB);
+ break;
+ case NSH_P_IPV4:
+ inner_proto = htons(ETH_P_IP);
+ break;
+ case NSH_P_IPV6:
+ inner_proto = htons(ETH_P_IPV6);
+ break;
+ case NSH_P_NSH:
+ inner_proto = htons(ETH_P_NSH);
+ break;
+ default:
+ return -ENOTSUPP;
+ }
+
+ length = nsh_hdr_len(nsh);
+ skb_pull(skb, length);
+ skb_reset_mac_header(skb);
+ skb_reset_mac_len(skb);
+ skb->protocol = inner_proto;
+
+ /* safe right before invalidate_flow_key */
+ if (inner_proto == htons(ETH_P_TEB))
+ key->mac_proto = MAC_PROTO_ETHERNET;
+ else
+ key->mac_proto = MAC_PROTO_NONE;
+ invalidate_flow_key(key);
+ return 0;
+}
+
static void update_ip_l4_checksum(struct sk_buff *skb, struct iphdr *nh,
__be32 addr, __be32 new_addr)
{
@@ -602,6 +711,49 @@ static int set_ipv6(struct sk_buff *skb, struct sw_flow_key *flow_key,
return 0;
}
+static int set_nsh(struct sk_buff *skb, struct sw_flow_key *flow_key,
+ const struct ovs_key_nsh *key,
+ const struct ovs_key_nsh *mask)
+{
+ struct nsh_hdr *nsh;
+ int err;
+ u8 flags;
+ int i;
+
+ err = skb_ensure_writable(skb, skb_network_offset(skb) +
+ sizeof(struct nsh_hdr));
+ if (unlikely(err))
+ return err;
+
+ nsh = (struct nsh_hdr *)skb_network_header(skb);
+
+ flags = (ntohs(nsh->ver_flags_len) & NSH_FLAGS_MASK) >>
+ NSH_FLAGS_SHIFT;
+ flags = OVS_MASKED(flags, key->flags, mask->flags);
+ flow_key->nsh.flags = flags;
+ nsh->ver_flags_len = htons(flags << NSH_FLAGS_SHIFT) |
+ (nsh->ver_flags_len & ~htons(NSH_FLAGS_MASK));
+ nsh->path_hdr = OVS_MASKED(nsh->path_hdr, key->path_hdr,
+ mask->path_hdr);
+ flow_key->nsh.path_hdr = nsh->path_hdr;
+ switch (nsh->md_type) {
+ case NSH_M_TYPE1:
+ for (i = 0; i < 4; i++) {
+ nsh->md1.c[i] =
+ OVS_MASKED(nsh->md1.c[i], key->c[i], mask->c[i]);
+ flow_key->nsh.c[i] = nsh->md1.c[i];
+ }
+ break;
+ case NSH_M_TYPE2:
+ for (i = 0; i < 4; i++)
+ flow_key->nsh.c[i] = 0;
+ break;
+ default:
+ return -EINVAL;
+ }
+ return 0;
+}
+
/* Must follow skb_ensure_writable() since that can move the skb data. */
static void set_tp_port(struct sk_buff *skb, __be16 *port,
__be16 new_port, __sum16 *check)
@@ -1024,6 +1176,11 @@ static int execute_masked_set_action(struct sk_buff *skb,
get_mask(a, struct ovs_key_ethernet *));
break;
+ case OVS_KEY_ATTR_NSH:
+ err = set_nsh(skb, flow_key, nla_data(a),
+ get_mask(a, struct ovs_key_nsh *));
+ break;
+
case OVS_KEY_ATTR_IPV4:
err = set_ipv4(skb, flow_key, nla_data(a),
get_mask(a, struct ovs_key_ipv4 *));
@@ -1210,6 +1367,14 @@ static int do_execute_actions(struct datapath *dp, struct sk_buff *skb,
case OVS_ACTION_ATTR_POP_ETH:
err = pop_eth(skb, key);
break;
+
+ case OVS_ACTION_ATTR_ENCAP_NSH:
+ err = encap_nsh(skb, key, nla_data(a));
+ break;
+
+ case OVS_ACTION_ATTR_DECAP_NSH:
+ err = decap_nsh(skb, key);
+ break;
}
if (unlikely(err)) {
diff --git a/net/openvswitch/flow.c b/net/openvswitch/flow.c
index 8c94cef..dc8631c 100644
--- a/net/openvswitch/flow.c
+++ b/net/openvswitch/flow.c
@@ -46,6 +46,7 @@
#include <net/ipv6.h>
#include <net/mpls.h>
#include <net/ndisc.h>
+#include <net/nsh.h>
#include "conntrack.h"
#include "datapath.h"
@@ -490,6 +491,42 @@ static int parse_icmpv6(struct sk_buff *skb, struct sw_flow_key *key,
return 0;
}
+static int parse_nsh(struct sk_buff *skb, struct sw_flow_key *key)
+{
+ struct nsh_hdr *nsh = (struct nsh_hdr *)skb_network_header(skb);
+ u16 ver_flags_len;
+ u8 version, length;
+ u32 path_hdr;
+ int i;
+
+ memset(&key->nsh, 0, sizeof(struct ovs_key_nsh));
+ ver_flags_len = ntohs(nsh->ver_flags_len);
+ version = (ver_flags_len & NSH_VER_MASK) >> NSH_VER_SHIFT;
+ length = (ver_flags_len & NSH_LEN_MASK) >> NSH_LEN_SHIFT;
+
+ key->nsh.flags = (ver_flags_len & NSH_FLAGS_MASK) >> NSH_FLAGS_SHIFT;
+ key->nsh.mdtype = nsh->md_type;
+ key->nsh.np = nsh->next_proto;
+ path_hdr = ntohl(nsh->path_hdr);
+ key->nsh.path_hdr = nsh->path_hdr;
+ switch (key->nsh.mdtype) {
+ case NSH_M_TYPE1:
+ if ((length << 2) != NSH_M_TYPE1_LEN)
+ return -EINVAL;
+
+ for (i = 0; i < 4; i++)
+ key->nsh.c[i] = nsh->md1.c[i];
+
+ break;
+ case NSH_M_TYPE2:
+ /* Don't support MD type 2 yet */
+ default:
+ return -EINVAL;
+ }
+
+ return 0;
+}
+
/**
* key_extract - extracts a flow key from an Ethernet frame.
* @skb: sk_buff that contains the frame, with skb->data pointing to the
@@ -735,6 +772,10 @@ static int key_extract(struct sk_buff *skb, struct sw_flow_key *key)
memset(&key->tp, 0, sizeof(key->tp));
}
}
+ } else if (key->eth.type == htons(ETH_P_NSH)) {
+ error = parse_nsh(skb, key);
+ if (error)
+ return error;
}
return 0;
}
diff --git a/net/openvswitch/flow.h b/net/openvswitch/flow.h
index 1875bba..d2a0e56 100644
--- a/net/openvswitch/flow.h
+++ b/net/openvswitch/flow.h
@@ -144,6 +144,7 @@ struct sw_flow_key {
};
} ipv6;
};
+ struct ovs_key_nsh nsh; /* network service header */
struct {
/* Connection tracking fields not packed above. */
struct {
diff --git a/net/openvswitch/flow_netlink.c b/net/openvswitch/flow_netlink.c
index f07d10a..147b3c0 100644
--- a/net/openvswitch/flow_netlink.c
+++ b/net/openvswitch/flow_netlink.c
@@ -48,6 +48,7 @@
#include <net/ndisc.h>
#include <net/mpls.h>
#include <net/vxlan.h>
+#include <net/nsh.h>
#include "flow_netlink.h"
@@ -76,9 +77,11 @@ static bool actions_may_change_flow(const struct nlattr *actions)
case OVS_ACTION_ATTR_CT:
case OVS_ACTION_ATTR_HASH:
+ case OVS_ACTION_ATTR_DECAP_NSH:
case OVS_ACTION_ATTR_POP_ETH:
case OVS_ACTION_ATTR_POP_MPLS:
case OVS_ACTION_ATTR_POP_VLAN:
+ case OVS_ACTION_ATTR_ENCAP_NSH:
case OVS_ACTION_ATTR_PUSH_ETH:
case OVS_ACTION_ATTR_PUSH_MPLS:
case OVS_ACTION_ATTR_PUSH_VLAN:
@@ -327,7 +330,7 @@ size_t ovs_key_attr_size(void)
/* Whenever adding new OVS_KEY_ FIELDS, we should consider
* updating this function.
*/
- BUILD_BUG_ON(OVS_KEY_ATTR_TUNNEL_INFO != 28);
+ BUILD_BUG_ON(OVS_KEY_ATTR_TUNNEL_INFO != 29);
return nla_total_size(4) /* OVS_KEY_ATTR_PRIORITY */
+ nla_total_size(0) /* OVS_KEY_ATTR_TUNNEL */
@@ -341,6 +344,7 @@ size_t ovs_key_attr_size(void)
+ nla_total_size(4) /* OVS_KEY_ATTR_CT_MARK */
+ nla_total_size(16) /* OVS_KEY_ATTR_CT_LABELS */
+ nla_total_size(40) /* OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV6 */
+ + nla_total_size(24) /* OVS_KEY_ATTR_NSH */
+ nla_total_size(12) /* OVS_KEY_ATTR_ETHERNET */
+ nla_total_size(2) /* OVS_KEY_ATTR_ETHERTYPE */
+ nla_total_size(4) /* OVS_KEY_ATTR_VLAN */
@@ -405,6 +409,7 @@ static const struct ovs_len_tbl ovs_key_lens[OVS_KEY_ATTR_MAX + 1] = {
.len = sizeof(struct ovs_key_ct_tuple_ipv4) },
[OVS_KEY_ATTR_CT_ORIG_TUPLE_IPV6] = {
.len = sizeof(struct ovs_key_ct_tuple_ipv6) },
+ [OVS_KEY_ATTR_NSH] = { .len = sizeof(struct ovs_key_nsh) },
};
static bool check_attr_len(unsigned int attr_len, unsigned int expected_len)
@@ -1306,6 +1311,22 @@ static int ovs_key_from_nlattrs(struct net *net, struct sw_flow_match *match,
attrs &= ~(1 << OVS_KEY_ATTR_ARP);
}
+ if (attrs & (1 << OVS_KEY_ATTR_NSH)) {
+ int i;
+ const struct ovs_key_nsh *nsh_key;
+
+ nsh_key = nla_data(a[OVS_KEY_ATTR_NSH]);
+ SW_FLOW_KEY_PUT(match, nsh.flags, nsh_key->flags, is_mask);
+ SW_FLOW_KEY_PUT(match, nsh.mdtype, nsh_key->mdtype, is_mask);
+ SW_FLOW_KEY_PUT(match, nsh.np, nsh_key->np, is_mask);
+ SW_FLOW_KEY_PUT(match, nsh.path_hdr, nsh_key->path_hdr,
+ is_mask);
+ for (i = 0; i < 4; i++)
+ SW_FLOW_KEY_PUT(match, nsh.c[i], nsh_key->c[i],
+ is_mask);
+ attrs &= ~(1 << OVS_KEY_ATTR_NSH);
+ }
+
if (attrs & (1 << OVS_KEY_ATTR_MPLS)) {
const struct ovs_key_mpls *mpls_key;
@@ -1750,6 +1771,21 @@ static int __ovs_nla_put_key(const struct sw_flow_key *swkey,
ipv6_key->ipv6_tclass = output->ip.tos;
ipv6_key->ipv6_hlimit = output->ip.ttl;
ipv6_key->ipv6_frag = output->ip.frag;
+ } else if (swkey->eth.type == htons(ETH_P_NSH)) {
+ int i;
+ struct ovs_key_nsh *nsh_key;
+
+ nla = nla_reserve(skb, OVS_KEY_ATTR_NSH, sizeof(*nsh_key));
+ if (!nla)
+ goto nla_put_failure;
+ nsh_key = nla_data(nla);
+ memset(nsh_key, 0, sizeof(struct ovs_key_nsh));
+ nsh_key->flags = output->nsh.flags;
+ nsh_key->mdtype = output->nsh.mdtype;
+ nsh_key->np = output->nsh.np;
+ nsh_key->path_hdr = output->nsh.path_hdr;
+ for (i = 0; i < 4; i++)
+ nsh_key->c[0] = output->nsh.c[i];
} else if (swkey->eth.type == htons(ETH_P_ARP) ||
swkey->eth.type == htons(ETH_P_RARP)) {
struct ovs_key_arp *arp_key;
@@ -2384,6 +2420,9 @@ static int validate_set(const struct nlattr *a,
break;
+ case OVS_KEY_ATTR_NSH:
+ break;
+
default:
return -EINVAL;
}
@@ -2482,6 +2521,8 @@ static int __ovs_nla_copy_actions(struct net *net, const struct nlattr *attr,
[OVS_ACTION_ATTR_TRUNC] = sizeof(struct ovs_action_trunc),
[OVS_ACTION_ATTR_PUSH_ETH] = sizeof(struct ovs_action_push_eth),
[OVS_ACTION_ATTR_POP_ETH] = 0,
+ [OVS_ACTION_ATTR_ENCAP_NSH] = sizeof(struct ovs_action_encap_nsh),
+ [OVS_ACTION_ATTR_DECAP_NSH] = 0,
};
const struct ovs_action_push_vlan *vlan;
int type = nla_type(a);
@@ -2636,6 +2677,17 @@ static int __ovs_nla_copy_actions(struct net *net, const struct nlattr *attr,
mac_proto = MAC_PROTO_ETHERNET;
break;
+ case OVS_ACTION_ATTR_ENCAP_NSH:
+ mac_proto = MAC_PROTO_NONE;
+ break;
+
+ case OVS_ACTION_ATTR_DECAP_NSH:
+ if (key->nsh.np == NSH_P_ETHERNET)
+ mac_proto = MAC_PROTO_ETHERNET;
+ else
+ mac_proto = MAC_PROTO_NONE;
+ break;
+
default:
OVS_NLERR(log, "Unknown Action type %d", type);
return -EINVAL;
--
2.5.5
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox