aboutsummaryrefslogtreecommitdiffstats
path: root/net/switchdev/switchdev.c
diff options
context:
space:
mode:
authorScott Feldman <sfeldma@gmail.com>2015-03-06 00:21:19 -0500
committerDavid S. Miller <davem@davemloft.net>2015-03-06 00:24:58 -0500
commit8e05fd7166c6123334b7a739a697d677747aa462 (patch)
tree92a66ecee7e1ff94f0314cd32e4fd65e2fd12741 /net/switchdev/switchdev.c
parent448b128a14501543748514a4f9adedd3c0da2e85 (diff)
fib: hook IPv4 fib for hardware offload
Call into the switchdev driver any time an IPv4 fib entry is added/modified/deleted from the kernel's FIB. The switchdev driver may or may not install the route to the offload device. In the case where the driver tries to install the route and something goes wrong (device's routing table is full, etc), then all of the offloaded routes will be flushed from the device, route forwarding falls back to the kernel, and no more routes are offloading. We can refine this logic later. For now, use the simplist model of offloading routes up to the point of failure, and then on failure, undo everything and mark IPv4 offloading disabled. Signed-off-by: Scott Feldman <sfeldma@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/switchdev/switchdev.c')
-rw-r--r--net/switchdev/switchdev.c28
1 files changed, 26 insertions, 2 deletions
diff --git a/net/switchdev/switchdev.c b/net/switchdev/switchdev.c
index 99907d829419..f4fd575aa2a3 100644
--- a/net/switchdev/switchdev.c
+++ b/net/switchdev/switchdev.c
@@ -305,8 +305,12 @@ int netdev_switch_fib_ipv4_add(u32 dst, int dst_len, struct fib_info *fi,
305 const struct net_device_ops *ops; 305 const struct net_device_ops *ops;
306 int err = 0; 306 int err = 0;
307 307
308 /* Don't offload route if using custom ip rules */ 308 /* Don't offload route if using custom ip rules or if
309 if (fi->fib_net->ipv4.fib_has_custom_rules) 309 * IPv4 FIB offloading has been disabled completely.
310 */
311
312 if (fi->fib_net->ipv4.fib_has_custom_rules |
313 fi->fib_net->ipv4.fib_offload_disabled)
310 return 0; 314 return 0;
311 315
312 dev = netdev_switch_get_dev_by_nhs(fi); 316 dev = netdev_switch_get_dev_by_nhs(fi);
@@ -362,3 +366,23 @@ int netdev_switch_fib_ipv4_del(u32 dst, int dst_len, struct fib_info *fi,
362 return err; 366 return err;
363} 367}
364EXPORT_SYMBOL(netdev_switch_fib_ipv4_del); 368EXPORT_SYMBOL(netdev_switch_fib_ipv4_del);
369
370/**
371 * netdev_switch_fib_ipv4_abort - Abort an IPv4 FIB operation
372 *
373 * @fi: route FIB info structure
374 */
375void netdev_switch_fib_ipv4_abort(struct fib_info *fi)
376{
377 /* There was a problem installing this route to the offload
378 * device. For now, until we come up with more refined
379 * policy handling, abruptly end IPv4 fib offloading for
380 * for entire net by flushing offload device(s) of all
381 * IPv4 routes, and mark IPv4 fib offloading broken from
382 * this point forward.
383 */
384
385 fib_flush_external(fi->fib_net);
386 fi->fib_net->ipv4.fib_offload_disabled = true;
387}
388EXPORT_SYMBOL(netdev_switch_fib_ipv4_abort);