Skip to content

Commit a24303d

Browse files
Hans Westgaard Ryvijay-suman
authored andcommitted
RDS/IB: Introduce bit_flag routines with memory-barrier for bit flags
'set_bit()' and 'clear_bit()' do not imply a memory barrier and should be surrounded by 'smp_mb__before_atomic()' and 'smp_mb__after_atomic()'. Orabug: 28388725 Fixes: a44b8b0ad261 ("net/rds: RDS connection shutdown stuck after CQ access violation error") Signed-off-by: Hans Westgaard Ry <[email protected]> Reviewed-by: William Kucharski <[email protected]>
1 parent eaf6ccd commit a24303d

File tree

2 files changed

+34
-6
lines changed

2 files changed

+34
-6
lines changed

net/rds/ib.h

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,29 @@
6161

6262
#define RDS_IB_CQ_ERR 2
6363
#define RDS_IB_NEED_SHUTDOWN 3
64+
static inline void set_bit_mb(long nr, unsigned long *flags)
65+
{
66+
/* set_bit() does not imply a memory barrier */
67+
smp_mb__before_atomic();
68+
set_bit(nr, flags);
69+
/* set_bit() does not imply a memory barrier */
70+
smp_mb__after_atomic();
71+
}
72+
73+
static inline void clear_bit_mb(long nr, unsigned long *flags)
74+
{
75+
/* clear_bit() does not imply a memory barrier */
76+
smp_mb__before_atomic();
77+
clear_bit(nr, flags);
78+
/* clear_bit() does not imply a memory barrier */
79+
smp_mb__after_atomic();
80+
}
81+
82+
enum rds_ib_conn_flags {
83+
RDS_IB_CLEAN_CACHE,
84+
RDS_IB_CQ_ERR,
85+
RDS_IB_NEED_SHUTDOWN
86+
};
6487

6588
#define RDS_IB_DEFAULT_FREG_PORT_NUM 1
6689

net/rds/ib_cm.c

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,7 @@ void rds_ib_cm_connect_complete(struct rds_connection *conn, struct rdma_cm_even
360360
}
361361

362362
ic->i_sl = ic->i_cm_id->route.path_rec->sl;
363-
clear_bit(RDS_IB_CQ_ERR, &ic->i_flags);
363+
clear_bit_mb(RDS_IB_CQ_ERR, &ic->i_flags);
364364

365365
/*
366366
* Init rings and fill recv. this needs to wait until protocol negotiation
@@ -524,7 +524,7 @@ static void rds_ib_cq_event_handler(struct ib_event *event, void *data)
524524
event->event, rds_ib_event_str(event->event), conn,
525525
&conn->c_laddr, &conn->c_faddr, conn->c_tos, ic, ic->i_cm_id);
526526

527-
set_ib_conn_flag(RDS_IB_CQ_ERR, ic);
527+
set_bit_mb(RDS_IB_CQ_ERR, &ic->i_flags);
528528
if (waitqueue_active(&rds_ib_ring_empty_wait))
529529
wake_up(&rds_ib_ring_empty_wait);
530530
if (test_bit(RDS_SHUTDOWN_WAITING, &conn->c_flags))
@@ -1165,7 +1165,7 @@ static int rds_ib_setup_qp(struct rds_connection *conn)
11651165
return ret;
11661166
}
11671167

1168-
set_ib_conn_flag(RDS_IB_NEED_SHUTDOWN, ic);
1168+
set_bit_mb(RDS_IB_NEED_SHUTDOWN, &ic->i_flags);
11691169

11701170
/* In the case of FRWR, mr registration wrs use the
11711171
* same work queue as the send wrs. To make sure that we are not
@@ -2049,7 +2049,6 @@ int rds_ib_conn_path_connect(struct rds_conn_path *cp)
20492049
ic->i_alt.cm_id = NULL;
20502050
}
20512051

2052-
smp_mb();
20532052
if (test_bit(RDS_IB_NEED_SHUTDOWN, &ic->i_flags)) {
20542053
/* The shutdown-path hasn't completed yet,
20552054
* so we can't make any progress quite yet.
@@ -2212,6 +2211,8 @@ void rds_ib_conn_path_shutdown_final(struct rds_conn_path *cp)
22122211
tasklet_kill(&ic->i_stasklet);
22132212
tasklet_kill(&ic->i_rtasklet);
22142213

2214+
clear_bit_mb(RDS_IB_CQ_ERR, &ic->i_flags);
2215+
22152216
/* first destroy the ib state that generates callbacks */
22162217
if (ic->i_cm_id->qp)
22172218
rdma_destroy_qp(ic->i_cm_id);
@@ -2245,8 +2246,12 @@ void rds_ib_conn_path_shutdown_final(struct rds_conn_path *cp)
22452246

22462247
rds_spawn_destroy_cm_id(cm_id);
22472248

2248-
clear_bit(RDS_IB_NEED_SHUTDOWN, &ic->i_flags);
2249-
smp_mb();
2249+
ic->i_pd = NULL;
2250+
ic->i_mr = NULL;
2251+
ic->i_send_hdrs = NULL;
2252+
ic->i_recv_hdrs = NULL;
2253+
ic->i_ack = NULL;
2254+
clear_bit_sb(RDS_IB_NEED_SHUTDOWN, &ic->i_flags);
22502255
}
22512256

22522257
BUG_ON(ic->rds_ibdev);

0 commit comments

Comments
 (0)