Skip to content

Commit b92ae13

Browse files
Alexandre Bouninetorvalds
authored andcommitted
rapidio/rio_cm: avoid GFP_KERNEL in atomic context
As reported by Alexey Khoroshilov (https://lkml.org/lkml/2016/9/9/737): riocm_send_close() is called from rio_cm_shutdown() under spin_lock_bh(idr_lock), but riocm_send_close() uses a GFP_KERNEL allocation. Fix by taking riocm_send_close() outside of spinlock protected code. [[email protected]: remove unneeded `if (!list_empty())'] Link: http://lkml.kernel.org/r/[email protected] Signed-off-by: Alexandre Bounine <[email protected]> Reported-by: Alexey Khoroshilov <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
1 parent 63b52c4 commit b92ae13

File tree

1 file changed

+16
-3
lines changed

1 file changed

+16
-3
lines changed

drivers/rapidio/rio_cm.c

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2247,17 +2247,30 @@ static int rio_cm_shutdown(struct notifier_block *nb, unsigned long code,
22472247
{
22482248
struct rio_channel *ch;
22492249
unsigned int i;
2250+
LIST_HEAD(list);
22502251

22512252
riocm_debug(EXIT, ".");
22522253

2254+
/*
2255+
* If there are any channels left in connected state send
2256+
* close notification to the connection partner.
2257+
* First build a list of channels that require a closing
2258+
* notification because function riocm_send_close() should
2259+
* be called outside of spinlock protected code.
2260+
*/
22532261
spin_lock_bh(&idr_lock);
22542262
idr_for_each_entry(&ch_idr, ch, i) {
2255-
riocm_debug(EXIT, "close ch %d", ch->id);
2256-
if (ch->state == RIO_CM_CONNECTED)
2257-
riocm_send_close(ch);
2263+
if (ch->state == RIO_CM_CONNECTED) {
2264+
riocm_debug(EXIT, "close ch %d", ch->id);
2265+
idr_remove(&ch_idr, ch->id);
2266+
list_add(&ch->ch_node, &list);
2267+
}
22582268
}
22592269
spin_unlock_bh(&idr_lock);
22602270

2271+
list_for_each_entry(ch, &list, ch_node)
2272+
riocm_send_close(ch);
2273+
22612274
return NOTIFY_DONE;
22622275
}
22632276

0 commit comments

Comments
 (0)