Merge to Fedora kernel-2.6.18-1.2224_FC5 patched with stable patch-2.6.18.1-vs2.0...
[linux-2.6.git] / drivers / infiniband / hw / ipath / ipath_cq.c
index 7ece113..3efee34 100644 (file)
@@ -1,4 +1,5 @@
 /*
+ * Copyright (c) 2006 QLogic, Inc. All rights reserved.
  * Copyright (c) 2005, 2006 PathScale, Inc. All rights reserved.
  *
  * This software is available to you under a choice of one of two
@@ -157,10 +158,21 @@ struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries,
                              struct ib_ucontext *context,
                              struct ib_udata *udata)
 {
+       struct ipath_ibdev *dev = to_idev(ibdev);
        struct ipath_cq *cq;
        struct ib_wc *wc;
        struct ib_cq *ret;
 
+       if (entries > ib_ipath_max_cqes) {
+               ret = ERR_PTR(-EINVAL);
+               goto bail;
+       }
+
+       if (dev->n_cqs_allocated == ib_ipath_max_cqs) {
+               ret = ERR_PTR(-ENOMEM);
+               goto bail;
+       }
+
        /*
         * Need to use vmalloc() if we want to support large #s of
         * entries.
@@ -196,6 +208,8 @@ struct ib_cq *ipath_create_cq(struct ib_device *ibdev, int entries,
 
        ret = &cq->ibcq;
 
+       dev->n_cqs_allocated++;
+
 bail:
        return ret;
 }
@@ -210,9 +224,11 @@ bail:
  */
 int ipath_destroy_cq(struct ib_cq *ibcq)
 {
+       struct ipath_ibdev *dev = to_idev(ibcq->device);
        struct ipath_cq *cq = to_icq(ibcq);
 
        tasklet_kill(&cq->comptask);
+       dev->n_cqs_allocated--;
        vfree(cq->queue);
        kfree(cq);