Merge branches 'acpi-pm', 'acpi-pci', 'acpi-sysfs' and 'acpi-tables'
[linux-2.6-microblaze.git] / tools / testing / selftests / drivers / net / ocelot / tc_flower_chains.sh
1 #!/bin/bash
2 # SPDX-License-Identifier: GPL-2.0
3 # Copyright 2020 NXP
4
5 WAIT_TIME=1
6 NUM_NETIFS=4
7 lib_dir=$(dirname $0)/../../../net/forwarding
8 source $lib_dir/tc_common.sh
9 source $lib_dir/lib.sh
10
11 require_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
27 eth0=${NETIFS[p1]}
28 eth1=${NETIFS[p2]}
29 eth2=${NETIFS[p3]}
30 eth3=${NETIFS[p4]}
31
32 eth0_mac="de:ad:be:ef:00:00"
33 eth1_mac="de:ad:be:ef:00:01"
34 eth2_mac="de:ad:be:ef:00:02"
35 eth3_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
48 IS1()
49 {
50         local lookup=$1
51
52         echo $((10000 + 1000 * lookup))
53 }
54
55 IS2()
56 {
57         local lookup=$1
58         local pag=$2
59
60         echo $((20000 + 1000 * lookup + pag))
61 }
62
63 ES0()
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
123 create_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
157 setup_prepare()
158 {
159         ip link set $eth0 up
160         ip link set $eth1 up
161         ip link set $eth2 up
162         ip link set $eth3 up
163
164         create_tcam_skeleton $eth0
165
166         ip link add br0 type bridge
167         ip link set $eth0 master br0
168         ip link set $eth1 master br0
169         ip link set br0 up
170
171         ip link add link $eth3 name $eth3.100 type vlan id 100
172         ip link set $eth3.100 up
173
174         ip link add link $eth3 name $eth3.200 type vlan id 200
175         ip link set $eth3.200 up
176
177         tc filter add dev $eth0 ingress chain $(IS1 1) pref 1 \
178                 protocol 802.1Q flower skip_sw vlan_id 100 \
179                 action vlan pop \
180                 action goto chain $(IS1 2)
181
182         tc filter add dev $eth0 egress chain $(ES0) pref 1 \
183                 flower skip_sw indev $eth1 \
184                 action vlan push protocol 802.1Q id 100
185
186         tc filter add dev $eth0 ingress chain $(IS1 0) pref 2 \
187                 protocol ipv4 flower skip_sw src_ip 10.1.1.2 \
188                 action skbedit priority 7 \
189                 action goto chain $(IS1 1)
190
191         tc filter add dev $eth0 ingress chain $(IS2 0 0) pref 1 \
192                 protocol ipv4 flower skip_sw ip_proto udp dst_port 5201 \
193                 action police rate 50mbit burst 64k conform-exceed drop/pipe \
194                 action goto chain $(IS2 1 0)
195 }
196
197 cleanup()
198 {
199         ip link del $eth3.200
200         ip link del $eth3.100
201         tc qdisc del dev $eth0 clsact
202         ip link del br0
203 }
204
205 test_vlan_pop()
206 {
207         printf "Testing VLAN pop..                      "
208
209         tcpdump_start $eth2
210
211         # Work around Mausezahn VLAN builder bug
212         # (https://github.com/netsniff-ng/netsniff-ng/issues/225) by using
213         # an 8021q upper
214         $MZ $eth3.100 -q -c 1 -p 64 -a $eth3_mac -b $eth2_mac -t ip
215
216         sleep 1
217
218         tcpdump_stop
219
220         if tcpdump_show | grep -q "$eth3_mac > $eth2_mac, ethertype IPv4"; then
221                 echo "OK"
222         else
223                 echo "FAIL"
224         fi
225
226         tcpdump_cleanup
227 }
228
229 test_vlan_push()
230 {
231         printf "Testing VLAN push..                     "
232
233         tcpdump_start $eth3.100
234
235         $MZ $eth2 -q -c 1 -p 64 -a $eth2_mac -b $eth3_mac -t ip
236
237         sleep 1
238
239         tcpdump_stop
240
241         if tcpdump_show | grep -q "$eth2_mac > $eth3_mac"; then
242                 echo "OK"
243         else
244                 echo "FAIL"
245         fi
246
247         tcpdump_cleanup
248 }
249
250 test_vlan_ingress_modify()
251 {
252         printf "Testing ingress VLAN modification..             "
253
254         ip link set br0 type bridge vlan_filtering 1
255         bridge vlan add dev $eth0 vid 200
256         bridge vlan add dev $eth0 vid 300
257         bridge vlan add dev $eth1 vid 300
258
259         tc filter add dev $eth0 ingress chain $(IS1 2) pref 3 \
260                 protocol 802.1Q flower skip_sw vlan_id 200 \
261                 action vlan modify id 300 \
262                 action goto chain $(IS2 0 0)
263
264         tcpdump_start $eth2
265
266         $MZ $eth3.200 -q -c 1 -p 64 -a $eth3_mac -b $eth2_mac -t ip
267
268         sleep 1
269
270         tcpdump_stop
271
272         if tcpdump_show | grep -q "$eth3_mac > $eth2_mac, .* vlan 300"; then
273                 echo "OK"
274         else
275                 echo "FAIL"
276         fi
277
278         tcpdump_cleanup
279
280         tc filter del dev $eth0 ingress chain $(IS1 2) pref 3
281
282         bridge vlan del dev $eth0 vid 200
283         bridge vlan del dev $eth0 vid 300
284         bridge vlan del dev $eth1 vid 300
285         ip link set br0 type bridge vlan_filtering 0
286 }
287
288 test_vlan_egress_modify()
289 {
290         printf "Testing egress VLAN modification..              "
291
292         tc qdisc add dev $eth1 clsact
293
294         ip link set br0 type bridge vlan_filtering 1
295         bridge vlan add dev $eth0 vid 200
296         bridge vlan add dev $eth1 vid 200
297
298         tc filter add dev $eth1 egress chain $(ES0) pref 3 \
299                 protocol 802.1Q flower skip_sw vlan_id 200 vlan_prio 0 \
300                 action vlan modify id 300 priority 7
301
302         tcpdump_start $eth2
303
304         $MZ $eth3.200 -q -c 1 -p 64 -a $eth3_mac -b $eth2_mac -t ip
305
306         sleep 1
307
308         tcpdump_stop
309
310         if tcpdump_show | grep -q "$eth3_mac > $eth2_mac, .* vlan 300"; then
311                 echo "OK"
312         else
313                 echo "FAIL"
314         fi
315
316         tcpdump_cleanup
317
318         tc filter del dev $eth1 egress chain $(ES0) pref 3
319         tc qdisc del dev $eth1 clsact
320
321         bridge vlan del dev $eth0 vid 200
322         bridge vlan del dev $eth1 vid 200
323         ip link set br0 type bridge vlan_filtering 0
324 }
325
326 test_skbedit_priority()
327 {
328         local num_pkts=100
329
330         printf "Testing frame prioritization..          "
331
332         before=$(ethtool_stats_get $eth0 'rx_green_prio_7')
333
334         $MZ $eth3 -q -c $num_pkts -p 64 -a $eth3_mac -b $eth2_mac -t ip -A 10.1.1.2
335
336         after=$(ethtool_stats_get $eth0 'rx_green_prio_7')
337
338         if [ $((after - before)) = $num_pkts ]; then
339                 echo "OK"
340         else
341                 echo "FAIL"
342         fi
343 }
344
345 trap cleanup EXIT
346
347 ALL_TESTS="
348         test_vlan_pop
349         test_vlan_push
350         test_vlan_ingress_modify
351         test_vlan_egress_modify
352         test_skbedit_priority
353 "
354
355 setup_prepare
356 setup_wait
357
358 tests_run
359
360 exit $EXIT_STATUS