2
0
mirror of https://github.com/edk2-porting/linux-next.git synced 2024-12-21 11:44:01 +08:00

Merge branch 'dsa-next'

Vivien Didelot says:

====================
net: dsa: push switchdev prepare phase in FDB ops

This patchset pushes the switchdev prepare phase for the FDB add and del
operations down to the DSA drivers. Currently only mv88e6xxx is affected.

Since the dump requires a bit of refactoring in the driver, it'll come in a
future patchset.

Changes in v2:
 * forward declare switchdev structs instead of fixing the dsa.h include.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
David S. Miller 2015-10-11 05:28:57 -07:00
commit 5010ea59e1
6 changed files with 42 additions and 14 deletions

View File

@ -121,6 +121,7 @@ struct dsa_switch_driver mv88e6171_switch_driver = {
.port_vlan_add = mv88e6xxx_port_vlan_add,
.port_vlan_del = mv88e6xxx_port_vlan_del,
.vlan_getnext = mv88e6xxx_vlan_getnext,
.port_fdb_prepare = mv88e6xxx_port_fdb_prepare,
.port_fdb_add = mv88e6xxx_port_fdb_add,
.port_fdb_del = mv88e6xxx_port_fdb_del,
.port_fdb_getnext = mv88e6xxx_port_fdb_getnext,

View File

@ -348,6 +348,7 @@ struct dsa_switch_driver mv88e6352_switch_driver = {
.port_vlan_add = mv88e6xxx_port_vlan_add,
.port_vlan_del = mv88e6xxx_port_vlan_del,
.vlan_getnext = mv88e6xxx_vlan_getnext,
.port_fdb_prepare = mv88e6xxx_port_fdb_prepare,
.port_fdb_add = mv88e6xxx_port_fdb_add,
.port_fdb_del = mv88e6xxx_port_fdb_del,
.port_fdb_getnext = mv88e6xxx_port_fdb_getnext,

View File

@ -23,6 +23,7 @@
#include <linux/phy.h>
#include <linux/seq_file.h>
#include <net/dsa.h>
#include <net/switchdev.h>
#include "mv88e6xxx.h"
/* MDIO bus access can be nested in the case of PHYs connected to the
@ -1841,30 +1842,41 @@ static int _mv88e6xxx_port_fdb_load(struct dsa_switch *ds, int port,
return _mv88e6xxx_atu_load(ds, &entry);
}
int mv88e6xxx_port_fdb_add(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid)
int mv88e6xxx_port_fdb_prepare(struct dsa_switch *ds, int port,
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans)
{
int state = is_multicast_ether_addr(addr) ?
/* We don't need any dynamic resource from the kernel (yet),
* so skip the prepare phase.
*/
return 0;
}
int mv88e6xxx_port_fdb_add(struct dsa_switch *ds, int port,
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans)
{
int state = is_multicast_ether_addr(fdb->addr) ?
GLOBAL_ATU_DATA_STATE_MC_STATIC :
GLOBAL_ATU_DATA_STATE_UC_STATIC;
struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
int ret;
mutex_lock(&ps->smi_mutex);
ret = _mv88e6xxx_port_fdb_load(ds, port, addr, vid, state);
ret = _mv88e6xxx_port_fdb_load(ds, port, fdb->addr, fdb->vid, state);
mutex_unlock(&ps->smi_mutex);
return ret;
}
int mv88e6xxx_port_fdb_del(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid)
const struct switchdev_obj_port_fdb *fdb)
{
struct mv88e6xxx_priv_state *ps = ds_to_priv(ds);
int ret;
mutex_lock(&ps->smi_mutex);
ret = _mv88e6xxx_port_fdb_load(ds, port, addr, vid,
ret = _mv88e6xxx_port_fdb_load(ds, port, fdb->addr, fdb->vid,
GLOBAL_ATU_DATA_STATE_UNUSED);
mutex_unlock(&ps->smi_mutex);

View File

@ -474,10 +474,14 @@ int mv88e6xxx_port_vlan_add(struct dsa_switch *ds, int port, u16 vid,
int mv88e6xxx_port_vlan_del(struct dsa_switch *ds, int port, u16 vid);
int mv88e6xxx_vlan_getnext(struct dsa_switch *ds, u16 *vid,
unsigned long *ports, unsigned long *untagged);
int mv88e6xxx_port_fdb_prepare(struct dsa_switch *ds, int port,
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans);
int mv88e6xxx_port_fdb_add(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid);
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans);
int mv88e6xxx_port_fdb_del(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid);
const struct switchdev_obj_port_fdb *fdb);
int mv88e6xxx_port_fdb_getnext(struct dsa_switch *ds, int port,
unsigned char *addr, u16 *vid, bool *is_static);
int mv88e6xxx_phy_page_read(struct dsa_switch *ds, int port, int page, int reg);

View File

@ -197,6 +197,9 @@ static inline u8 dsa_upstream_port(struct dsa_switch *ds)
return ds->pd->rtable[dst->cpu_switch];
}
struct switchdev_trans;
struct switchdev_obj_port_fdb;
struct dsa_switch_driver {
struct list_head list;
@ -316,10 +319,14 @@ struct dsa_switch_driver {
/*
* Forwarding database
*/
int (*port_fdb_prepare)(struct dsa_switch *ds, int port,
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans);
int (*port_fdb_add)(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid);
const struct switchdev_obj_port_fdb *fdb,
struct switchdev_trans *trans);
int (*port_fdb_del)(struct dsa_switch *ds, int port,
const unsigned char *addr, u16 vid);
const struct switchdev_obj_port_fdb *fdb);
int (*port_fdb_getnext)(struct dsa_switch *ds, int port,
unsigned char *addr, u16 *vid,
bool *is_static);

View File

@ -346,12 +346,15 @@ static int dsa_slave_port_fdb_add(struct net_device *dev,
{
struct dsa_slave_priv *p = netdev_priv(dev);
struct dsa_switch *ds = p->parent;
int ret = -EOPNOTSUPP;
int ret;
if (!ds->drv->port_fdb_prepare || !ds->drv->port_fdb_add)
return -EOPNOTSUPP;
if (switchdev_trans_ph_prepare(trans))
ret = ds->drv->port_fdb_add ? 0 : -EOPNOTSUPP;
ret = ds->drv->port_fdb_prepare(ds, p->port, fdb, trans);
else
ret = ds->drv->port_fdb_add(ds, p->port, fdb->addr, fdb->vid);
ret = ds->drv->port_fdb_add(ds, p->port, fdb, trans);
return ret;
}
@ -364,7 +367,7 @@ static int dsa_slave_port_fdb_del(struct net_device *dev,
int ret = -EOPNOTSUPP;
if (ds->drv->port_fdb_del)
ret = ds->drv->port_fdb_del(ds, p->port, fdb->addr, fdb->vid);
ret = ds->drv->port_fdb_del(ds, p->port, fdb);
return ret;
}