Commit 7318166c authored by Florian Fainelli's avatar Florian Fainelli Committed by David S. Miller

net: dsa: bcm_sf2: Add support for ethtool::rxnfc

Add support for configuring classification rules using the
ethtool::rxnfc API.  This is useful to program the switch's CFP/TCAM to
redirect specific packets to specific ports/queues for instance. For
now, we allow any kind of IPv4 5-tuple matching.
Signed-off-by: default avatarFlorian Fainelli <f.fainelli@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 85345808
obj-$(CONFIG_NET_DSA_MV88E6060) += mv88e6060.o obj-$(CONFIG_NET_DSA_MV88E6060) += mv88e6060.o
obj-$(CONFIG_NET_DSA_BCM_SF2) += bcm_sf2.o obj-$(CONFIG_NET_DSA_BCM_SF2) += bcm_sf2.o
bcm_sf2-objs += bcm_sf2_cfp.o
obj-$(CONFIG_NET_DSA_QCA8K) += qca8k.o obj-$(CONFIG_NET_DSA_QCA8K) += qca8k.o
obj-y += b53/ obj-y += b53/
......
...@@ -1045,6 +1045,8 @@ static const struct dsa_switch_ops bcm_sf2_ops = { ...@@ -1045,6 +1045,8 @@ static const struct dsa_switch_ops bcm_sf2_ops = {
.port_fdb_dump = b53_fdb_dump, .port_fdb_dump = b53_fdb_dump,
.port_fdb_add = b53_fdb_add, .port_fdb_add = b53_fdb_add,
.port_fdb_del = b53_fdb_del, .port_fdb_del = b53_fdb_del,
.get_rxnfc = bcm_sf2_get_rxnfc,
.set_rxnfc = bcm_sf2_set_rxnfc,
}; };
struct bcm_sf2_of_data { struct bcm_sf2_of_data {
...@@ -1168,6 +1170,12 @@ static int bcm_sf2_sw_probe(struct platform_device *pdev) ...@@ -1168,6 +1170,12 @@ static int bcm_sf2_sw_probe(struct platform_device *pdev)
spin_lock_init(&priv->indir_lock); spin_lock_init(&priv->indir_lock);
mutex_init(&priv->stats_mutex); mutex_init(&priv->stats_mutex);
mutex_init(&priv->cfp.lock);
/* CFP rule #0 cannot be used for specific classifications, flag it as
* permanently used
*/
set_bit(0, priv->cfp.used);
bcm_sf2_identify_ports(priv, dn->child); bcm_sf2_identify_ports(priv, dn->child);
...@@ -1197,6 +1205,12 @@ static int bcm_sf2_sw_probe(struct platform_device *pdev) ...@@ -1197,6 +1205,12 @@ static int bcm_sf2_sw_probe(struct platform_device *pdev)
return ret; return ret;
} }
ret = bcm_sf2_cfp_rst(priv);
if (ret) {
pr_err("failed to reset CFP\n");
goto out_mdio;
}
/* Disable all interrupts and request them */ /* Disable all interrupts and request them */
bcm_sf2_intr_disable(priv); bcm_sf2_intr_disable(priv);
......
...@@ -52,6 +52,13 @@ struct bcm_sf2_port_status { ...@@ -52,6 +52,13 @@ struct bcm_sf2_port_status {
struct ethtool_eee eee; struct ethtool_eee eee;
}; };
struct bcm_sf2_cfp_priv {
/* Mutex protecting concurrent accesses to the CFP registers */
struct mutex lock;
DECLARE_BITMAP(used, CFP_NUM_RULES);
unsigned int rules_cnt;
};
struct bcm_sf2_priv { struct bcm_sf2_priv {
/* Base registers, keep those in order with BCM_SF2_REGS_NAME */ /* Base registers, keep those in order with BCM_SF2_REGS_NAME */
void __iomem *core; void __iomem *core;
...@@ -103,6 +110,9 @@ struct bcm_sf2_priv { ...@@ -103,6 +110,9 @@ struct bcm_sf2_priv {
/* Bitmask of ports needing BRCM tags */ /* Bitmask of ports needing BRCM tags */
unsigned int brcm_tag_mask; unsigned int brcm_tag_mask;
/* CFP rules context */
struct bcm_sf2_cfp_priv cfp;
}; };
static inline struct bcm_sf2_priv *bcm_sf2_to_priv(struct dsa_switch *ds) static inline struct bcm_sf2_priv *bcm_sf2_to_priv(struct dsa_switch *ds)
...@@ -197,4 +207,11 @@ SF2_IO_MACRO(acb); ...@@ -197,4 +207,11 @@ SF2_IO_MACRO(acb);
SWITCH_INTR_L2(0); SWITCH_INTR_L2(0);
SWITCH_INTR_L2(1); SWITCH_INTR_L2(1);
/* RXNFC */
int bcm_sf2_get_rxnfc(struct dsa_switch *ds, int port,
struct ethtool_rxnfc *nfc, u32 *rule_locs);
int bcm_sf2_set_rxnfc(struct dsa_switch *ds, int port,
struct ethtool_rxnfc *nfc);
int bcm_sf2_cfp_rst(struct bcm_sf2_priv *priv);
#endif /* __BCM_SF2_H */ #endif /* __BCM_SF2_H */
This diff is collapsed.
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