RDMA/hns: Fix cqn type and init resp
authorYixian Liu <liuyixian@huawei.com>
Thu, 15 Mar 2018 07:23:14 +0000 (15:23 +0800)
committerJason Gunthorpe <jgg@mellanox.com>
Thu, 15 Mar 2018 21:34:26 +0000 (15:34 -0600)
This patch changes the type of cqn from u32 to u64 to keep
userspace and kernel consistent, initializes resp both for
cq and qp to zeros, and also changes the condition judgment
of outlen considering future caps extension.

Suggested-by: Jason Gunthorpe <jgg@mellanox.com>
Fixes: e088a685eae9 (hns: Support rq record doorbell for the user space)
Fixes: 9b44703d0a21 (hns: Support cq record doorbell for the user space)
Signed-off-by: Yixian Liu <liuyixian@huawei.com>
Signed-off-by: Lijun Ou <oulijun@huawei.com>
Signed-off-by: Wei Hu (Xavier) <xavier.huwei@huawei.com>
Signed-off-by: Shaobo Xu <xushaobo2@huawei.com>
Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
drivers/infiniband/hw/hns/hns_roce_cq.c
drivers/infiniband/hw/hns/hns_roce_qp.c
include/uapi/rdma/hns-abi.h

index 462b644bbbd78b67f984193e9ad8881184bd7f09..095a9100717d1bbb4193010963463963ba2bc8d5 100644 (file)
@@ -315,7 +315,7 @@ struct ib_cq *hns_roce_ib_create_cq(struct ib_device *ib_dev,
        struct hns_roce_dev *hr_dev = to_hr_dev(ib_dev);
        struct device *dev = hr_dev->dev;
        struct hns_roce_ib_create_cq ucmd;
-       struct hns_roce_ib_create_cq_resp resp;
+       struct hns_roce_ib_create_cq_resp resp = {};
        struct hns_roce_cq *hr_cq = NULL;
        struct hns_roce_uar *uar = NULL;
        int vector = attr->comp_vector;
@@ -389,7 +389,7 @@ struct ib_cq *hns_roce_ib_create_cq(struct ib_device *ib_dev,
        }
 
        if (context && (hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB) &&
-           (udata->outlen == sizeof(resp))) {
+           (udata->outlen >= sizeof(resp))) {
                ret = hns_roce_db_map_user(to_hr_ucontext(context),
                                           ucmd.db_addr, &hr_cq->db);
                if (ret) {
@@ -413,15 +413,14 @@ struct ib_cq *hns_roce_ib_create_cq(struct ib_device *ib_dev,
        hr_cq->cq_depth = cq_entries;
 
        if (context) {
+               resp.cqn = hr_cq->cqn;
                if ((hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB) &&
-                                       (udata->outlen == sizeof(resp))) {
+                                       (udata->outlen >= sizeof(resp))) {
                        hr_cq->db_en = 1;
-                       resp.cqn = hr_cq->cqn;
                        resp.cap_flags |= HNS_ROCE_SUPPORT_CQ_RECORD_DB;
-                       ret = ib_copy_to_udata(udata, &resp, sizeof(resp));
-               } else
-                       ret = ib_copy_to_udata(udata, &hr_cq->cqn, sizeof(u64));
+               }
 
+               ret = ib_copy_to_udata(udata, &resp, sizeof(resp));
                if (ret)
                        goto err_dbmap;
        }
@@ -430,7 +429,7 @@ struct ib_cq *hns_roce_ib_create_cq(struct ib_device *ib_dev,
 
 err_dbmap:
        if (context && (hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB) &&
-           (udata->outlen == sizeof(resp)))
+           (udata->outlen >= sizeof(resp)))
                hns_roce_db_unmap_user(to_hr_ucontext(context),
                                       &hr_cq->db);
 
index f0ad455ad62b2b2ee6f2bf5c00f620c1e4d5e6a3..e289a924e7890a6b955522d818d4660584920d2f 100644 (file)
@@ -506,7 +506,7 @@ static int hns_roce_create_qp_common(struct hns_roce_dev *hr_dev,
 {
        struct device *dev = hr_dev->dev;
        struct hns_roce_ib_create_qp ucmd;
-       struct hns_roce_ib_create_qp_resp resp;
+       struct hns_roce_ib_create_qp_resp resp = {};
        unsigned long qpn = 0;
        int ret = 0;
        u32 page_shift;
@@ -614,7 +614,7 @@ static int hns_roce_create_qp_common(struct hns_roce_dev *hr_dev,
                }
 
                if ((hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB) &&
-                   (udata->outlen == sizeof(resp)) &&
+                   (udata->outlen >= sizeof(resp)) &&
                    hns_roce_qp_has_rq(init_attr)) {
                        ret = hns_roce_db_map_user(
                                        to_hr_ucontext(ib_pd->uobject->context),
@@ -730,7 +730,7 @@ static int hns_roce_create_qp_common(struct hns_roce_dev *hr_dev,
        else
                hr_qp->doorbell_qpn = cpu_to_le64(hr_qp->qpn);
 
-       if (ib_pd->uobject && (udata->outlen == sizeof(resp)) &&
+       if (ib_pd->uobject && (udata->outlen >= sizeof(resp)) &&
                (hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB)) {
 
                /* indicate kernel supports record db */
@@ -759,7 +759,7 @@ err_qpn:
 err_wrid:
        if (ib_pd->uobject) {
                if ((hr_dev->caps.flags & HNS_ROCE_CAP_FLAG_RECORD_DB) &&
-                   (udata->outlen == sizeof(resp)) &&
+                   (udata->outlen >= sizeof(resp)) &&
                    hns_roce_qp_has_rq(init_attr))
                        hns_roce_db_unmap_user(
                                        to_hr_ucontext(ib_pd->uobject->context),
index 38e8f192bf72bfa9d48676faf0e108bbfb5cc490..f7af7e59a5e450929cce0eeb9f7472bde8150fbc 100644 (file)
@@ -42,8 +42,7 @@ struct hns_roce_ib_create_cq {
 };
 
 struct hns_roce_ib_create_cq_resp {
-       __u32   cqn;
-       __u32   reserved;
+       __u64   cqn; /* Only 32 bits used, 64 for compat */
        __u64   cap_flags;
 };