* [PATCH net-next 0/2] net: l3mdev: Allow send on enslaved interface @ 2016-05-05 4:54 David Ahern 2016-05-05 4:54 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern 2016-05-05 4:54 ` [PATCH net-next 2/2] net: l3mdev: Allow send on enslaved interface David Ahern 0 siblings, 2 replies; 5+ messages in thread From: David Ahern @ 2016-05-05 4:54 UTC (permalink / raw) To: netdev; +Cc: David Ahern First patch preps for the second. The second is required for several use cases such as ping on an interface and BFD that need to send packets on a specific interface, including ones enslaved to a VRF device. David Ahern (2): net: l3mdev: Move get_saddr and rt6_dst net: l3mdev: Allow send on enslaved interface drivers/net/vrf.c | 2 ++ include/net/l3mdev.h | 56 +++----------------------------------------- net/ipv4/route.c | 4 ++++ net/ipv6/route.c | 2 +- net/l3mdev/l3mdev.c | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 5 files changed, 75 insertions(+), 54 deletions(-) -- 2.1.4 ^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst 2016-05-05 4:54 [PATCH net-next 0/2] net: l3mdev: Allow send on enslaved interface David Ahern @ 2016-05-05 4:54 ` David Ahern 2016-05-07 19:01 ` David Miller 2016-05-05 4:54 ` [PATCH net-next 2/2] net: l3mdev: Allow send on enslaved interface David Ahern 1 sibling, 1 reply; 5+ messages in thread From: David Ahern @ 2016-05-05 4:54 UTC (permalink / raw) To: netdev; +Cc: David Ahern Move l3mdev_rt6_dst_by_oif and l3mdev_get_saddr to l3mdev.c. Collapse l3mdev_get_rt6_dst into l3mdev_rt6_dst_by_oif since it is the only user and keep the l3mdev_get_rt6_dst name for consistency with other hooks. A follow-on patch adds more code to these functions making them long for inlined functions. Signed-off-by: David Ahern <dsa@cumulusnetworks.com> --- include/net/l3mdev.h | 56 +++------------------------------------------------- net/ipv6/route.c | 2 +- net/l3mdev/l3mdev.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 59 insertions(+), 54 deletions(-) diff --git a/include/net/l3mdev.h b/include/net/l3mdev.h index c43a9c73de5e..78872bd1dc2c 100644 --- a/include/net/l3mdev.h +++ b/include/net/l3mdev.h @@ -130,52 +130,9 @@ static inline bool netif_index_is_l3_master(struct net *net, int ifindex) return rc; } -static inline int l3mdev_get_saddr(struct net *net, int ifindex, - struct flowi4 *fl4) -{ - struct net_device *dev; - int rc = 0; - - if (ifindex) { - - rcu_read_lock(); - - dev = dev_get_by_index_rcu(net, ifindex); - if (dev && netif_is_l3_master(dev) && - dev->l3mdev_ops->l3mdev_get_saddr) { - rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); - } - - rcu_read_unlock(); - } - - return rc; -} +int l3mdev_get_saddr(struct net *net, int ifindex, struct flowi4 *fl4); -static inline struct dst_entry *l3mdev_get_rt6_dst(const struct net_device *dev, - const struct flowi6 *fl6) -{ - if (netif_is_l3_master(dev) && dev->l3mdev_ops->l3mdev_get_rt6_dst) - return dev->l3mdev_ops->l3mdev_get_rt6_dst(dev, fl6); - - return NULL; -} - -static inline -struct dst_entry *l3mdev_rt6_dst_by_oif(struct net *net, - const struct flowi6 *fl6) -{ - struct dst_entry *dst = NULL; - struct net_device *dev; - - dev = dev_get_by_index(net, fl6->flowi6_oif); - if (dev) { - dst = l3mdev_get_rt6_dst(dev, fl6); - dev_put(dev); - } - - return dst; -} +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, const struct flowi6 *fl6); #else @@ -233,14 +190,7 @@ static inline int l3mdev_get_saddr(struct net *net, int ifindex, } static inline -struct dst_entry *l3mdev_get_rt6_dst(const struct net_device *dev, - const struct flowi6 *fl6) -{ - return NULL; -} -static inline -struct dst_entry *l3mdev_rt6_dst_by_oif(struct net *net, - const struct flowi6 *fl6) +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, const struct flowi6 *fl6) { return NULL; } diff --git a/net/ipv6/route.c b/net/ipv6/route.c index af46e19205f5..c42fa1deb152 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -1190,7 +1190,7 @@ struct dst_entry *ip6_route_output_flags(struct net *net, const struct sock *sk, struct dst_entry *dst; bool any_src; - dst = l3mdev_rt6_dst_by_oif(net, fl6); + dst = l3mdev_get_rt6_dst(net, fl6); if (dst) return dst; diff --git a/net/l3mdev/l3mdev.c b/net/l3mdev/l3mdev.c index e925037fa0df..0fe4211e646f 100644 --- a/net/l3mdev/l3mdev.c +++ b/net/l3mdev/l3mdev.c @@ -97,3 +97,58 @@ u32 l3mdev_fib_table_by_index(struct net *net, int ifindex) return tb_id; } EXPORT_SYMBOL_GPL(l3mdev_fib_table_by_index); + +/** + * l3mdev_get_rt6_dst - IPv6 route lookup based on flow. Returns + * cached route for L3 master device if relevant + * to flow + * @net: network namespace for device index lookup + * @fl6: IPv6 flow struct for lookup + */ + +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, + const struct flowi6 *fl6) +{ + struct dst_entry *dst = NULL; + struct net_device *dev; + + dev = dev_get_by_index(net, fl6->flowi6_oif); + if (dev) { + if (netif_is_l3_master(dev) && + dev->l3mdev_ops->l3mdev_get_rt6_dst) + dst = dev->l3mdev_ops->l3mdev_get_rt6_dst(dev, fl6); + dev_put(dev); + } + + return dst; +} +EXPORT_SYMBOL_GPL(l3mdev_get_rt6_dst); + +/** + * l3mdev_get_saddr - get source address for a flow based on an interface + * enslaved to an L3 master device + * @net: network namespace for device index lookup + * @ifindex: Interface index + * @fl4: IPv4 flow struct + */ + +int l3mdev_get_saddr(struct net *net, int ifindex, struct flowi4 *fl4) +{ + struct net_device *dev; + int rc = 0; + + if (ifindex) { + rcu_read_lock(); + + dev = dev_get_by_index_rcu(net, ifindex); + if (dev && netif_is_l3_master(dev) && + dev->l3mdev_ops->l3mdev_get_saddr) { + rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); + } + + rcu_read_unlock(); + } + + return rc; +} +EXPORT_SYMBOL_GPL(l3mdev_get_saddr); -- 2.1.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* Re: [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst 2016-05-05 4:54 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern @ 2016-05-07 19:01 ` David Miller 0 siblings, 0 replies; 5+ messages in thread From: David Miller @ 2016-05-07 19:01 UTC (permalink / raw) To: dsa; +Cc: netdev From: David Ahern <dsa@cumulusnetworks.com> Date: Wed, 4 May 2016 21:54:09 -0700 > + if (dev && netif_is_l3_master(dev) && > + dev->l3mdev_ops->l3mdev_get_saddr) { > + rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); > + } Please do not use braces for single statement basic blocks. The same issue exists in patch #2 so please fix it there as well. Thanks. ^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH net-next 2/2] net: l3mdev: Allow send on enslaved interface 2016-05-05 4:54 [PATCH net-next 0/2] net: l3mdev: Allow send on enslaved interface David Ahern 2016-05-05 4:54 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern @ 2016-05-05 4:54 ` David Ahern 1 sibling, 0 replies; 5+ messages in thread From: David Ahern @ 2016-05-05 4:54 UTC (permalink / raw) To: netdev; +Cc: David Ahern Allow udp and raw sockets to send by oif that is an enslaved interface versus the l3mdev/VRF device. For example, this allows BFD to use ifindex from IP_PKTINFO on a receive to send a response without the need to convert to the VRF index. It also allows ping and ping6 to work when specifying an enslaved interface (e.g., ping -I swp1 <ip>) which is a natural use case. Signed-off-by: David Ahern <dsa@cumulusnetworks.com> --- drivers/net/vrf.c | 2 ++ net/ipv4/route.c | 4 ++++ net/l3mdev/l3mdev.c | 20 +++++++++++++++----- 3 files changed, 21 insertions(+), 5 deletions(-) diff --git a/drivers/net/vrf.c b/drivers/net/vrf.c index 4b2461ae5d3b..c8db55aa8280 100644 --- a/drivers/net/vrf.c +++ b/drivers/net/vrf.c @@ -648,6 +648,8 @@ static int vrf_get_saddr(struct net_device *dev, struct flowi4 *fl4) fl4->flowi4_flags |= FLOWI_FLAG_SKIP_NH_OIF; fl4->flowi4_iif = LOOPBACK_IFINDEX; + /* make sure oif is set to VRF device for lookup */ + fl4->flowi4_oif = dev->ifindex; fl4->flowi4_tos = tos & IPTOS_RT_MASK; fl4->flowi4_scope = ((tos & RTO_ONLINK) ? RT_SCOPE_LINK : RT_SCOPE_UNIVERSE); diff --git a/net/ipv4/route.c b/net/ipv4/route.c index 8c8c655bb2c4..a1f2830d8110 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c @@ -2146,6 +2146,7 @@ struct rtable *__ip_route_output_key_hash(struct net *net, struct flowi4 *fl4, unsigned int flags = 0; struct fib_result res; struct rtable *rth; + int master_idx; int orig_oif; int err = -ENETUNREACH; @@ -2155,6 +2156,9 @@ struct rtable *__ip_route_output_key_hash(struct net *net, struct flowi4 *fl4, orig_oif = fl4->flowi4_oif; + master_idx = l3mdev_master_ifindex_by_index(net, fl4->flowi4_oif); + if (master_idx) + fl4->flowi4_oif = master_idx; fl4->flowi4_iif = LOOPBACK_IFINDEX; fl4->flowi4_tos = tos & IPTOS_RT_MASK; fl4->flowi4_scope = ((tos & RTO_ONLINK) ? diff --git a/net/l3mdev/l3mdev.c b/net/l3mdev/l3mdev.c index 0fe4211e646f..0fd8cc1417cd 100644 --- a/net/l3mdev/l3mdev.c +++ b/net/l3mdev/l3mdev.c @@ -112,12 +112,19 @@ struct dst_entry *l3mdev_get_rt6_dst(struct net *net, struct dst_entry *dst = NULL; struct net_device *dev; - dev = dev_get_by_index(net, fl6->flowi6_oif); - if (dev) { - if (netif_is_l3_master(dev) && - dev->l3mdev_ops->l3mdev_get_rt6_dst) + if (fl6->flowi6_oif) { + rcu_read_lock(); + + dev = dev_get_by_index_rcu(net, fl6->flowi6_oif); + if (dev && netif_is_l3_slave(dev)) + dev = netdev_master_upper_dev_get_rcu(dev); + + if (dev && netif_is_l3_master(dev) && + dev->l3mdev_ops->l3mdev_get_rt6_dst) { dst = dev->l3mdev_ops->l3mdev_get_rt6_dst(dev, fl6); - dev_put(dev); + } + + rcu_read_unlock(); } return dst; @@ -141,6 +148,9 @@ int l3mdev_get_saddr(struct net *net, int ifindex, struct flowi4 *fl4) rcu_read_lock(); dev = dev_get_by_index_rcu(net, ifindex); + if (dev && netif_is_l3_slave(dev)) + dev = netdev_master_upper_dev_get_rcu(dev); + if (dev && netif_is_l3_master(dev) && dev->l3mdev_ops->l3mdev_get_saddr) { rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); -- 2.1.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH net-next v2 0/2] net: l3mdev: Allow send on enslaved interface @ 2016-05-07 23:48 David Ahern 2016-05-07 23:48 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern 0 siblings, 1 reply; 5+ messages in thread From: David Ahern @ 2016-05-07 23:48 UTC (permalink / raw) To: netdev; +Cc: David Ahern First patch preps for the second. The second is required for several use cases such as ping on an interface and BFD that need to send packets on a specific interface, including ones enslaved to a VRF device. v2 - fixed brackets on both patches per comment from DaveM David Ahern (2): net: l3mdev: Move get_saddr and rt6_dst net: l3mdev: Allow send on enslaved interface drivers/net/vrf.c | 2 ++ include/net/l3mdev.h | 56 +++------------------------------------------- net/ipv4/route.c | 4 ++++ net/ipv6/route.c | 2 +- net/l3mdev/l3mdev.c | 63 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 5 files changed, 73 insertions(+), 54 deletions(-) -- 2.1.4 ^ permalink raw reply [flat|nested] 5+ messages in thread
* [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst 2016-05-07 23:48 [PATCH net-next v2 0/2] " David Ahern @ 2016-05-07 23:48 ` David Ahern 0 siblings, 0 replies; 5+ messages in thread From: David Ahern @ 2016-05-07 23:48 UTC (permalink / raw) To: netdev; +Cc: David Ahern Move l3mdev_rt6_dst_by_oif and l3mdev_get_saddr to l3mdev.c. Collapse l3mdev_get_rt6_dst into l3mdev_rt6_dst_by_oif since it is the only user and keep the l3mdev_get_rt6_dst name for consistency with other hooks. A follow-on patch adds more code to these functions making them long for inlined functions. Signed-off-by: David Ahern <dsa@cumulusnetworks.com> --- include/net/l3mdev.h | 56 +++------------------------------------------------- net/ipv6/route.c | 2 +- net/l3mdev/l3mdev.c | 54 ++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 58 insertions(+), 54 deletions(-) diff --git a/include/net/l3mdev.h b/include/net/l3mdev.h index c43a9c73de5e..78872bd1dc2c 100644 --- a/include/net/l3mdev.h +++ b/include/net/l3mdev.h @@ -130,52 +130,9 @@ static inline bool netif_index_is_l3_master(struct net *net, int ifindex) return rc; } -static inline int l3mdev_get_saddr(struct net *net, int ifindex, - struct flowi4 *fl4) -{ - struct net_device *dev; - int rc = 0; - - if (ifindex) { - - rcu_read_lock(); - - dev = dev_get_by_index_rcu(net, ifindex); - if (dev && netif_is_l3_master(dev) && - dev->l3mdev_ops->l3mdev_get_saddr) { - rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); - } - - rcu_read_unlock(); - } - - return rc; -} +int l3mdev_get_saddr(struct net *net, int ifindex, struct flowi4 *fl4); -static inline struct dst_entry *l3mdev_get_rt6_dst(const struct net_device *dev, - const struct flowi6 *fl6) -{ - if (netif_is_l3_master(dev) && dev->l3mdev_ops->l3mdev_get_rt6_dst) - return dev->l3mdev_ops->l3mdev_get_rt6_dst(dev, fl6); - - return NULL; -} - -static inline -struct dst_entry *l3mdev_rt6_dst_by_oif(struct net *net, - const struct flowi6 *fl6) -{ - struct dst_entry *dst = NULL; - struct net_device *dev; - - dev = dev_get_by_index(net, fl6->flowi6_oif); - if (dev) { - dst = l3mdev_get_rt6_dst(dev, fl6); - dev_put(dev); - } - - return dst; -} +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, const struct flowi6 *fl6); #else @@ -233,14 +190,7 @@ static inline int l3mdev_get_saddr(struct net *net, int ifindex, } static inline -struct dst_entry *l3mdev_get_rt6_dst(const struct net_device *dev, - const struct flowi6 *fl6) -{ - return NULL; -} -static inline -struct dst_entry *l3mdev_rt6_dst_by_oif(struct net *net, - const struct flowi6 *fl6) +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, const struct flowi6 *fl6) { return NULL; } diff --git a/net/ipv6/route.c b/net/ipv6/route.c index af46e19205f5..c42fa1deb152 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -1190,7 +1190,7 @@ struct dst_entry *ip6_route_output_flags(struct net *net, const struct sock *sk, struct dst_entry *dst; bool any_src; - dst = l3mdev_rt6_dst_by_oif(net, fl6); + dst = l3mdev_get_rt6_dst(net, fl6); if (dst) return dst; diff --git a/net/l3mdev/l3mdev.c b/net/l3mdev/l3mdev.c index e925037fa0df..898d01e0f87b 100644 --- a/net/l3mdev/l3mdev.c +++ b/net/l3mdev/l3mdev.c @@ -97,3 +97,57 @@ u32 l3mdev_fib_table_by_index(struct net *net, int ifindex) return tb_id; } EXPORT_SYMBOL_GPL(l3mdev_fib_table_by_index); + +/** + * l3mdev_get_rt6_dst - IPv6 route lookup based on flow. Returns + * cached route for L3 master device if relevant + * to flow + * @net: network namespace for device index lookup + * @fl6: IPv6 flow struct for lookup + */ + +struct dst_entry *l3mdev_get_rt6_dst(struct net *net, + const struct flowi6 *fl6) +{ + struct dst_entry *dst = NULL; + struct net_device *dev; + + dev = dev_get_by_index(net, fl6->flowi6_oif); + if (dev) { + if (netif_is_l3_master(dev) && + dev->l3mdev_ops->l3mdev_get_rt6_dst) + dst = dev->l3mdev_ops->l3mdev_get_rt6_dst(dev, fl6); + dev_put(dev); + } + + return dst; +} +EXPORT_SYMBOL_GPL(l3mdev_get_rt6_dst); + +/** + * l3mdev_get_saddr - get source address for a flow based on an interface + * enslaved to an L3 master device + * @net: network namespace for device index lookup + * @ifindex: Interface index + * @fl4: IPv4 flow struct + */ + +int l3mdev_get_saddr(struct net *net, int ifindex, struct flowi4 *fl4) +{ + struct net_device *dev; + int rc = 0; + + if (ifindex) { + rcu_read_lock(); + + dev = dev_get_by_index_rcu(net, ifindex); + if (dev && netif_is_l3_master(dev) && + dev->l3mdev_ops->l3mdev_get_saddr) + rc = dev->l3mdev_ops->l3mdev_get_saddr(dev, fl4); + + rcu_read_unlock(); + } + + return rc; +} +EXPORT_SYMBOL_GPL(l3mdev_get_saddr); -- 2.1.4 ^ permalink raw reply related [flat|nested] 5+ messages in thread
end of thread, other threads:[~2016-05-07 23:49 UTC | newest] Thread overview: 5+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2016-05-05 4:54 [PATCH net-next 0/2] net: l3mdev: Allow send on enslaved interface David Ahern 2016-05-05 4:54 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern 2016-05-07 19:01 ` David Miller 2016-05-05 4:54 ` [PATCH net-next 2/2] net: l3mdev: Allow send on enslaved interface David Ahern -- strict thread matches above, loose matches on Subject: below -- 2016-05-07 23:48 [PATCH net-next v2 0/2] " David Ahern 2016-05-07 23:48 ` [PATCH net-next 1/2] net: l3mdev: Move get_saddr and rt6_dst David Ahern
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).