Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

IB/core: Add ability for drivers to report an alternate MAD size.

Add max MAD size to the device immutable data set and have all drivers that
support MADs report the current IB MAD size (IB_MGMT_MAD_SIZE) to the core.

Verify MAD size data in both the MAD core and when reading the immutable data.

OPA drivers will report alternate MAD sizes in subsequent patches.

Signed-off-by: Ira Weiny <ira.weiny@intel.com>
Signed-off-by: Doug Ledford <dledford@redhat.com>

authored by

Ira Weiny and committed by
Doug Ledford
337877a4 da2dfaa3

+43
+11
drivers/infiniband/core/device.c
··· 211 211 return 0; 212 212 } 213 213 214 + static int verify_immutable(const struct ib_device *dev, u8 port) 215 + { 216 + return WARN_ON(!rdma_cap_ib_mad(dev, port) && 217 + rdma_max_mad_size(dev, port) != 0); 218 + } 219 + 214 220 static int read_port_immutable(struct ib_device *device) 215 221 { 216 222 int ret = -ENOMEM; ··· 242 236 &device->port_immutable[port]); 243 237 if (ret) 244 238 goto err; 239 + 240 + if (verify_immutable(device, port)) { 241 + ret = -EINVAL; 242 + goto err; 243 + } 245 244 } 246 245 247 246 ret = 0;
+3
drivers/infiniband/core/mad.c
··· 2939 2939 int has_smi; 2940 2940 struct ib_cq_init_attr cq_attr = {}; 2941 2941 2942 + if (WARN_ON(rdma_max_mad_size(device, port_num) < IB_MGMT_MAD_SIZE)) 2943 + return -EFAULT; 2944 + 2942 2945 /* Create new device info */ 2943 2946 port_priv = kzalloc(sizeof *port_priv, GFP_KERNEL); 2944 2947 if (!port_priv) {
+2
drivers/infiniband/hw/ehca/ehca_main.c
··· 46 46 47 47 #include <linux/notifier.h> 48 48 #include <linux/memory.h> 49 + #include <rdma/ib_mad.h> 49 50 #include "ehca_classes.h" 50 51 #include "ehca_iverbs.h" 51 52 #include "ehca_mrmw.h" ··· 445 444 immutable->pkey_tbl_len = attr.pkey_tbl_len; 446 445 immutable->gid_tbl_len = attr.gid_tbl_len; 447 446 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_IB; 447 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 448 448 449 449 return 0; 450 450 }
+1
drivers/infiniband/hw/ipath/ipath_verbs.c
··· 1996 1996 immutable->pkey_tbl_len = attr.pkey_tbl_len; 1997 1997 immutable->gid_tbl_len = attr.gid_tbl_len; 1998 1998 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_IB; 1999 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 1999 2000 2000 2001 return 0; 2001 2002 }
+2
drivers/infiniband/hw/mlx4/main.c
··· 2189 2189 else 2190 2190 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_ROCE; 2191 2191 2192 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 2193 + 2192 2194 return 0; 2193 2195 } 2194 2196
+1
drivers/infiniband/hw/mlx5/main.c
··· 1203 1203 immutable->pkey_tbl_len = attr.pkey_tbl_len; 1204 1204 immutable->gid_tbl_len = attr.gid_tbl_len; 1205 1205 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_IB; 1206 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 1206 1207 1207 1208 return 0; 1208 1209 }
+1
drivers/infiniband/hw/mthca/mthca_provider.c
··· 1264 1264 immutable->pkey_tbl_len = attr.pkey_tbl_len; 1265 1265 immutable->gid_tbl_len = attr.gid_tbl_len; 1266 1266 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_IB; 1267 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 1267 1268 1268 1269 return 0; 1269 1270 }
+2
drivers/infiniband/hw/ocrdma/ocrdma_main.c
··· 30 30 #include <rdma/ib_verbs.h> 31 31 #include <rdma/ib_user_verbs.h> 32 32 #include <rdma/ib_addr.h> 33 + #include <rdma/ib_mad.h> 33 34 34 35 #include <linux/netdevice.h> 35 36 #include <net/addrconf.h> ··· 216 215 immutable->pkey_tbl_len = attr.pkey_tbl_len; 217 216 immutable->gid_tbl_len = attr.gid_tbl_len; 218 217 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_ROCE; 218 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 219 219 220 220 return 0; 221 221 }
+1
drivers/infiniband/hw/qib/qib_verbs.c
··· 2055 2055 immutable->pkey_tbl_len = attr.pkey_tbl_len; 2056 2056 immutable->gid_tbl_len = attr.gid_tbl_len; 2057 2057 immutable->core_cap_flags = RDMA_CORE_PORT_IBA_IB; 2058 + immutable->max_mad_size = IB_MGMT_MAD_SIZE; 2058 2059 2059 2060 return 0; 2060 2061 }
+1
include/rdma/ib_mad.h
··· 135 135 IB_MGMT_SA_DATA = 200, 136 136 IB_MGMT_DEVICE_HDR = 64, 137 137 IB_MGMT_DEVICE_DATA = 192, 138 + IB_MGMT_MAD_SIZE = IB_MGMT_MAD_HDR + IB_MGMT_MAD_DATA, 138 139 }; 139 140 140 141 struct ib_mad_hdr {
+18
include/rdma/ib_verbs.h
··· 1534 1534 int pkey_tbl_len; 1535 1535 int gid_tbl_len; 1536 1536 u32 core_cap_flags; 1537 + u32 max_mad_size; 1537 1538 }; 1538 1539 1539 1540 struct ib_device { ··· 2051 2050 u8 port_num) 2052 2051 { 2053 2052 return !(device->port_immutable[port_num].core_cap_flags & RDMA_CORE_CAP_PROT_IWARP); 2053 + } 2054 + 2055 + /** 2056 + * rdma_max_mad_size - Return the max MAD size required by this RDMA Port. 2057 + * 2058 + * @device: Device 2059 + * @port_num: Port number 2060 + * 2061 + * This MAD size includes the MAD headers and MAD payload. No other headers 2062 + * are included. 2063 + * 2064 + * Return the max MAD size required by the Port. Will return 0 if the port 2065 + * does not support MADs 2066 + */ 2067 + static inline size_t rdma_max_mad_size(const struct ib_device *device, u8 port_num) 2068 + { 2069 + return device->port_immutable[port_num].max_mad_size; 2054 2070 } 2055 2071 2056 2072 int ib_query_gid(struct ib_device *device,