[PATCH V3] net-next: dsa: add FIB support

Subsystems: documentation, networking [dsa], networking [general], the rest

STALE3682d

4 messages, 2 authors, 2016-09-13 · open the first message on its own page

[PATCH V3] net-next: dsa: add FIB support

From: John Crispin <john@phrozen.org>
Date: 2016-09-13 06:02:41

Add SWITCHDEV_OBJ_ID_IPV4_FIB support to the DSA layer.

Signed-off-by: John Crispin <john@phrozen.org>
---
Changes in V2
* rebase on latest net-next to fix compile errors

Changes in V3
* fix subject prefix. this needs to go into the next tree

 Documentation/networking/dsa/dsa.txt |   18 +++++++++++++++
 include/net/dsa.h                    |   13 +++++++++++
 net/dsa/slave.c                      |   41 ++++++++++++++++++++++++++++++++++
 3 files changed, 72 insertions(+)
diff --git a/Documentation/networking/dsa/dsa.txt b/Documentation/networking/dsa/dsa.txt
index 6d6c07c..6cd5831 100644
--- a/Documentation/networking/dsa/dsa.txt
+++ b/Documentation/networking/dsa/dsa.txt
@@ -607,6 +607,24 @@ of DSA, would be the its port-based VLAN, used by the associated bridge device.
   function that the driver has to call for each MAC address known to be behind
   the given port. A switchdev object is used to carry the VID and MDB info.
 
+Route offloading
+----------------
+
+- ipv4_fib_prepare: routing layer function invoked to prepare the installation
+  of an ipv4 route into the switches routing database. If the operation is not
+  supported this function should return -EOPNOTSUPP. No hardware setup must be
+  done in this function. See ipv4_fib_add for this and details.
+
+- ipv4_fib_add: routing layer function invoked when a new ipv4 route should be
+  installed into the routing database of the switch, it should be programmed
+  with the route for the specified VLAN ID of the device that the route applies
+  to.
+
+- ipv4_fib_del: routing layer function invoked when an ipv4 route should be
+  removed from the routing database, the switch hardware should be programmed
+  to delete the specified MAC address of the nexthop from the specified VLAN ID
+  if it was mapped into the forwarding database.
+
 TODO
 ====
 
diff --git a/include/net/dsa.h b/include/net/dsa.h
index 7556646..7fdd63e 100644
--- a/include/net/dsa.h
+++ b/include/net/dsa.h
@@ -237,6 +237,7 @@ struct switchdev_obj;
 struct switchdev_obj_port_fdb;
 struct switchdev_obj_port_mdb;
 struct switchdev_obj_port_vlan;
+struct switchdev_obj_ipv4_fib;
 
 struct dsa_switch_ops {
 	struct list_head	list;
@@ -386,6 +387,18 @@ struct dsa_switch_ops {
 	int	(*port_mdb_dump)(struct dsa_switch *ds, int port,
 				 struct switchdev_obj_port_mdb *mdb,
 				 int (*cb)(struct switchdev_obj *obj));
+
+	/*
+	 * IPV4 routing
+	 */
+	int	(*ipv4_fib_prepare)(struct dsa_switch *ds, int port,
+				    const struct switchdev_obj_ipv4_fib *fib4,
+				    struct switchdev_trans *trans);
+	int	(*ipv4_fib_add)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4,
+				struct switchdev_trans *trans);
+	int	(*ipv4_fib_del)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4);
 };
 
 void register_switch_driver(struct dsa_switch_ops *type);
diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 9ecbe78..c974ac0 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -334,6 +334,38 @@ static int dsa_slave_port_mdb_dump(struct net_device *dev,
 	return -EOPNOTSUPP;
 }
 
+static int dsa_slave_ipv4_fib_add(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4,
+				  struct switchdev_trans *trans)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret;
+
+	if (!ds->ops->ipv4_fib_prepare || !ds->ops->ipv4_fib_add)
+		return -EOPNOTSUPP;
+
+	if (switchdev_trans_ph_prepare(trans))
+		ret = ds->ops->ipv4_fib_prepare(ds, p->port, fib4, trans);
+	else
+		ret = ds->ops->ipv4_fib_add(ds, p->port, fib4, trans);
+
+	return ret;
+}
+
+static int dsa_slave_ipv4_fib_del(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret = -EOPNOTSUPP;
+
+	if (ds->ops->ipv4_fib_del)
+		ret = ds->ops->ipv4_fib_del(ds, p->port, fib4);
+
+	return ret;
+}
+
 static int dsa_slave_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
 {
 	struct dsa_slave_priv *p = netdev_priv(dev);
@@ -465,6 +497,11 @@ static int dsa_slave_port_obj_add(struct net_device *dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj),
 					      trans);
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_add(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj),
+					     trans);
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
@@ -490,6 +527,10 @@ static int dsa_slave_port_obj_del(struct net_device *dev,
 		err = dsa_slave_port_vlan_del(dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj));
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_del(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj));
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
-- 
1.7.10.4

