[ofa-general] [PATCH 1 of 3] IB/verbs: add cq comp_vector support in core

Michael S. Tsirkin mst at dev.mellanox.co.il
Thu May 3 03:48:47 PDT 2007


Extend ib_create_cq to pass in comp_vector parameter -
this parallels our userspace API.
Update all ULPs and providers.
Make uverbs use multiple vectors if available.

Signed-off-by: Michael S. Tsirkin <mst at dev.mellanox.co.il>

---

Note: since num_comp_vectors = 0 is not legal, and to mimizime provider churn,
I set num_comp_vectors to a sane value in core. Providers can increase that.

Index: linux-2.6/drivers/infiniband/core/device.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/core/device.c
+++ linux-2.6/drivers/infiniband/core/device.c
@@ -161,9 +161,14 @@ static int alloc_name(char *name)
  */
 struct ib_device *ib_alloc_device(size_t size)
 {
+	struct ib_device *dev;
 	BUG_ON(size < sizeof (struct ib_device));
 
-	return kzalloc(size, GFP_KERNEL);
+	dev = kzalloc(size, GFP_KERNEL);
+	if (dev)
+		dev->num_comp_vectors = 1;
+
+	return dev;
 }
 EXPORT_SYMBOL(ib_alloc_device);
 
Index: linux-2.6/drivers/infiniband/core/mad.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/core/mad.c
+++ linux-2.6/drivers/infiniband/core/mad.c
@@ -2767,7 +2767,7 @@ static int ib_mad_port_open(struct ib_de
 	cq_size = (IB_MAD_QP_SEND_SIZE + IB_MAD_QP_RECV_SIZE) * 2;
 	port_priv->cq = ib_create_cq(port_priv->device,
 				     ib_mad_thread_completion_handler,
-				     NULL, port_priv, cq_size);
+				     NULL, port_priv, cq_size, 0);
 	if (IS_ERR(port_priv->cq)) {
 		printk(KERN_ERR PFX "Couldn't create ib_mad CQ\n");
 		ret = PTR_ERR(port_priv->cq);
Index: linux-2.6/drivers/infiniband/core/uverbs_cmd.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/core/uverbs_cmd.c
+++ linux-2.6/drivers/infiniband/core/uverbs_cmd.c
@@ -802,6 +802,7 @@ ssize_t ib_uverbs_create_cq(struct ib_uv
 	INIT_LIST_HEAD(&obj->async_list);
 
 	cq = file->device->ib_dev->create_cq(file->device->ib_dev, cmd.cqe,
+					     cmd.comp_vector,
 					     file->ucontext, &udata);
 	if (IS_ERR(cq)) {
 		ret = PTR_ERR(cq);
Index: linux-2.6/drivers/infiniband/core/uverbs_main.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/core/uverbs_main.c
+++ linux-2.6/drivers/infiniband/core/uverbs_main.c
@@ -752,7 +752,7 @@ static void ib_uverbs_add_one(struct ib_
 	spin_unlock(&map_lock);
 
 	uverbs_dev->ib_dev           = device;
-	uverbs_dev->num_comp_vectors = 1;
+	uverbs_dev->num_comp_vectors = device->num_comp_vectors;
 
 	uverbs_dev->dev = cdev_alloc();
 	if (!uverbs_dev->dev)
Index: linux-2.6/drivers/infiniband/core/verbs.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/core/verbs.c
+++ linux-2.6/drivers/infiniband/core/verbs.c
@@ -609,11 +609,11 @@ EXPORT_SYMBOL(ib_destroy_qp);
 struct ib_cq *ib_create_cq(struct ib_device *device,
 			   ib_comp_handler comp_handler,
 			   void (*event_handler)(struct ib_event *, void *),
-			   void *cq_context, int cqe)
+			   void *cq_context, int cqe, int comp_vector)
 {
 	struct ib_cq *cq;
 
-	cq = device->create_cq(device, cqe, NULL, NULL);
+	cq = device->create_cq(device, cqe, comp_vector, NULL, NULL);
 
 	if (!IS_ERR(cq)) {
 		cq->device        = device;
Index: linux-2.6/drivers/infiniband/hw/amso1100/c2_provider.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/amso1100/c2_provider.c
+++ linux-2.6/drivers/infiniband/hw/amso1100/c2_provider.c
@@ -290,7 +290,7 @@ static int c2_destroy_qp(struct ib_qp *i
 	return 0;
 }
 
-static struct ib_cq *c2_create_cq(struct ib_device *ibdev, int entries,
+static struct ib_cq *c2_create_cq(struct ib_device *ibdev, int entries, int vector,
 				  struct ib_ucontext *context,
 				  struct ib_udata *udata)
 {
Index: linux-2.6/drivers/infiniband/hw/cxgb3/iwch_provider.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/cxgb3/iwch_provider.c
+++ linux-2.6/drivers/infiniband/hw/cxgb3/iwch_provider.c
@@ -139,7 +139,7 @@ static int iwch_destroy_cq(struct ib_cq 
 	return 0;
 }
 
-static struct ib_cq *iwch_create_cq(struct ib_device *ibdev, int entries,
+static struct ib_cq *iwch_create_cq(struct ib_device *ibdev, int entries, int vector,
 			     struct ib_ucontext *ib_context,
 			     struct ib_udata *udata)
 {
Index: linux-2.6/drivers/infiniband/hw/ehca/ehca_cq.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/ehca/ehca_cq.c
+++ linux-2.6/drivers/infiniband/hw/ehca/ehca_cq.c
@@ -113,7 +113,7 @@ struct ehca_qp* ehca_cq_get_qp(struct eh
 	return ret;
 }
 
-struct ib_cq *ehca_create_cq(struct ib_device *device, int cqe,
+struct ib_cq *ehca_create_cq(struct ib_device *device, int cqe, int comp_vector,
 			     struct ib_ucontext *context,
 			     struct ib_udata *udata)
 {
Index: linux-2.6/drivers/infiniband/hw/ehca/ehca_iverbs.h
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/ehca/ehca_iverbs.h
+++ linux-2.6/drivers/infiniband/hw/ehca/ehca_iverbs.h
@@ -123,7 +123,7 @@ int ehca_destroy_eq(struct ehca_shca *sh
 void *ehca_poll_eq(struct ehca_shca *shca, struct ehca_eq *eq);
 
 
-struct ib_cq *ehca_create_cq(struct ib_device *device, int cqe,
+struct ib_cq *ehca_create_cq(struct ib_device *device, int cqe, int comp_vector,
 			     struct ib_ucontext *context,
 			     struct ib_udata *udata);
 
Index: linux-2.6/drivers/infiniband/hw/ehca/ehca_main.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/ehca/ehca_main.c
+++ linux-2.6/drivers/infiniband/hw/ehca/ehca_main.c
@@ -375,7 +375,7 @@ static int ehca_create_aqp1(struct ehca_
 		return -EPERM;
 	}
 
-	ibcq = ib_create_cq(&shca->ib_device, NULL, NULL, (void*)(-1), 10);
+	ibcq = ib_create_cq(&shca->ib_device, NULL, NULL, (void*)(-1), 10, 0);
 	if (IS_ERR(ibcq)) {
 		ehca_err(&shca->ib_device, "Cannot create AQP1 CQ.");
 		return PTR_ERR(ibcq);
Index: linux-2.6/drivers/infiniband/hw/ipath/ipath_cq.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/ipath/ipath_cq.c
+++ linux-2.6/drivers/infiniband/hw/ipath/ipath_cq.c
@@ -170,7 +170,7 @@ static void send_complete(unsigned long 
  *
  * Called by ib_create_cq() in the generic verbs code.
  */
-struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries,
+struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries, int comp_vector,
 			      struct ib_ucontext *context,
 			      struct ib_udata *udata)
 {
Index: linux-2.6/drivers/infiniband/hw/ipath/ipath_verbs.h
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/ipath/ipath_verbs.h
+++ linux-2.6/drivers/infiniband/hw/ipath/ipath_verbs.h
@@ -710,7 +710,7 @@ void ipath_cq_enter(struct ipath_cq *cq,
 
 int ipath_poll_cq(struct ib_cq *ibcq, int num_entries, struct ib_wc *entry);
 
-struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries,
+struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries, int comp_vector,
 			      struct ib_ucontext *context,
 			      struct ib_udata *udata);
 
Index: linux-2.6/drivers/infiniband/hw/mthca/mthca_provider.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/hw/mthca/mthca_provider.c
+++ linux-2.6/drivers/infiniband/hw/mthca/mthca_provider.c
@@ -663,6 +663,7 @@ static int mthca_destroy_qp(struct ib_qp
 }
 
 static struct ib_cq *mthca_create_cq(struct ib_device *ibdev, int entries,
+				     int comp_vector,
 				     struct ib_ucontext *context,
 				     struct ib_udata *udata)
 {
Index: linux-2.6/drivers/infiniband/ulp/ipoib/ipoib_cm.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/ulp/ipoib/ipoib_cm.c
+++ linux-2.6/drivers/infiniband/ulp/ipoib/ipoib_cm.c
@@ -793,7 +793,7 @@ static int ipoib_cm_tx_init(struct ipoib
 	}
 
 	p->cq = ib_create_cq(priv->ca, ipoib_cm_tx_completion, NULL, p,
-			     ipoib_sendq_size + 1);
+			     ipoib_sendq_size + 1, 0);
 	if (IS_ERR(p->cq)) {
 		ret = PTR_ERR(p->cq);
 		ipoib_warn(priv, "failed to allocate tx cq: %d\n", ret);
Index: linux-2.6/drivers/infiniband/ulp/ipoib/ipoib_verbs.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/ulp/ipoib/ipoib_verbs.c
+++ linux-2.6/drivers/infiniband/ulp/ipoib/ipoib_verbs.c
@@ -187,7 +187,7 @@ int ipoib_transport_dev_init(struct net_
 	if (!ret)
 		size += ipoib_recvq_size;
 
-	priv->cq = ib_create_cq(priv->ca, ipoib_ib_completion, NULL, dev, size);
+	priv->cq = ib_create_cq(priv->ca, ipoib_ib_completion, NULL, dev, size, 0);
 	if (IS_ERR(priv->cq)) {
 		printk(KERN_WARNING "%s: failed to create CQ\n", ca->name);
 		goto out_free_mr;
Index: linux-2.6/drivers/infiniband/ulp/iser/iser_verbs.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/ulp/iser/iser_verbs.c
+++ linux-2.6/drivers/infiniband/ulp/iser/iser_verbs.c
@@ -76,7 +76,7 @@ static int iser_create_device_ib_res(str
 				  iser_cq_callback,
 				  iser_cq_event_callback,
 				  (void *)device,
-				  ISER_MAX_CQ_LEN);
+				  ISER_MAX_CQ_LEN, 0);
 	if (IS_ERR(device->cq))
 		goto cq_err;
 
Index: linux-2.6/drivers/infiniband/ulp/srp/ib_srp.c
===================================================================
--- linux-2.6.orig/drivers/infiniband/ulp/srp/ib_srp.c
+++ linux-2.6/drivers/infiniband/ulp/srp/ib_srp.c
@@ -197,7 +197,7 @@ static int srp_create_target_ib(struct s
 		return -ENOMEM;
 
 	target->cq = ib_create_cq(target->srp_host->dev->dev, srp_completion,
-				  NULL, target, SRP_CQ_SIZE);
+				  NULL, target, SRP_CQ_SIZE, 0);
 	if (IS_ERR(target->cq)) {
 		ret = PTR_ERR(target->cq);
 		goto out;
Index: linux-2.6/include/rdma/ib_verbs.h
===================================================================
--- linux-2.6.orig/include/rdma/ib_verbs.h
+++ linux-2.6/include/rdma/ib_verbs.h
@@ -912,6 +912,8 @@ struct ib_device {
 
 	u32                           flags;
 
+	int                           num_comp_vectors;
+
 	struct iw_cm_verbs	     *iwcm;
 
 	int		           (*query_device)(struct ib_device *device,
@@ -978,6 +980,7 @@ struct ib_device {
 						struct ib_recv_wr *recv_wr,
 						struct ib_recv_wr **bad_recv_wr);
 	struct ib_cq *             (*create_cq)(struct ib_device *device, int cqe,
+						int comp_vector,
 						struct ib_ucontext *context,
 						struct ib_udata *udata);
 	int                        (*destroy_cq)(struct ib_cq *cq);
@@ -1358,13 +1361,15 @@ static inline int ib_post_recv(struct ib
  * @cq_context: Context associated with the CQ returned to the user via
  *   the associated completion and event handlers.
  * @cqe: The minimum size of the CQ.
+ * @comp_vector - Completion vector used to signal completion events.
+ *     Must be >= 0 and < context->num_comp_vectors.
  *
  * Users can examine the cq structure to determine the actual CQ size.
  */
 struct ib_cq *ib_create_cq(struct ib_device *device,
 			   ib_comp_handler comp_handler,
 			   void (*event_handler)(struct ib_event *, void *),
-			   void *cq_context, int cqe);
+			   void *cq_context, int cqe, int comp_vector);
 
 /**
  * ib_resize_cq - Modifies the capacity of the CQ.

-- 
MST



More information about the general mailing list