From: Jiaran Zhang <zhangjiaran@xxxxxxxxxx> According to the RoCE v1 specification, the sl (service level) 0-7 are mapped directly to priorities 0-7 respectively, sl 8-15 are reserved. The driver should verify whether the value of sl is larger than 7, if so, an exception should be returned. Fixes: d6a3627e311c ("RDMA/hns: Optimize wqe buffer set flow for post send") Signed-off-by: Jiaran Zhang <zhangjiaran@xxxxxxxxxx> Signed-off-by: Weihang Li <liweihang@xxxxxxxxxx> --- drivers/infiniband/hw/hns/hns_roce_hw_v2.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/drivers/infiniband/hw/hns/hns_roce_hw_v2.c b/drivers/infiniband/hw/hns/hns_roce_hw_v2.c index 7a1d30f..69386a5 100644 --- a/drivers/infiniband/hw/hns/hns_roce_hw_v2.c +++ b/drivers/infiniband/hw/hns/hns_roce_hw_v2.c @@ -427,9 +427,10 @@ static inline int set_ud_wqe(struct hns_roce_qp *qp, void *wqe, unsigned int *sge_idx, unsigned int owner_bit) { - struct hns_roce_dev *hr_dev = to_hr_dev(qp->ibqp.device); struct hns_roce_ah *ah = to_hr_ah(ud_wr(wr)->ah); struct hns_roce_v2_ud_send_wqe *ud_sq_wqe = wqe; + struct ib_device *ib_dev = qp->ibqp.device; + struct hns_roce_dev *hr_dev = to_hr_dev(ib_dev); unsigned int curr_idx = *sge_idx; int valid_num_sge; u32 msg_len = 0; @@ -489,6 +490,13 @@ static inline int set_ud_wqe(struct hns_roce_qp *qp, V2_UD_SEND_WQE_BYTE_36_TCLASS_S, ah->av.tclass); roce_set_field(ud_sq_wqe->byte_40, V2_UD_SEND_WQE_BYTE_40_FLOW_LABEL_M, V2_UD_SEND_WQE_BYTE_40_FLOW_LABEL_S, ah->av.flowlabel); + + if (unlikely(ah->av.sl > MAX_SERVICE_LEVEL)) { + ibdev_err(ib_dev, + "failed to fill ud av, ud sl (%d) shouldn't be larger than %d.\n", + ah->av.sl, MAX_SERVICE_LEVEL); + return -EINVAL; + } roce_set_field(ud_sq_wqe->byte_40, V2_UD_SEND_WQE_BYTE_40_SL_M, V2_UD_SEND_WQE_BYTE_40_SL_S, ah->av.sl); roce_set_field(ud_sq_wqe->byte_40, V2_UD_SEND_WQE_BYTE_40_PORTN_M, -- 2.8.1