Re: [PATCH V3] net-next: dsa: add FIB support

From: Vivien Didelot <hidden>
Date: 2016-09-13 16:21:47

Hi John,

John Crispin [off-list ref] writes:
quoted hunk
@@ -237,6 +237,7 @@ struct switchdev_obj;
 struct switchdev_obj_port_fdb;
 struct switchdev_obj_port_mdb;
 struct switchdev_obj_port_vlan;
+struct switchdev_obj_ipv4_fib;
Can you keep it ordered please (put obj_ipv4 above port_fdb).
quoted hunk
 
 struct dsa_switch_ops {
 	struct list_head	list;
@@ -386,6 +387,18 @@ struct dsa_switch_ops {
 	int	(*port_mdb_dump)(struct dsa_switch *ds, int port,
 				 struct switchdev_obj_port_mdb *mdb,
 				 int (*cb)(struct switchdev_obj *obj));
+
+	/*
+	 * IPV4 routing
+	 */
+	int	(*ipv4_fib_prepare)(struct dsa_switch *ds, int port,
+				    const struct switchdev_obj_ipv4_fib *fib4,
+				    struct switchdev_trans *trans);
+	int	(*ipv4_fib_add)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4,
+				struct switchdev_trans *trans);
DSA *_add ops should return void, since no error is supposed to occure in
the commit phase.

If they are port-based operations, please prefix them with "port_",
otherwise, the int port parameter is not necessary.
quoted hunk
+	int	(*ipv4_fib_del)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4);
 };
 
 void register_switch_driver(struct dsa_switch_ops *type);
diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 9ecbe78..c974ac0 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -334,6 +334,38 @@ static int dsa_slave_port_mdb_dump(struct net_device *dev,
 	return -EOPNOTSUPP;
 }
 
+static int dsa_slave_ipv4_fib_add(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4,
+				  struct switchdev_trans *trans)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret;
+
+	if (!ds->ops->ipv4_fib_prepare || !ds->ops->ipv4_fib_add)
+		return -EOPNOTSUPP;
+
+	if (switchdev_trans_ph_prepare(trans))
+		ret = ds->ops->ipv4_fib_prepare(ds, p->port, fib4, trans);
+	else
+		ret = ds->ops->ipv4_fib_add(ds, p->port, fib4, trans);
+
+	return ret;
+}
Please see dsa_slave_port_vlan_add for a better logic with the prepare
phase and void add routine.
quoted hunk
+
+static int dsa_slave_ipv4_fib_del(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret = -EOPNOTSUPP;
+
+	if (ds->ops->ipv4_fib_del)
+		ret = ds->ops->ipv4_fib_del(ds, p->port, fib4);
+
+	return ret;
+}
Just curious, isn't there a dump operation for SWITCHDEV_OBJ_ID_IPV4_FIB?
quoted hunk
+
 static int dsa_slave_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
 {
 	struct dsa_slave_priv *p = netdev_priv(dev);
@@ -465,6 +497,11 @@ static int dsa_slave_port_obj_add(struct net_device *dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj),
 					      trans);
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_add(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj),
+					     trans);
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
@@ -490,6 +527,10 @@ static int dsa_slave_port_obj_del(struct net_device *dev,
 		err = dsa_slave_port_vlan_del(dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj));
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_del(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj));
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
Please keep the SWITCHDEV_OBJ_ID_IPV4_FIB case ordered with other cases
as well.

I'm adding Jiri's in the loop, since he has started a thread on FIB
notifications a few days ago, his feedback might be interesting. If I'm
not mistaken, there is a plan to factorize FID routines (not sure).

Thanks,

        Vivien

Re: [PATCH V3] net-next: dsa: add FIB support

From: John Crispin <john@phrozen.org>
Date: 2016-09-13 16:27:54


On 13/09/2016 18:21, Vivien Didelot wrote:
Hi John,

John Crispin [off-list ref] writes:
quoted
@@ -237,6 +237,7 @@ struct switchdev_obj;
 struct switchdev_obj_port_fdb;
 struct switchdev_obj_port_mdb;
 struct switchdev_obj_port_vlan;
