diff options
-rw-r--r-- | drivers/infiniband/core/sa_query.c | 6 | ||||
-rw-r--r-- | drivers/infiniband/core/ucma.c | 49 | ||||
-rw-r--r-- | include/rdma/ib_sa.h | 6 | ||||
-rw-r--r-- | include/rdma/ib_user_sa.h | 16 | ||||
-rw-r--r-- | include/rdma/rdma_user_cm.h | 6 |
5 files changed, 81 insertions, 2 deletions
diff --git a/drivers/infiniband/core/sa_query.c b/drivers/infiniband/core/sa_query.c index 82543716d59e..7e1ffd8ccd5c 100644 --- a/drivers/infiniband/core/sa_query.c +++ b/drivers/infiniband/core/sa_query.c | |||
@@ -604,6 +604,12 @@ retry: | |||
604 | return ret ? ret : id; | 604 | return ret ? ret : id; |
605 | } | 605 | } |
606 | 606 | ||
607 | void ib_sa_unpack_path(void *attribute, struct ib_sa_path_rec *rec) | ||
608 | { | ||
609 | ib_unpack(path_rec_table, ARRAY_SIZE(path_rec_table), attribute, rec); | ||
610 | } | ||
611 | EXPORT_SYMBOL(ib_sa_unpack_path); | ||
612 | |||
607 | static void ib_sa_path_rec_callback(struct ib_sa_query *sa_query, | 613 | static void ib_sa_path_rec_callback(struct ib_sa_query *sa_query, |
608 | int status, | 614 | int status, |
609 | struct ib_sa_mad *mad) | 615 | struct ib_sa_mad *mad) |
diff --git a/drivers/infiniband/core/ucma.c b/drivers/infiniband/core/ucma.c index bb96d3c4b0f4..f1cbd26a9de0 100644 --- a/drivers/infiniband/core/ucma.c +++ b/drivers/infiniband/core/ucma.c | |||
@@ -43,6 +43,7 @@ | |||
43 | #include <rdma/rdma_user_cm.h> | 43 | #include <rdma/rdma_user_cm.h> |
44 | #include <rdma/ib_marshall.h> | 44 | #include <rdma/ib_marshall.h> |
45 | #include <rdma/rdma_cm.h> | 45 | #include <rdma/rdma_cm.h> |
46 | #include <rdma/rdma_cm_ib.h> | ||
46 | 47 | ||
47 | MODULE_AUTHOR("Sean Hefty"); | 48 | MODULE_AUTHOR("Sean Hefty"); |
48 | MODULE_DESCRIPTION("RDMA Userspace Connection Manager Access"); | 49 | MODULE_DESCRIPTION("RDMA Userspace Connection Manager Access"); |
@@ -812,6 +813,51 @@ static int ucma_set_option_id(struct ucma_context *ctx, int optname, | |||
812 | return ret; | 813 | return ret; |
813 | } | 814 | } |
814 | 815 | ||
816 | static int ucma_set_ib_path(struct ucma_context *ctx, | ||
817 | struct ib_path_rec_data *path_data, size_t optlen) | ||
818 | { | ||
819 | struct ib_sa_path_rec sa_path; | ||
820 | struct rdma_cm_event event; | ||
821 | int ret; | ||
822 | |||
823 | if (optlen % sizeof(*path_data)) | ||
824 | return -EINVAL; | ||
825 | |||
826 | for (; optlen; optlen -= sizeof(*path_data), path_data++) { | ||
827 | if (path_data->flags == (IB_PATH_GMP | IB_PATH_PRIMARY | | ||
828 | IB_PATH_BIDIRECTIONAL)) | ||
829 | break; | ||
830 | } | ||
831 | |||
832 | if (!optlen) | ||
833 | return -EINVAL; | ||
834 | |||
835 | ib_sa_unpack_path(path_data->path_rec, &sa_path); | ||
836 | ret = rdma_set_ib_paths(ctx->cm_id, &sa_path, 1); | ||
837 | if (ret) | ||
838 | return ret; | ||
839 | |||
840 | memset(&event, 0, sizeof event); | ||
841 | event.event = RDMA_CM_EVENT_ROUTE_RESOLVED; | ||
842 | return ucma_event_handler(ctx->cm_id, &event); | ||
843 | } | ||
844 | |||
845 | static int ucma_set_option_ib(struct ucma_context *ctx, int optname, | ||
846 | void *optval, size_t optlen) | ||
847 | { | ||
848 | int ret; | ||
849 | |||
850 | switch (optname) { | ||
851 | case RDMA_OPTION_IB_PATH: | ||
852 | ret = ucma_set_ib_path(ctx, optval, optlen); | ||
853 | break; | ||
854 | default: | ||
855 | ret = -ENOSYS; | ||
856 | } | ||
857 | |||
858 | return ret; | ||
859 | } | ||
860 | |||
815 | static int ucma_set_option_level(struct ucma_context *ctx, int level, | 861 | static int ucma_set_option_level(struct ucma_context *ctx, int level, |
816 | int optname, void *optval, size_t optlen) | 862 | int optname, void *optval, size_t optlen) |
817 | { | 863 | { |
@@ -821,6 +867,9 @@ static int ucma_set_option_level(struct ucma_context *ctx, int level, | |||
821 | case RDMA_OPTION_ID: | 867 | case RDMA_OPTION_ID: |
822 | ret = ucma_set_option_id(ctx, optname, optval, optlen); | 868 | ret = ucma_set_option_id(ctx, optname, optval, optlen); |
823 | break; | 869 | break; |
870 | case RDMA_OPTION_IB: | ||
871 | ret = ucma_set_option_ib(ctx, optname, optval, optlen); | ||
872 | break; | ||
824 | default: | 873 | default: |
825 | ret = -ENOSYS; | 874 | ret = -ENOSYS; |
826 | } | 875 | } |
diff --git a/include/rdma/ib_sa.h b/include/rdma/ib_sa.h index 3841c1aff692..1082afaed158 100644 --- a/include/rdma/ib_sa.h +++ b/include/rdma/ib_sa.h | |||
@@ -379,4 +379,10 @@ int ib_init_ah_from_path(struct ib_device *device, u8 port_num, | |||
379 | struct ib_sa_path_rec *rec, | 379 | struct ib_sa_path_rec *rec, |
380 | struct ib_ah_attr *ah_attr); | 380 | struct ib_ah_attr *ah_attr); |
381 | 381 | ||
382 | /** | ||
383 | * ib_sa_unpack_path - Convert a path record from MAD format to struct | ||
384 | * ib_sa_path_rec. | ||
385 | */ | ||
386 | void ib_sa_unpack_path(void *attribute, struct ib_sa_path_rec *rec); | ||
387 | |||
382 | #endif /* IB_SA_H */ | 388 | #endif /* IB_SA_H */ |
diff --git a/include/rdma/ib_user_sa.h b/include/rdma/ib_user_sa.h index 659120157e14..cfc7c9ba781e 100644 --- a/include/rdma/ib_user_sa.h +++ b/include/rdma/ib_user_sa.h | |||
@@ -35,6 +35,22 @@ | |||
35 | 35 | ||
36 | #include <linux/types.h> | 36 | #include <linux/types.h> |
37 | 37 | ||
38 | enum { | ||
39 | IB_PATH_GMP = 1, | ||
40 | IB_PATH_PRIMARY = (1<<1), | ||
41 | IB_PATH_ALTERNATE = (1<<2), | ||
42 | IB_PATH_OUTBOUND = (1<<3), | ||
43 | IB_PATH_INBOUND = (1<<4), | ||
44 | IB_PATH_INBOUND_REVERSE = (1<<5), | ||
45 | IB_PATH_BIDIRECTIONAL = IB_PATH_OUTBOUND | IB_PATH_INBOUND_REVERSE | ||
46 | }; | ||
47 | |||
48 | struct ib_path_rec_data { | ||
49 | __u32 flags; | ||
50 | __u32 reserved; | ||
51 | __u32 path_rec[16]; | ||
52 | }; | ||
53 | |||
38 | struct ib_user_path_rec { | 54 | struct ib_user_path_rec { |
39 | __u8 dgid[16]; | 55 | __u8 dgid[16]; |
40 | __u8 sgid[16]; | 56 | __u8 sgid[16]; |
diff --git a/include/rdma/rdma_user_cm.h b/include/rdma/rdma_user_cm.h index c55705460b87..1d165022c02d 100644 --- a/include/rdma/rdma_user_cm.h +++ b/include/rdma/rdma_user_cm.h | |||
@@ -215,12 +215,14 @@ struct rdma_ucm_event_resp { | |||
215 | 215 | ||
216 | /* Option levels */ | 216 | /* Option levels */ |
217 | enum { | 217 | enum { |
218 | RDMA_OPTION_ID = 0 | 218 | RDMA_OPTION_ID = 0, |
219 | RDMA_OPTION_IB = 1 | ||
219 | }; | 220 | }; |
220 | 221 | ||
221 | /* Option details */ | 222 | /* Option details */ |
222 | enum { | 223 | enum { |
223 | RDMA_OPTION_ID_TOS = 0 | 224 | RDMA_OPTION_ID_TOS = 0, |
225 | RDMA_OPTION_IB_PATH = 1 | ||
224 | }; | 226 | }; |
225 | 227 | ||
226 | struct rdma_ucm_set_option { | 228 | struct rdma_ucm_set_option { |