long fd_flags;
uint64_t so_opts;
uint64_t ipv6_opts;
+ void *optval;
+ size_t optlen;
int state;
int cq_armed;
int retries;
rs->retries = 0;
resolve_route:
to = 1000 << rs->retries++;
- ret = rdma_resolve_route(rs->cm_id, to);
- if (!ret)
- goto do_connect;
+ if (rs->optval) {
+ ret = rdma_set_option(rs->cm_id, RDMA_OPTION_IB,
+ RDMA_OPTION_IB_PATH, rs->optval,
+ rs->optlen);
+ free(rs->optval);
+ rs->optval = NULL;
+ if (!ret) {
+ rs->state = rs_resolving_route;
+ goto resolving_route;
+ }
+ } else {
+ ret = rdma_resolve_route(rs->cm_id, to);
+ if (!ret)
+ goto do_connect;
+ }
if (errno == EAGAIN || errno == EWOULDBLOCK)
rs->state = rs_resolving_route;
break;
case rs_resolving_route:
+resolving_route:
ret = ucma_complete(rs->cm_id);
if (ret) {
if (errno == ETIMEDOUT && rs->retries <= RS_CONN_RETRIES)
rs->target_iomap_size = (uint16_t) rs_scale_to_value(
(uint8_t) rs_value_to_scale(*(int *) optval, 8), 8);
break;
+ case RDMA_ROUTE:
+ if ((rs->optval = calloc(optlen, 1))) {
+ memcpy(rs->optval, optval, optlen);
+ rs->optlen = optlen;
+ ret = 0;
+ } else {
+ ret = ERR(ENOMEM);
+ }
+ break;
default:
break;
}