summaryrefslogtreecommitdiff
path: root/drivers/infiniband/core
diff options
context:
space:
mode:
authorMajd Dibbiny <majd@mellanox.com>2017-11-14 14:51:56 +0200
committerJason Gunthorpe <jgg@mellanox.com>2017-12-27 15:40:35 -0700
commit727b7e9a65c01569f8e4f9809d6f2be8c331c42a (patch)
tree60eb18e715075ccba5abcf43eb849462930eb388 /drivers/infiniband/core
parent2e903b611b3e5b6ef1bf875a747368ec6b30f667 (diff)
IB/core: Make sure that PSN does not overflow
The rq/sq->psn is 24 bits as defined in the IB spec, therefore we mask out the 8 most significant bits to avoid overflow in modify_qp. Signed-off-by: Majd Dibbiny <majd@mellanox.com> Signed-off-by: Daniel Jurgens <danielj@mellanox.com> Reviewed-by: Parav Pandit <parav@mellanox.com> Signed-off-by: Leon Romanovsky <leon@kernel.org> Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
Diffstat (limited to 'drivers/infiniband/core')
-rw-r--r--drivers/infiniband/core/verbs.c16
1 files changed, 16 insertions, 0 deletions
diff --git a/drivers/infiniband/core/verbs.c b/drivers/infiniband/core/verbs.c
index 43e025435418..b53fb0e98751 100644
--- a/drivers/infiniband/core/verbs.c
+++ b/drivers/infiniband/core/verbs.c
@@ -1320,6 +1320,7 @@ static int ib_resolve_eth_dmac(struct ib_device *device,
int ib_modify_qp_with_udata(struct ib_qp *qp, struct ib_qp_attr *attr,
int attr_mask, struct ib_udata *udata)
{
+ u8 port = attr_mask & IB_QP_PORT ? attr->port_num : qp->port;
int ret;
if (attr_mask & IB_QP_AV) {
@@ -1327,6 +1328,21 @@ int ib_modify_qp_with_udata(struct ib_qp *qp, struct ib_qp_attr *attr,
if (ret)
return ret;
}
+
+ if (rdma_ib_or_roce(qp->device, port)) {
+ if (attr_mask & IB_QP_RQ_PSN && attr->rq_psn & ~0xffffff) {
+ pr_warn("%s: %s rq_psn overflow, masking to 24 bits\n",
+ __func__, qp->device->name);
+ attr->rq_psn &= 0xffffff;
+ }
+
+ if (attr_mask & IB_QP_SQ_PSN && attr->sq_psn & ~0xffffff) {
+ pr_warn("%s: %s sq_psn overflow, masking to 24 bits\n",
+ __func__, qp->device->name);
+ attr->sq_psn &= 0xffffff;
+ }
+ }
+
ret = ib_security_modify_qp(qp, attr, attr_mask, udata);
if (!ret && (attr_mask & IB_QP_PORT))
qp->port = attr->port_num;