Skip to content

Commit 817a68a

Browse files
Dennis Dalessandrojgunthorpe
authored andcommitted
IB/hfi1, qib: Ensure RCU is locked when accessing list
The packet handling function, specifically the iteration of the qp list for mad packet processing misses locking RCU before running through the list. Not only is this incorrect, but the list_for_each_entry_rcu() call can not be called with a conditional check for lock dependency. Remedy this by invoking the rcu lock and unlock around the critical section. This brings MAD packet processing in line with what is done for non-MAD packets. Fixes: 7724105 ("IB/hfi1: add driver files") Link: https://lore.kernel.org/r/[email protected] Reviewed-by: Mike Marciniszyn <[email protected]> Signed-off-by: Dennis Dalessandro <[email protected]> Signed-off-by: Jason Gunthorpe <[email protected]>
1 parent 801b67f commit 817a68a

File tree

2 files changed

+5
-1
lines changed

2 files changed

+5
-1
lines changed

drivers/infiniband/hw/hfi1/verbs.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -515,10 +515,11 @@ static inline void hfi1_handle_packet(struct hfi1_packet *packet,
515515
opa_get_lid(packet->dlid, 9B));
516516
if (!mcast)
517517
goto drop;
518+
rcu_read_lock();
518519
list_for_each_entry_rcu(p, &mcast->qp_list, list) {
519520
packet->qp = p->qp;
520521
if (hfi1_do_pkey_check(packet))
521-
goto drop;
522+
goto unlock_drop;
522523
spin_lock_irqsave(&packet->qp->r_lock, flags);
523524
packet_handler = qp_ok(packet);
524525
if (likely(packet_handler))
@@ -527,6 +528,7 @@ static inline void hfi1_handle_packet(struct hfi1_packet *packet,
527528
ibp->rvp.n_pkt_drops++;
528529
spin_unlock_irqrestore(&packet->qp->r_lock, flags);
529530
}
531+
rcu_read_unlock();
530532
/*
531533
* Notify rvt_multicast_detach() if it is waiting for us
532534
* to finish.

drivers/infiniband/hw/qib/qib_verbs.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -329,8 +329,10 @@ void qib_ib_rcv(struct qib_ctxtdata *rcd, void *rhdr, void *data, u32 tlen)
329329
if (mcast == NULL)
330330
goto drop;
331331
this_cpu_inc(ibp->pmastats->n_multicast_rcv);
332+
rcu_read_lock();
332333
list_for_each_entry_rcu(p, &mcast->qp_list, list)
333334
qib_qp_rcv(rcd, hdr, 1, data, tlen, p->qp);
335+
rcu_read_unlock();
334336
/*
335337
* Notify rvt_multicast_detach() if it is waiting for us
336338
* to finish.

0 commit comments

Comments
 (0)