Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1cab3da6 authored by Daniel Lezcano's avatar Daniel Lezcano Committed by David S. Miller
Browse files

[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: default avatarDaniel Lezcano <dlezcano@fr.ibm.com>
Signed-off-by: default avatarBenjamin Thery <benjamin.thery@bull.net>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 06bfe655
Loading
Loading
Loading
Loading
+5 −3
Original line number Diff line number Diff line
@@ -67,9 +67,11 @@ extern int ipv6_chk_addr(struct net *net,
#if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
extern int			ipv6_chk_home_addr(struct in6_addr *addr);
#endif
extern struct inet6_ifaddr *	ipv6_get_ifaddr(struct in6_addr *addr,
extern struct inet6_ifaddr      *ipv6_get_ifaddr(struct net *net,
						 struct in6_addr *addr,
						 struct net_device *dev,
						 int strict);

extern int			ipv6_get_saddr(struct dst_entry *dst, 
					       struct in6_addr *daddr,
					       struct in6_addr *saddr);
+7 −4
Original line number Diff line number Diff line
@@ -1247,13 +1247,16 @@ int ipv6_chk_same_addr(struct net *net, const struct in6_addr *addr,
	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;
	u8 hash = ipv6_addr_hash(addr);

	read_lock_bh(&addrconf_hash_lock);
	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 (dev == NULL || ifp->idev->dev == dev ||
			    !(ifp->scope&(IFA_LINK|IFA_HOST) || strict)) {
@@ -1739,7 +1742,7 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len)

ok:

		ifp = ipv6_get_ifaddr(&addr, dev, 1);
		ifp = ipv6_get_ifaddr(&init_net, &addr, dev, 1);

		if (ifp == NULL && valid_lft) {
			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. */
	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) {
		/*
		 * 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)
		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;
		goto errout;
	}
+2 −1
Original line number Diff line number Diff line
@@ -936,7 +936,8 @@ static int ip6_dst_lookup_tail(struct sock *sk,
			struct flowi fl_gw;
			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);
			if (ifp)
+5 −4
Original line number Diff line number Diff line
@@ -556,7 +556,7 @@ static void ndisc_send_na(struct net_device *dev, struct neighbour *neigh,
	};

	/* 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) {
		src_addr = solicited_addr;
		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.
	 */
	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->flags & IFA_F_OPTIMISTIC)  {
				send_sllao = 0;
@@ -741,7 +742,7 @@ static void ndisc_recv_ns(struct sk_buff *skb)

	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 (dad) {
@@ -899,7 +900,7 @@ static void ndisc_recv_na(struct sk_buff *skb)
			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) {
			addrconf_dad_failure(ifp);
			return;