Linux kernel mirror (for testing)
git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel
os
linux
1#!/bin/bash
2# SPDX-License-Identifier: GPL-2.0
3# Copyright 2020 NXP Semiconductors
4
5WAIT_TIME=1
6NUM_NETIFS=4
7lib_dir=$(dirname $0)/../../../net/forwarding
8source $lib_dir/tc_common.sh
9source $lib_dir/lib.sh
10
11require_command tcpdump
12
13#
14# +---------------------------------------------+
15# | DUT ports Generator ports |
16# | +--------+ +--------+ +--------+ +--------+ |
17# | | | | | | | | | |
18# | | eth0 | | eth1 | | eth2 | | eth3 | |
19# | | | | | | | | | |
20# +-+--------+-+--------+-+--------+-+--------+-+
21# | | | |
22# | | | |
23# | +-----------+ |
24# | |
25# +--------------------------------+
26
27eth0=${NETIFS[p1]}
28eth1=${NETIFS[p2]}
29eth2=${NETIFS[p3]}
30eth3=${NETIFS[p4]}
31
32eth0_mac="de:ad:be:ef:00:00"
33eth1_mac="de:ad:be:ef:00:01"
34eth2_mac="de:ad:be:ef:00:02"
35eth3_mac="de:ad:be:ef:00:03"
36
37# Helpers to map a VCAP IS1 and VCAP IS2 lookup and policy to a chain number
38# used by the kernel driver. The numbers are:
39# VCAP IS1 lookup 0: 10000
40# VCAP IS1 lookup 1: 11000
41# VCAP IS1 lookup 2: 12000
42# VCAP IS2 lookup 0 policy 0: 20000
43# VCAP IS2 lookup 0 policy 1: 20001
44# VCAP IS2 lookup 0 policy 255: 20255
45# VCAP IS2 lookup 1 policy 0: 21000
46# VCAP IS2 lookup 1 policy 1: 21001
47# VCAP IS2 lookup 1 policy 255: 21255
48IS1()
49{
50 local lookup=$1
51
52 echo $((10000 + 1000 * lookup))
53}
54
55IS2()
56{
57 local lookup=$1
58 local pag=$2
59
60 echo $((20000 + 1000 * lookup + pag))
61}
62
63ES0()
64{
65 echo 0
66}
67
68# The Ocelot switches have a fixed ingress pipeline composed of:
69#
70# +----------------------------------------------+ +-----------------------------------------+
71# | VCAP IS1 | | VCAP IS2 |
72# | | | |
73# | +----------+ +----------+ +----------+ | | +----------+ +----------+ |
74# | | Lookup 0 | | Lookup 1 | | Lookup 2 | | --+------> PAG 0: | Lookup 0 | -> | Lookup 1 | |
75# | +----------+ -> +----------+ -> +----------+ | | | +----------+ +----------+ |
76# | |key&action| |key&action| |key&action| | | | |key&action| |key&action| |
77# | |key&action| |key&action| |key&action| | | | | .. | | .. | |
78# | | .. | | .. | | .. | | | | +----------+ +----------+ |
79# | +----------+ +----------+ +----------+ | | | |
80# | selects PAG | | | +----------+ +----------+ |
81# +----------------------------------------------+ +------> PAG 1: | Lookup 0 | -> | Lookup 1 | |
82# | | +----------+ +----------+ |
83# | | |key&action| |key&action| |
84# | | | .. | | .. | |
85# | | +----------+ +----------+ |
86# | | ... |
87# | | |
88# | | +----------+ +----------+ |
89# +----> PAG 254: | Lookup 0 | -> | Lookup 1 | |
90# | | +----------+ +----------+ |
91# | | |key&action| |key&action| |
92# | | | .. | | .. | |
93# | | +----------+ +----------+ |
94# | | |
95# | | +----------+ +----------+ |
96# +----> PAG 255: | Lookup 0 | -> | Lookup 1 | |
97# | +----------+ +----------+ |
98# | |key&action| |key&action| |
99# | | .. | | .. | |
100# | +----------+ +----------+ |
101# +-----------------------------------------+
102#
103# Both the VCAP IS1 (Ingress Stage 1) and IS2 (Ingress Stage 2) are indexed
104# (looked up) multiple times: IS1 3 times, and IS2 2 times. Each filter
105# (key and action pair) can be configured to only match during the first, or
106# second, etc, lookup.
107#
108# During one TCAM lookup, the filter processing stops at the first entry that
109# matches, then the pipeline jumps to the next lookup.
110# The driver maps each individual lookup of each individual ingress TCAM to a
111# separate chain number. For correct rule offloading, it is mandatory that each
112# filter installed in one TCAM is terminated by a non-optional GOTO action to
113# the next lookup from the fixed pipeline.
114#
115# A chain can only be used if there is a GOTO action correctly set up from the
116# prior lookup in the processing pipeline. Setting up all chains is not
117# mandatory.
118
119# NOTE: VCAP IS1 currently uses only S1_NORMAL half keys and VCAP IS2
120# dynamically chooses between MAC_ETYPE, ARP, IP4_TCP_UDP, IP4_OTHER, which are
121# all half keys as well.
122
123create_tcam_skeleton()
124{
125 local eth=$1
126
127 tc qdisc add dev $eth clsact
128
129 # VCAP IS1 is the Ingress Classification TCAM and can offload the
130 # following actions:
131 # - skbedit priority
132 # - vlan pop
133 # - vlan modify
134 # - goto (only in lookup 2, the last IS1 lookup)
135 tc filter add dev $eth ingress chain 0 pref 49152 flower \
136 skip_sw action goto chain $(IS1 0)
137 tc filter add dev $eth ingress chain $(IS1 0) pref 49152 \
138 flower skip_sw action goto chain $(IS1 1)
139 tc filter add dev $eth ingress chain $(IS1 1) pref 49152 \
140 flower skip_sw action goto chain $(IS1 2)
141 tc filter add dev $eth ingress chain $(IS1 2) pref 49152 \
142 flower skip_sw action goto chain $(IS2 0 0)
143
144 # VCAP IS2 is the Security Enforcement ingress TCAM and can offload the
145 # following actions:
146 # - trap
147 # - drop
148 # - police
149 # The two VCAP IS2 lookups can be segmented into up to 256 groups of
150 # rules, called Policies. A Policy is selected through the Policy
151 # Association Group (PAG) action of VCAP IS1 (which is the
152 # GOTO offload).
153 tc filter add dev $eth ingress chain $(IS2 0 0) pref 49152 \
154 flower skip_sw action goto chain $(IS2 1 0)
155}
156
157setup_prepare()
158{
159 create_tcam_skeleton $eth0
160
161 ip link add br0 type bridge
162 ip link set $eth0 master br0
163 ip link set $eth1 master br0
164 ip link set br0 up
165
166 ip link add link $eth3 name $eth3.100 type vlan id 100
167 ip link set $eth3.100 up
168
169 ip link add link $eth3 name $eth3.200 type vlan id 200
170 ip link set $eth3.200 up
171
172 tc filter add dev $eth0 ingress chain $(IS1 1) pref 1 \
173 protocol 802.1Q flower skip_sw vlan_id 100 \
174 action vlan pop \
175 action goto chain $(IS1 2)
176
177 tc filter add dev $eth0 egress chain $(ES0) pref 1 \
178 flower skip_sw indev $eth1 \
179 action vlan push protocol 802.1Q id 100
180
181 tc filter add dev $eth0 ingress chain $(IS1 0) pref 2 \
182 protocol ipv4 flower skip_sw src_ip 10.1.1.2 \
183 action skbedit priority 7 \
184 action goto chain $(IS1 1)
185
186 tc filter add dev $eth0 ingress chain $(IS2 0 0) pref 1 \
187 protocol ipv4 flower skip_sw ip_proto udp dst_port 5201 \
188 action police rate 50mbit burst 64k \
189 action goto chain $(IS2 1 0)
190}
191
192cleanup()
193{
194 ip link del $eth3.200
195 ip link del $eth3.100
196 tc qdisc del dev $eth0 clsact
197 ip link del br0
198}
199
200test_vlan_pop()
201{
202 printf "Testing VLAN pop.. "
203
204 tcpdump_start $eth2
205
206 # Work around Mausezahn VLAN builder bug
207 # (https://github.com/netsniff-ng/netsniff-ng/issues/225) by using
208 # an 8021q upper
209 $MZ $eth3.100 -q -c 1 -p 64 -a $eth3_mac -b $eth2_mac -t ip
210
211 sleep 1
212
213 tcpdump_stop
214
215 if tcpdump_show | grep -q "$eth3_mac > $eth2_mac, ethertype IPv4"; then
216 echo "OK"
217 else
218 echo "FAIL"
219 fi
220
221 tcpdump_cleanup
222}
223
224test_vlan_push()
225{
226 printf "Testing VLAN push.. "
227
228 tcpdump_start $eth3.100
229
230 $MZ $eth2 -q -c 1 -p 64 -a $eth2_mac -b $eth3_mac -t ip
231
232 sleep 1
233
234 tcpdump_stop
235
236 if tcpdump_show | grep -q "$eth2_mac > $eth3_mac"; then
237 echo "OK"
238 else
239 echo "FAIL"
240 fi
241
242 tcpdump_cleanup
243}
244
245test_vlan_modify()
246{
247 printf "Testing VLAN modification.. "
248
249 ip link set br0 type bridge vlan_filtering 1
250 bridge vlan add dev $eth0 vid 200
251 bridge vlan add dev $eth0 vid 300
252 bridge vlan add dev $eth1 vid 300
253
254 tc filter add dev $eth0 ingress chain $(IS1 2) pref 3 \
255 protocol 802.1Q flower skip_sw vlan_id 200 \
256 action vlan modify id 300 \
257 action goto chain $(IS2 0 0)
258
259 tcpdump_start $eth2
260
261 $MZ $eth3.200 -q -c 1 -p 64 -a $eth3_mac -b $eth2_mac -t ip
262
263 sleep 1
264
265 tcpdump_stop
266
267 if tcpdump_show | grep -q "$eth3_mac > $eth2_mac, .* vlan 300"; then
268 echo "OK"
269 else
270 echo "FAIL"
271 fi
272
273 tcpdump_cleanup
274
275 tc filter del dev $eth0 ingress chain $(IS1 2) pref 3
276
277 bridge vlan del dev $eth0 vid 200
278 bridge vlan del dev $eth0 vid 300
279 bridge vlan del dev $eth1 vid 300
280 ip link set br0 type bridge vlan_filtering 0
281}
282
283test_skbedit_priority()
284{
285 local num_pkts=100
286
287 printf "Testing frame prioritization.. "
288
289 before=$(ethtool_stats_get $eth0 'rx_green_prio_7')
290
291 $MZ $eth3 -q -c $num_pkts -p 64 -a $eth3_mac -b $eth2_mac -t ip -A 10.1.1.2
292
293 after=$(ethtool_stats_get $eth0 'rx_green_prio_7')
294
295 if [ $((after - before)) = $num_pkts ]; then
296 echo "OK"
297 else
298 echo "FAIL"
299 fi
300}
301
302trap cleanup EXIT
303
304ALL_TESTS="
305 test_vlan_pop
306 test_vlan_push
307 test_vlan_modify
308 test_skbedit_priority
309"
310
311setup_prepare
312setup_wait
313
314tests_run
315
316exit $EXIT_STATUS