+struct switchdev_obj_ipv4_fib;
Can you keep it ordered please (put obj_ipv4 above port_fdb).
quoted
 
 struct dsa_switch_ops {
 	struct list_head	list;
@@ -386,6 +387,18 @@ struct dsa_switch_ops {
 	int	(*port_mdb_dump)(struct dsa_switch *ds, int port,
 				 struct switchdev_obj_port_mdb *mdb,
 				 int (*cb)(struct switchdev_obj *obj));
+
+	/*
+	 * IPV4 routing
+	 */
+	int	(*ipv4_fib_prepare)(struct dsa_switch *ds, int port,
+				    const struct switchdev_obj_ipv4_fib *fib4,
+				    struct switchdev_trans *trans);
+	int	(*ipv4_fib_add)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4,
+				struct switchdev_trans *trans);
DSA *_add ops should return void, since no error is supposed to occure in
the commit phase.

If they are port-based operations, please prefix them with "port_",
otherwise, the int port parameter is not necessary.
quoted
+	int	(*ipv4_fib_del)(struct dsa_switch *ds, int port,
+				const struct switchdev_obj_ipv4_fib *fib4);
 };
 
 void register_switch_driver(struct dsa_switch_ops *type);
diff --git a/net/dsa/slave.c b/net/dsa/slave.c
index 9ecbe78..c974ac0 100644
--- a/net/dsa/slave.c
+++ b/net/dsa/slave.c
@@ -334,6 +334,38 @@ static int dsa_slave_port_mdb_dump(struct net_device *dev,
 	return -EOPNOTSUPP;
 }
 
+static int dsa_slave_ipv4_fib_add(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4,
+				  struct switchdev_trans *trans)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret;
+
+	if (!ds->ops->ipv4_fib_prepare || !ds->ops->ipv4_fib_add)
+		return -EOPNOTSUPP;
+
+	if (switchdev_trans_ph_prepare(trans))
+		ret = ds->ops->ipv4_fib_prepare(ds, p->port, fib4, trans);
+	else
+		ret = ds->ops->ipv4_fib_add(ds, p->port, fib4, trans);
+
+	return ret;
+}
Please see dsa_slave_port_vlan_add for a better logic with the prepare
phase and void add routine.
quoted
+
+static int dsa_slave_ipv4_fib_del(struct net_device *dev,
+				  const struct switchdev_obj_ipv4_fib *fib4)
+{
+	struct dsa_slave_priv *p = netdev_priv(dev);
+	struct dsa_switch *ds = p->parent;
+	int ret = -EOPNOTSUPP;
+
+	if (ds->ops->ipv4_fib_del)
+		ret = ds->ops->ipv4_fib_del(ds, p->port, fib4);
+
+	return ret;
+}
Just curious, isn't there a dump operation for SWITCHDEV_OBJ_ID_IPV4_FIB?
quoted
+
 static int dsa_slave_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
 {
 	struct dsa_slave_priv *p = netdev_priv(dev);
@@ -465,6 +497,11 @@ static int dsa_slave_port_obj_add(struct net_device *dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj),
 					      trans);
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_add(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj),
+					     trans);
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
@@ -490,6 +527,10 @@ static int dsa_slave_port_obj_del(struct net_device *dev,
 		err = dsa_slave_port_vlan_del(dev,
 					      SWITCHDEV_OBJ_PORT_VLAN(obj));
 		break;
+	case SWITCHDEV_OBJ_ID_IPV4_FIB:
+		err = dsa_slave_ipv4_fib_del(dev,
+					     SWITCHDEV_OBJ_IPV4_FIB(obj));
+		break;
 	default:
 		err = -EOPNOTSUPP;
 		break;
Please keep the SWITCHDEV_OBJ_ID_IPV4_FIB case ordered with other cases
as well.

I'm adding Jiri's in the loop, since he has started a thread on FIB
notifications a few days ago, his feedback might be interesting. If I'm
not mistaken, there is a plan to factorize FID routines (not sure).

Thanks,

        Vivien
Hi Vivien,

i sent an email to Jiri earlier today and he asked me to drop this until
his notification series got merged.

	John

Re: [PATCH V3] net-next: dsa: add FIB support

From: Vivien Didelot <hidden>
Date: 2016-09-13 16:35:00

Hi John,

John Crispin [off-list ref] writes:
i sent an email to Jiri earlier today and he asked me to drop this
until his notification series got merged.
That makes sense then. So David should ignore this for the moment.

Thanks,

        Vivien
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help