Commit 5351b859 authored by Or Gerlitz's avatar Or Gerlitz Committed by Greg Kroah-Hartman

net/mlx5e: Don't match on vlan non-existence if ethertype is wildcarded

[ Upstream commit d3a80bb5 ]

For the "all" ethertype we should not care whether the packet has
vlans. Besides being wrong, the way we did it caused FW error
for rules such as:

tc filter add dev eth0 protocol all parent ffff: \
	prio 1 flower skip_sw action drop

b/c the matching meta-data (outer headers bit in struct mlx5_flow_spec)
wasn't set. Fix that by matching on vlan non-existence only if we were
also told to match on the ethertype.

Fixes: cee26487 ('net/mlx5e: Set vlan masks for all offloaded TC rules')
Signed-off-by: default avatarOr Gerlitz <ogerlitz@mellanox.com>
Reported-by: default avatarSlava Ovsiienko <viacheslavo@mellanox.com>
Reviewed-by: default avatarJianbo Liu <jianbol@mellanox.com>
Reviewed-by: default avatarRoi Dayan <roid@mellanox.com>
Signed-off-by: default avatarSaeed Mahameed <saeedm@mellanox.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 961842dc
...@@ -1310,31 +1310,21 @@ static int __parse_cls_flower(struct mlx5e_priv *priv, ...@@ -1310,31 +1310,21 @@ static int __parse_cls_flower(struct mlx5e_priv *priv,
inner_headers); inner_headers);
} }
if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_ETH_ADDRS)) { if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_BASIC)) {
struct flow_dissector_key_eth_addrs *key = struct flow_dissector_key_basic *key =
skb_flow_dissector_target(f->dissector, skb_flow_dissector_target(f->dissector,
FLOW_DISSECTOR_KEY_ETH_ADDRS, FLOW_DISSECTOR_KEY_BASIC,
f->key); f->key);
struct flow_dissector_key_eth_addrs *mask = struct flow_dissector_key_basic *mask =
skb_flow_dissector_target(f->dissector, skb_flow_dissector_target(f->dissector,
FLOW_DISSECTOR_KEY_ETH_ADDRS, FLOW_DISSECTOR_KEY_BASIC,
f->mask); f->mask);
MLX5_SET(fte_match_set_lyr_2_4, headers_c, ethertype,
ntohs(mask->n_proto));
MLX5_SET(fte_match_set_lyr_2_4, headers_v, ethertype,
ntohs(key->n_proto));
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_c, if (mask->n_proto)
dmac_47_16),
mask->dst);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_v,
dmac_47_16),
key->dst);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_c,
smac_47_16),
mask->src);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_v,
smac_47_16),
key->src);
if (!is_zero_ether_addr(mask->src) || !is_zero_ether_addr(mask->dst))
*match_level = MLX5_MATCH_L2; *match_level = MLX5_MATCH_L2;
} }
...@@ -1368,9 +1358,10 @@ static int __parse_cls_flower(struct mlx5e_priv *priv, ...@@ -1368,9 +1358,10 @@ static int __parse_cls_flower(struct mlx5e_priv *priv,
*match_level = MLX5_MATCH_L2; *match_level = MLX5_MATCH_L2;
} }
} else { } else if (*match_level != MLX5_MATCH_NONE) {
MLX5_SET(fte_match_set_lyr_2_4, headers_c, svlan_tag, 1); MLX5_SET(fte_match_set_lyr_2_4, headers_c, svlan_tag, 1);
MLX5_SET(fte_match_set_lyr_2_4, headers_c, cvlan_tag, 1); MLX5_SET(fte_match_set_lyr_2_4, headers_c, cvlan_tag, 1);
*match_level = MLX5_MATCH_L2;
} }
if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_CVLAN)) { if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_CVLAN)) {
...@@ -1408,21 +1399,31 @@ static int __parse_cls_flower(struct mlx5e_priv *priv, ...@@ -1408,21 +1399,31 @@ static int __parse_cls_flower(struct mlx5e_priv *priv,
} }
} }
if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_BASIC)) { if (dissector_uses_key(f->dissector, FLOW_DISSECTOR_KEY_ETH_ADDRS)) {
struct flow_dissector_key_basic *key = struct flow_dissector_key_eth_addrs *key =
skb_flow_dissector_target(f->dissector, skb_flow_dissector_target(f->dissector,
FLOW_DISSECTOR_KEY_BASIC, FLOW_DISSECTOR_KEY_ETH_ADDRS,
f->key); f->key);
struct flow_dissector_key_basic *mask = struct flow_dissector_key_eth_addrs *mask =
skb_flow_dissector_target(f->dissector, skb_flow_dissector_target(f->dissector,
FLOW_DISSECTOR_KEY_BASIC, FLOW_DISSECTOR_KEY_ETH_ADDRS,
f->mask); f->mask);
MLX5_SET(fte_match_set_lyr_2_4, headers_c, ethertype,
ntohs(mask->n_proto));
MLX5_SET(fte_match_set_lyr_2_4, headers_v, ethertype,
ntohs(key->n_proto));
if (mask->n_proto) ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_c,
dmac_47_16),
mask->dst);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_v,
dmac_47_16),
key->dst);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_c,
smac_47_16),
mask->src);
ether_addr_copy(MLX5_ADDR_OF(fte_match_set_lyr_2_4, headers_v,
smac_47_16),
key->src);
if (!is_zero_ether_addr(mask->src) || !is_zero_ether_addr(mask->dst))
*match_level = MLX5_MATCH_L2; *match_level = MLX5_MATCH_L2;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment