aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/infiniband
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/infiniband')
-rw-r--r--drivers/infiniband/core/cma.c86
1 files changed, 60 insertions, 26 deletions
diff --git a/drivers/infiniband/core/cma.c b/drivers/infiniband/core/cma.c
index d951896ff7fc..2a2e50871b40 100644
--- a/drivers/infiniband/core/cma.c
+++ b/drivers/infiniband/core/cma.c
@@ -42,6 +42,7 @@
42#include <linux/inetdevice.h> 42#include <linux/inetdevice.h>
43 43
44#include <net/tcp.h> 44#include <net/tcp.h>
45#include <net/ipv6.h>
45 46
46#include <rdma/rdma_cm.h> 47#include <rdma/rdma_cm.h>
47#include <rdma/rdma_cm_ib.h> 48#include <rdma/rdma_cm_ib.h>
@@ -636,7 +637,12 @@ static inline int cma_zero_addr(struct sockaddr *addr)
636 637
637static inline int cma_loopback_addr(struct sockaddr *addr) 638static inline int cma_loopback_addr(struct sockaddr *addr)
638{ 639{
639 return ipv4_is_loopback(((struct sockaddr_in *) addr)->sin_addr.s_addr); 640 if (addr->sa_family == AF_INET)
641 return ipv4_is_loopback(
642 ((struct sockaddr_in *) addr)->sin_addr.s_addr);
643 else
644 return ipv6_addr_loopback(
645 &((struct sockaddr_in6 *) addr)->sin6_addr);
640} 646}
641 647
642static inline int cma_any_addr(struct sockaddr *addr) 648static inline int cma_any_addr(struct sockaddr *addr)
@@ -1467,10 +1473,10 @@ static void cma_listen_on_all(struct rdma_id_private *id_priv)
1467 1473
1468static int cma_bind_any(struct rdma_cm_id *id, sa_family_t af) 1474static int cma_bind_any(struct rdma_cm_id *id, sa_family_t af)
1469{ 1475{
1470 struct sockaddr_in addr_in; 1476 struct sockaddr_storage addr_in;
1471 1477
1472 memset(&addr_in, 0, sizeof addr_in); 1478 memset(&addr_in, 0, sizeof addr_in);
1473 addr_in.sin_family = af; 1479 addr_in.ss_family = af;
1474 return rdma_bind_addr(id, (struct sockaddr *) &addr_in); 1480 return rdma_bind_addr(id, (struct sockaddr *) &addr_in);
1475} 1481}
1476 1482
@@ -2073,7 +2079,7 @@ int rdma_bind_addr(struct rdma_cm_id *id, struct sockaddr *addr)
2073 struct rdma_id_private *id_priv; 2079 struct rdma_id_private *id_priv;
2074 int ret; 2080 int ret;
2075 2081
2076 if (addr->sa_family != AF_INET) 2082 if (addr->sa_family != AF_INET && addr->sa_family != AF_INET6)
2077 return -EAFNOSUPPORT; 2083 return -EAFNOSUPPORT;
2078 2084
2079 id_priv = container_of(id, struct rdma_id_private, id); 2085 id_priv = container_of(id, struct rdma_id_private, id);
@@ -2113,31 +2119,59 @@ EXPORT_SYMBOL(rdma_bind_addr);
2113static int cma_format_hdr(void *hdr, enum rdma_port_space ps, 2119static int cma_format_hdr(void *hdr, enum rdma_port_space ps,
2114 struct rdma_route *route) 2120 struct rdma_route *route)
2115{ 2121{
2116 struct sockaddr_in *src4, *dst4;
2117 struct cma_hdr *cma_hdr; 2122 struct cma_hdr *cma_hdr;
2118 struct sdp_hh *sdp_hdr; 2123 struct sdp_hh *sdp_hdr;
2119 2124
2120 src4 = (struct sockaddr_in *) &route->addr.src_addr; 2125 if (route->addr.src_addr.ss_family == AF_INET) {
2121 dst4 = (struct sockaddr_in *) &route->addr.dst_addr; 2126 struct sockaddr_in *src4, *dst4;
2122 2127
2123 switch (ps) { 2128 src4 = (struct sockaddr_in *) &route->addr.src_addr;
2124 case RDMA_PS_SDP: 2129 dst4 = (struct sockaddr_in *) &route->addr.dst_addr;
2125 sdp_hdr = hdr; 2130
2126 if (sdp_get_majv(sdp_hdr->sdp_version) != SDP_MAJ_VERSION) 2131 switch (ps) {
2127 return -EINVAL; 2132 case RDMA_PS_SDP:
2128 sdp_set_ip_ver(sdp_hdr, 4); 2133 sdp_hdr = hdr;
2129 sdp_hdr->src_addr.ip4.addr = src4->sin_addr.s_addr; 2134 if (sdp_get_majv(sdp_hdr->sdp_version) != SDP_MAJ_VERSION)
2130 sdp_hdr->dst_addr.ip4.addr = dst4->sin_addr.s_addr; 2135 return -EINVAL;
2131 sdp_hdr->port = src4->sin_port; 2136 sdp_set_ip_ver(sdp_hdr, 4);
2132 break; 2137 sdp_hdr->src_addr.ip4.addr = src4->sin_addr.s_addr;
2133 default: 2138 sdp_hdr->dst_addr.ip4.addr = dst4->sin_addr.s_addr;
2134 cma_hdr = hdr; 2139 sdp_hdr->port = src4->sin_port;
2135 cma_hdr->cma_version = CMA_VERSION; 2140 break;
2136 cma_set_ip_ver(cma_hdr, 4); 2141 default:
2137 cma_hdr->src_addr.ip4.addr = src4->sin_addr.s_addr; 2142 cma_hdr = hdr;
2138 cma_hdr->dst_addr.ip4.addr = dst4->sin_addr.s_addr; 2143 cma_hdr->cma_version = CMA_VERSION;
2139 cma_hdr->port = src4->sin_port; 2144 cma_set_ip_ver(cma_hdr, 4);
2140 break; 2145 cma_hdr->src_addr.ip4.addr = src4->sin_addr.s_addr;
2146 cma_hdr->dst_addr.ip4.addr = dst4->sin_addr.s_addr;
2147 cma_hdr->port = src4->sin_port;
2148 break;
2149 }
2150 } else {
2151 struct sockaddr_in6 *src6, *dst6;
2152
2153 src6 = (struct sockaddr_in6 *) &route->addr.src_addr;
2154 dst6 = (struct sockaddr_in6 *) &route->addr.dst_addr;
2155
2156 switch (ps) {
2157 case RDMA_PS_SDP:
2158 sdp_hdr = hdr;
2159 if (sdp_get_majv(sdp_hdr->sdp_version) != SDP_MAJ_VERSION)
2160 return -EINVAL;
2161 sdp_set_ip_ver(sdp_hdr, 6);
2162 sdp_hdr->src_addr.ip6 = src6->sin6_addr;
2163 sdp_hdr->dst_addr.ip6 = dst6->sin6_addr;
2164 sdp_hdr->port = src6->sin6_port;
2165 break;
2166 default:
2167 cma_hdr = hdr;
2168 cma_hdr->cma_version = CMA_VERSION;
2169 cma_set_ip_ver(cma_hdr, 6);
2170 cma_hdr->src_addr.ip6 = src6->sin6_addr;
2171 cma_hdr->dst_addr.ip6 = dst6->sin6_addr;
2172 cma_hdr->port = src6->sin6_port;
2173 break;
2174 }
2141 } 2175 }
2142 return 0; 2176 return 0;
2143} 2177}