Commit 836a0fbb authored by Leon Romanovsky's avatar Leon Romanovsky Committed by Doug Ledford
Browse files

RDMA: Check umem pointer validity prior to release



Update ib_umem_release() to behave similarly to kfree() and allow
submitting NULL pointer as safe input to this function.

Fixes: a52c8e24 ("RDMA: Clean destroy CQ in drivers do not return errors")
Signed-off-by: default avatarLeon Romanovsky <leonro@mellanox.com>
Signed-off-by: default avatarDoug Ledford <dledford@redhat.com>
parent 89a6da3c
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -361,6 +361,9 @@ static void __ib_umem_release_tail(struct ib_umem *umem)
 */
void ib_umem_release(struct ib_umem *umem)
{
	if (!umem)
		return;

	if (umem->is_odp) {
		ib_umem_odp_release(to_ib_umem_odp(umem));
		__ib_umem_release_tail(umem);
+9 −20
Original line number Diff line number Diff line
@@ -805,9 +805,7 @@ int bnxt_re_destroy_qp(struct ib_qp *ib_qp, struct ib_udata *udata)
		rdev->sqp_ah = NULL;
	}

	if (!IS_ERR_OR_NULL(qp->rumem))
	ib_umem_release(qp->rumem);
	if (!IS_ERR_OR_NULL(qp->sumem))
	ib_umem_release(qp->sumem);

	mutex_lock(&rdev->qp_lock);
@@ -1201,12 +1199,8 @@ struct ib_qp *bnxt_re_create_qp(struct ib_pd *ib_pd,
qp_destroy:
	bnxt_qplib_destroy_qp(&rdev->qplib_res, &qp->qplib_qp);
free_umem:
	if (udata) {
		if (qp->rumem)
	ib_umem_release(qp->rumem);
		if (qp->sumem)
	ib_umem_release(qp->sumem);
	}
fail:
	kfree(qp);
	return ERR_PTR(rc);
@@ -1302,7 +1296,6 @@ void bnxt_re_destroy_srq(struct ib_srq *ib_srq, struct ib_udata *udata)
	if (qplib_srq->cq)
		nq = qplib_srq->cq->nq;
	bnxt_qplib_destroy_srq(&rdev->qplib_res, qplib_srq);
	if (srq->umem)
	ib_umem_release(srq->umem);
	atomic_dec(&rdev->srq_count);
	if (nq)
@@ -1412,7 +1405,6 @@ int bnxt_re_create_srq(struct ib_srq *ib_srq,
	return 0;

fail:
	if (srq->umem)
	ib_umem_release(srq->umem);
exit:
	return rc;
@@ -2528,7 +2520,6 @@ void bnxt_re_destroy_cq(struct ib_cq *ib_cq, struct ib_udata *udata)
	nq = cq->qplib_cq.nq;

	bnxt_qplib_destroy_cq(&rdev->qplib_res, &cq->qplib_cq);
	if (!cq->umem)
	ib_umem_release(cq->umem);

	atomic_dec(&rdev->cq_count);
@@ -2632,7 +2623,6 @@ int bnxt_re_create_cq(struct ib_cq *ibcq, const struct ib_cq_init_attr *attr,
	return 0;

c2fail:
	if (udata)
	ib_umem_release(cq->umem);
fail:
	kfree(cq->cql);
@@ -3340,7 +3330,6 @@ int bnxt_re_dereg_mr(struct ib_mr *ib_mr, struct ib_udata *udata)
		mr->npages = 0;
		mr->pages = NULL;
	}
	if (!IS_ERR_OR_NULL(mr->ib_umem))
	ib_umem_release(mr->ib_umem);

	kfree(mr);
+1 −2
Original line number Diff line number Diff line
@@ -346,7 +346,6 @@ static int iwch_dereg_mr(struct ib_mr *ib_mr, struct ib_udata *udata)
	xa_erase_irq(&rhp->mrs, mmid);
	if (mhp->kva)
		kfree((void *) (unsigned long) mhp->kva);
	if (mhp->umem)
	ib_umem_release(mhp->umem);
	pr_debug("%s mmid 0x%x ptr %p\n", __func__, mmid, mhp);
	kfree(mhp);
+1 −2
Original line number Diff line number Diff line
@@ -808,7 +808,6 @@ int c4iw_dereg_mr(struct ib_mr *ib_mr, struct ib_udata *udata)
				  mhp->attr.pbl_size << 3);
	if (mhp->kva)
		kfree((void *) (unsigned long) mhp->kva);
	if (mhp->umem)
	ib_umem_release(mhp->umem);
	pr_debug("mmid 0x%x ptr %p\n", mmid, mhp);
	c4iw_put_wr_wait(mhp->wr_waitp);
+1 −1
Original line number Diff line number Diff line
@@ -1513,8 +1513,8 @@ int efa_dereg_mr(struct ib_mr *ibmr, struct ib_udata *udata)
		err = efa_com_dereg_mr(&dev->edev, &params);
		if (err)
			return err;
		ib_umem_release(mr->umem);
	}
	ib_umem_release(mr->umem);

	kfree(mr);

Loading