RDMA/hns: Limit the size of extend sge of sq
authorLijun Ou <oulijun@huawei.com>
Sun, 30 Sep 2018 09:00:31 +0000 (17:00 +0800)
committerJason Gunthorpe <jgg@mellanox.com>
Wed, 3 Oct 2018 22:21:17 +0000 (16:21 -0600)
The hip08 split two hardware version. The version id are 0x20 and 0x21
according to the PCI revison. The max size of extend sge of sq is limited
to 2M for 0x20 version and 8M for 0x21 version. It may be exceeded to 2M
according to the algorithm that compute the product of wqe count and
extend sge number of every wqe. But the product always less than 8M.

Signed-off-by: Lijun Ou <oulijun@huawei.com>
Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
drivers/infiniband/hw/hns/hns_roce_device.h
drivers/infiniband/hw/hns/hns_roce_hw_v2.c
drivers/infiniband/hw/hns/hns_roce_hw_v2.h
drivers/infiniband/hw/hns/hns_roce_qp.c

index 34f8e90..b06d3e4 100644 (file)
@@ -670,6 +670,7 @@ struct hns_roce_caps {
        u32             max_sq_sg;      /* 2 */
        u32             max_sq_inline;  /* 32 */
        u32             max_rq_sg;      /* 2 */
+       u32             max_extend_sg;
        int             num_qps;        /* 256k */
        int             reserved_qps;
        u32             max_wqes;       /* 16k */
index 20cc866..d563d29 100644 (file)
@@ -1191,6 +1191,7 @@ static int hns_roce_v2_profile(struct hns_roce_dev *hr_dev)
        caps->num_cqs           = HNS_ROCE_V2_MAX_CQ_NUM;
        caps->max_cqes          = HNS_ROCE_V2_MAX_CQE_NUM;
        caps->max_sq_sg         = HNS_ROCE_V2_MAX_SQ_SGE_NUM;
+       caps->max_extend_sg     = HNS_ROCE_V2_MAX_EXTEND_SGE_NUM;
        caps->max_rq_sg         = HNS_ROCE_V2_MAX_RQ_SGE_NUM;
        caps->max_sq_inline     = HNS_ROCE_V2_MAX_SQ_INLINE;
        caps->num_uars          = HNS_ROCE_V2_UAR_NUM;
index 1877581..b921ca6 100644 (file)
@@ -50,6 +50,7 @@
 #define HNS_ROCE_V2_MAX_CQE_NUM                        0x10000
 #define HNS_ROCE_V2_MAX_RQ_SGE_NUM             0x100
 #define HNS_ROCE_V2_MAX_SQ_SGE_NUM             0xff
+#define HNS_ROCE_V2_MAX_EXTEND_SGE_NUM         0x200000
 #define HNS_ROCE_V2_MAX_SQ_INLINE              0x20
 #define HNS_ROCE_V2_UAR_NUM                    256
 #define HNS_ROCE_V2_PHY_UAR_NUM                        1
index 0e0c796..2805ab2 100644 (file)
@@ -31,6 +31,7 @@
  * SOFTWARE.
  */
 
+#include <linux/pci.h>
 #include <linux/platform_device.h>
 #include <rdma/ib_addr.h>
 #include <rdma/ib_umem.h>
@@ -372,6 +373,16 @@ static int hns_roce_set_user_sq_size(struct hns_roce_dev *hr_dev,
        if (hr_qp->sq.max_gs > 2)
                hr_qp->sge.sge_cnt = roundup_pow_of_two(hr_qp->sq.wqe_cnt *
                                                        (hr_qp->sq.max_gs - 2));
+
+       if ((hr_qp->sq.max_gs > 2) && (hr_dev->pci_dev->revision == 0x20)) {
+               if (hr_qp->sge.sge_cnt > hr_dev->caps.max_extend_sg) {
+                       dev_err(hr_dev->dev,
+                               "The extended sge cnt error! sge_cnt=%d\n",
+                               hr_qp->sge.sge_cnt);
+                       return -EINVAL;
+               }
+       }
+
        hr_qp->sge.sge_shift = 4;
 
        /* Get buf size, SQ and RQ  are aligned to page_szie */
@@ -465,6 +476,14 @@ static int hns_roce_set_kernel_sq_size(struct hns_roce_dev *hr_dev,
                hr_qp->sge.sge_shift = 4;
        }
 
+       if ((hr_qp->sq.max_gs > 2) && hr_dev->pci_dev->revision == 0x20) {
+               if (hr_qp->sge.sge_cnt > hr_dev->caps.max_extend_sg) {
+                       dev_err(dev, "The extended sge cnt error! sge_cnt=%d\n",
+                               hr_qp->sge.sge_cnt);
+                       return -EINVAL;
+               }
+       }
+
        /* Get buf size, SQ and RQ are aligned to PAGE_SIZE */
        page_size = 1 << (hr_dev->caps.mtt_buf_pg_sz + PAGE_SHIFT);
        hr_qp->sq.offset = 0;