The problem that IPv6 address not catched by this function.
There is ip_dev_find function in the kernel for IPv4 protocol, but no analog 
for IPv6.
The solution is to use ipv6_chk_addr function for each network device found in 
the system.
The small problem that the same action  ( ip_dev_find ) executed in another 
place ( addr_resolve_local ),
so it may be better write local, static no exported ipv6_dev_find function and 
used it 
from addr_resolve_local and rdma_translate_ip instead write the same code twice.




Signed-off-by: Aleksey Senin <[EMAIL PROTECTED]>
---
 drivers/infiniband/core/addr.c |   30 +++++++++++++++++++++++-------
 1 files changed, 23 insertions(+), 7 deletions(-)

diff --git a/drivers/infiniband/core/addr.c b/drivers/infiniband/core/addr.c
index b59ad53..f95d21f 100644
--- a/drivers/infiniband/core/addr.c
+++ b/drivers/infiniband/core/addr.c
@@ -41,6 +41,7 @@
 #include <net/neighbour.h>
 #include <net/route.h>
 #include <net/netevent.h>
+#include <net/addrconf.h>
 #include <rdma/ib_addr.h>
 
 MODULE_AUTHOR("Sean Hefty");
@@ -113,15 +114,30 @@ EXPORT_SYMBOL(rdma_copy_addr);
 int rdma_translate_ip(struct sockaddr *addr, struct rdma_dev_addr *dev_addr)
 {
        struct net_device *dev;
-       __be32 ip = ((struct sockaddr_in *) addr)->sin_addr.s_addr;
-       int ret;
+       int ret = -EADDRNOTAVAIL;
 
-       dev = ip_dev_find(&init_net, ip);
-       if (!dev)
-               return -EADDRNOTAVAIL;
+       switch (addr->sa_family) {
+       case AF_INET:
+               dev = ip_dev_find(&init_net,
+                       ((struct sockaddr_in *) addr)->sin_addr.s_addr);
 
-       ret = rdma_copy_addr(dev_addr, dev, NULL);
-       dev_put(dev);
+               if (!dev)
+                       return -EADDRNOTAVAIL;
+
+               ret = rdma_copy_addr(dev_addr, dev, NULL);
+               dev_put(dev);
+               break;
+       case AF_INET6:
+               for_each_netdev(&init_net, dev) {
+                       if (ipv6_chk_addr(&init_net, &((struct sockaddr_in6 *) 
addr)->sin6_addr, dev, 1)) {
+                               ret = rdma_copy_addr(dev_addr, dev, NULL);
+                               break;
+                       }
+               }
+               break;
+       default:
+               break;
+       }
        return ret;
 }
 EXPORT_SYMBOL(rdma_translate_ip);
-- 
1.5.6.dirty


_______________________________________________
general mailing list
[email protected]
http://lists.openfabrics.org/cgi-bin/mailman/listinfo/general

To unsubscribe, please visit http://openib.org/mailman/listinfo/openib-general

Reply via email to