[NETNS][IPV6]: inet6_addr - ipv6_get_ifaddr namespace aware
The inet6_addr_lst is browsed taking into account the network namespace specified as parameter. If an address does not belong to the specified namespace, it is ignored. Signed-off-by: Daniel Lezcano <dlezcano@fr.ibm.com> Signed-off-by: Benjamin Thery <benjamin.thery@bull.net> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
06bfe655e7
commit
1cab3da6be
@ -67,9 +67,11 @@ extern int ipv6_chk_addr(struct net *net,
|
|||||||
#if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
|
#if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
|
||||||
extern int ipv6_chk_home_addr(struct in6_addr *addr);
|
extern int ipv6_chk_home_addr(struct in6_addr *addr);
|
||||||
#endif
|
#endif
|
||||||
extern struct inet6_ifaddr * ipv6_get_ifaddr(struct in6_addr *addr,
|
extern struct inet6_ifaddr *ipv6_get_ifaddr(struct net *net,
|
||||||
struct net_device *dev,
|
struct in6_addr *addr,
|
||||||
int strict);
|
struct net_device *dev,
|
||||||
|
int strict);
|
||||||
|
|
||||||
extern int ipv6_get_saddr(struct dst_entry *dst,
|
extern int ipv6_get_saddr(struct dst_entry *dst,
|
||||||
struct in6_addr *daddr,
|
struct in6_addr *daddr,
|
||||||
struct in6_addr *saddr);
|
struct in6_addr *saddr);
|
||||||
|
@ -1247,13 +1247,16 @@ int ipv6_chk_same_addr(struct net *net, const struct in6_addr *addr,
|
|||||||
return ifp != NULL;
|
return ifp != NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct inet6_ifaddr * ipv6_get_ifaddr(struct in6_addr *addr, struct net_device *dev, int strict)
|
struct inet6_ifaddr *ipv6_get_ifaddr(struct net *net, struct in6_addr *addr,
|
||||||
|
struct net_device *dev, int strict)
|
||||||
{
|
{
|
||||||
struct inet6_ifaddr * ifp;
|
struct inet6_ifaddr * ifp;
|
||||||
u8 hash = ipv6_addr_hash(addr);
|
u8 hash = ipv6_addr_hash(addr);
|
||||||
|
|
||||||
read_lock_bh(&addrconf_hash_lock);
|
read_lock_bh(&addrconf_hash_lock);
|
||||||
for(ifp = inet6_addr_lst[hash]; ifp; ifp=ifp->lst_next) {
|
for(ifp = inet6_addr_lst[hash]; ifp; ifp=ifp->lst_next) {
|
||||||
|
if (ifp->idev->dev->nd_net != net)
|
||||||
|
continue;
|
||||||
if (ipv6_addr_equal(&ifp->addr, addr)) {
|
if (ipv6_addr_equal(&ifp->addr, addr)) {
|
||||||
if (dev == NULL || ifp->idev->dev == dev ||
|
if (dev == NULL || ifp->idev->dev == dev ||
|
||||||
!(ifp->scope&(IFA_LINK|IFA_HOST) || strict)) {
|
!(ifp->scope&(IFA_LINK|IFA_HOST) || strict)) {
|
||||||
@ -1739,7 +1742,7 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len)
|
|||||||
|
|
||||||
ok:
|
ok:
|
||||||
|
|
||||||
ifp = ipv6_get_ifaddr(&addr, dev, 1);
|
ifp = ipv6_get_ifaddr(&init_net, &addr, dev, 1);
|
||||||
|
|
||||||
if (ifp == NULL && valid_lft) {
|
if (ifp == NULL && valid_lft) {
|
||||||
int max_addresses = in6_dev->cnf.max_addresses;
|
int max_addresses = in6_dev->cnf.max_addresses;
|
||||||
@ -3135,7 +3138,7 @@ inet6_rtm_newaddr(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg)
|
|||||||
/* We ignore other flags so far. */
|
/* We ignore other flags so far. */
|
||||||
ifa_flags = ifm->ifa_flags & (IFA_F_NODAD | IFA_F_HOMEADDRESS);
|
ifa_flags = ifm->ifa_flags & (IFA_F_NODAD | IFA_F_HOMEADDRESS);
|
||||||
|
|
||||||
ifa = ipv6_get_ifaddr(pfx, dev, 1);
|
ifa = ipv6_get_ifaddr(net, pfx, dev, 1);
|
||||||
if (ifa == NULL) {
|
if (ifa == NULL) {
|
||||||
/*
|
/*
|
||||||
* It would be best to check for !NLM_F_CREATE here but
|
* It would be best to check for !NLM_F_CREATE here but
|
||||||
@ -3442,7 +3445,7 @@ static int inet6_rtm_getaddr(struct sk_buff *in_skb, struct nlmsghdr* nlh,
|
|||||||
if (ifm->ifa_index)
|
if (ifm->ifa_index)
|
||||||
dev = __dev_get_by_index(&init_net, ifm->ifa_index);
|
dev = __dev_get_by_index(&init_net, ifm->ifa_index);
|
||||||
|
|
||||||
if ((ifa = ipv6_get_ifaddr(addr, dev, 1)) == NULL) {
|
if ((ifa = ipv6_get_ifaddr(net, addr, dev, 1)) == NULL) {
|
||||||
err = -EADDRNOTAVAIL;
|
err = -EADDRNOTAVAIL;
|
||||||
goto errout;
|
goto errout;
|
||||||
}
|
}
|
||||||
|
@ -936,7 +936,8 @@ static int ip6_dst_lookup_tail(struct sock *sk,
|
|||||||
struct flowi fl_gw;
|
struct flowi fl_gw;
|
||||||
int redirect;
|
int redirect;
|
||||||
|
|
||||||
ifp = ipv6_get_ifaddr(&fl->fl6_src, (*dst)->dev, 1);
|
ifp = ipv6_get_ifaddr(&init_net, &fl->fl6_src,
|
||||||
|
(*dst)->dev, 1);
|
||||||
|
|
||||||
redirect = (ifp && ifp->flags & IFA_F_OPTIMISTIC);
|
redirect = (ifp && ifp->flags & IFA_F_OPTIMISTIC);
|
||||||
if (ifp)
|
if (ifp)
|
||||||
|
@ -556,7 +556,7 @@ static void ndisc_send_na(struct net_device *dev, struct neighbour *neigh,
|
|||||||
};
|
};
|
||||||
|
|
||||||
/* for anycast or proxy, solicited_addr != src_addr */
|
/* for anycast or proxy, solicited_addr != src_addr */
|
||||||
ifp = ipv6_get_ifaddr(solicited_addr, dev, 1);
|
ifp = ipv6_get_ifaddr(&init_net, solicited_addr, dev, 1);
|
||||||
if (ifp) {
|
if (ifp) {
|
||||||
src_addr = solicited_addr;
|
src_addr = solicited_addr;
|
||||||
if (ifp->flags & IFA_F_OPTIMISTIC)
|
if (ifp->flags & IFA_F_OPTIMISTIC)
|
||||||
@ -616,7 +616,8 @@ void ndisc_send_rs(struct net_device *dev, struct in6_addr *saddr,
|
|||||||
* suppress the inclusion of the sllao.
|
* suppress the inclusion of the sllao.
|
||||||
*/
|
*/
|
||||||
if (send_sllao) {
|
if (send_sllao) {
|
||||||
struct inet6_ifaddr *ifp = ipv6_get_ifaddr(saddr, dev, 1);
|
struct inet6_ifaddr *ifp = ipv6_get_ifaddr(&init_net, saddr,
|
||||||
|
dev, 1);
|
||||||
if (ifp) {
|
if (ifp) {
|
||||||
if (ifp->flags & IFA_F_OPTIMISTIC) {
|
if (ifp->flags & IFA_F_OPTIMISTIC) {
|
||||||
send_sllao = 0;
|
send_sllao = 0;
|
||||||
@ -741,7 +742,7 @@ static void ndisc_recv_ns(struct sk_buff *skb)
|
|||||||
|
|
||||||
inc = ipv6_addr_is_multicast(daddr);
|
inc = ipv6_addr_is_multicast(daddr);
|
||||||
|
|
||||||
if ((ifp = ipv6_get_ifaddr(&msg->target, dev, 1)) != NULL) {
|
if ((ifp = ipv6_get_ifaddr(&init_net, &msg->target, dev, 1)) != NULL) {
|
||||||
|
|
||||||
if (ifp->flags & (IFA_F_TENTATIVE|IFA_F_OPTIMISTIC)) {
|
if (ifp->flags & (IFA_F_TENTATIVE|IFA_F_OPTIMISTIC)) {
|
||||||
if (dad) {
|
if (dad) {
|
||||||
@ -899,7 +900,7 @@ static void ndisc_recv_na(struct sk_buff *skb)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ((ifp = ipv6_get_ifaddr(&msg->target, dev, 1))) {
|
if ((ifp = ipv6_get_ifaddr(&init_net, &msg->target, dev, 1))) {
|
||||||
if (ifp->flags & IFA_F_TENTATIVE) {
|
if (ifp->flags & IFA_F_TENTATIVE) {
|
||||||
addrconf_dad_failure(ifp);
|
addrconf_dad_failure(ifp);
|
||||||
return;
|
return;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user