Skip to content

Commit 50ee713

Browse files
Wei Lin GuayLinuxMinion
authored andcommitted
Revert "net/rds: Revert "RDS: add reconnect retry scheme for stalled
connections"" This commit restores commit 5acb959 ("RDS: add reconnect retry scheme for stalled connections"). Even though this retry scheme "workaround" causes a long brownout time in the OVM configuration, it is needed to avoid RDS loopback connections stalls after switch reboot in the bare-metal system. As for now, the plan agreed with Exadata is to put back this commit first and have a similar code path among QU6, QU5 and QU4. Orabug: 26497333 Signed-off-by: Wei Lin Guay <[email protected]> Reviewed-by: Ajaykumar Hotchandani <[email protected]>
1 parent d5c9b79 commit 50ee713

File tree

7 files changed

+79
-28
lines changed

7 files changed

+79
-28
lines changed

net/rds/connection.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -260,6 +260,9 @@ static struct rds_connection *__rds_conn_create(struct net *net,
260260

261261
__rds_conn_path_init(conn, cp, is_outgoing);
262262
cp->cp_index = i;
263+
cp->cp_reconnect_retry = rds_sysctl_reconnect_retry_ms;
264+
cp->cp_reconnect_retry_count = 0;
265+
263266
if (conn->c_loopback)
264267
cp->cp_wq = rds_local_wq;
265268
else

net/rds/ib_cm.c

Lines changed: 14 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -937,22 +937,23 @@ int rds_ib_cm_handle_connect(struct rdma_cm_id *cm_id,
937937
rds_ib_stats_inc(s_ib_listen_closed_stale);
938938
} else if (rds_conn_state(conn) == RDS_CONN_CONNECTING) {
939939
unsigned long now = get_seconds();
940+
unsigned long retry = conn->c_reconnect_retry;
940941

941-
/*
942-
* after 15 seconds, give up on existing connection
943-
* attempts and make them try again. At this point
944-
* it's no longer a race but something has gone
945-
* horribly wrong
942+
943+
/* after retry seconds, give up on
944+
* existing connection attempts and try again.
945+
* At this point it's no longer backoff race but
946+
* something has gone horribly wrong.
946947
*/
948+
retry = DIV_ROUND_UP(retry, 1000);
947949
if (now > conn->c_connection_start &&
948-
now - conn->c_connection_start > 15) {
949-
printk(KERN_CRIT "RDS/IB: connection "
950-
"<%u.%u.%u.%u,%u.%u.%u.%u,%d> "
951-
"racing for 15s, forcing reset ",
952-
NIPQUAD(conn->c_laddr),
953-
NIPQUAD(conn->c_faddr),
954-
conn->c_tos);
955-
rds_conn_drop(conn, DR_IB_REQ_WHILE_CONNECTING);
950+
now - conn->c_connection_start > retry) {
951+
pr_info("RDS/IB: conn <%pI4,%pI4,%d> racing for more than %lus, retry\n",
952+
&conn->c_laddr, &conn->c_faddr,
953+
conn->c_tos, retry);
954+
set_bit(RDS_RECONNECT_TIMEDOUT,
955+
&conn->c_reconn_flags);
956+
rds_conn_drop(conn, DR_RECONNECT_TIMEOUT);
956957
rds_ib_stats_inc(s_ib_listen_closed_stale);
957958
} else {
958959
/* Wait and see - our connect may still be succeeding */

net/rds/rdma_transport.c

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -308,8 +308,12 @@ int rds_rdma_cm_event_handler(struct rdma_cm_id *cm_id,
308308
"ADDR_CHANGE: calling rds_conn_drop <%u.%u.%u.%u,%u.%u.%u.%u,%d>\n",
309309
NIPQUAD(conn->c_laddr), NIPQUAD(conn->c_faddr),
310310
conn->c_tos);
311-
if (!rds_conn_self_loopback_passive(conn))
311+
if (!rds_conn_self_loopback_passive(conn)) {
312+
queue_delayed_work(conn->c_path[0].cp_wq,
313+
&conn->c_reconn_w,
314+
msecs_to_jiffies(conn->c_reconnect_retry));
312315
rds_conn_drop(conn, DR_IB_ADDR_CHANGE);
316+
}
313317
}
314318
break;
315319

net/rds/rds.h

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,8 @@ enum {
145145
#define RDS_MPATH_WORKERS 8
146146
#define RDS_MPATH_HASH(rs, n) (jhash_1word((rs)->rs_bound_port, \
147147
(rs)->rs_hash_initval) & ((n) - 1))
148+
/* Bits for c_reconn_flags */
149+
#define RDS_RECONNECT_TIMEDOUT 0
148150
enum rds_conn_drop_src {
149151
/* rds-core */
150152
DR_DEFAULT,
@@ -318,15 +320,6 @@ struct rds_connection {
318320
unsigned int c_version;
319321
struct net *c_net;
320322

321-
/* Re-connect stall diagnostics */
322-
unsigned long c_reconnect_start;
323-
unsigned int c_reconnect_drops;
324-
int c_reconnect_warn;
325-
int c_reconnect_err;
326-
int c_to_index;
327-
328-
unsigned int c_reconnect;
329-
330323
/* Qos support */
331324
u8 c_tos;
332325

@@ -1135,6 +1128,8 @@ extern unsigned long rds_sysctl_trace_flags;
11351128
extern unsigned int rds_sysctl_trace_level;
11361129
extern unsigned int rds_sysctl_shutdown_trace_start_time;
11371130
extern unsigned int rds_sysctl_shutdown_trace_end_time;
1131+
extern unsigned long rds_sysctl_reconnect_retry_ms;
1132+
extern unsigned int rds_sysctl_reconnect_max_retries;
11381133

11391134
/* threads.c */
11401135
int rds_threads_init(void);

net/rds/rds_single_path.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#define c_send_w c_path[0].cp_send_w
2222
#define c_recv_w c_path[0].cp_recv_w
2323
#define c_conn_w c_path[0].cp_conn_w
24+
#define c_reconn_w c_path[0].cp_reconn_w
2425
#define c_down_w c_path[0].cp_down_w
2526
#define c_cm_lock c_path[0].cp_cm_lock
2627
#define c_waitq c_path[0].cp_waitq
@@ -31,6 +32,8 @@
3132
#define c_acl_init c_path[0].cp_acl_init
3233
#define c_connection_start c_path[0].cp_connection_start
3334
#define c_reconnect_racing c_path[0].cp_reconnect_racing
35+
#define c_reconnect_retry c_path[0].cp_reconnect_retry
36+
#define c_reconn_flags c_path[0].cp_reconn_flags
3437
#define c_reconnect c_path[0].cp_reconnect
3538
#define c_to_index c_path[0].cp_to_index
3639
#define c_base_conn c_path[0].cp_base_conn

net/rds/sysctl.c

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,13 @@ unsigned int rds_sysctl_ping_enable = 1;
5252
unsigned int rds_sysctl_shutdown_trace_start_time;
5353
unsigned int rds_sysctl_shutdown_trace_end_time;
5454

55+
unsigned long rds_sysctl_reconnect_retry_ms = 1000;
56+
static unsigned long reconnect_retry_ms_min = 100;
57+
static unsigned long reconnect_retry_ms_max = 15000;
58+
59+
unsigned int rds_sysctl_reconnect_max_retries = 60;
60+
static unsigned long reconnect_min_retries = 15;
61+
5562
/*
5663
* We have official values, but must maintain the sysctl interface for existing
5764
* software that expects to find these values here.
@@ -126,6 +133,25 @@ static struct ctl_table rds_sysctl_rds_table[] = {
126133
.maxlen = sizeof(int),
127134
.mode = 0644,
128135
.proc_handler = &proc_dointvec,
136+
137+
},
138+
{
139+
.procname = "reconnect_retry_ms",
140+
.data = &rds_sysctl_reconnect_retry_ms,
141+
.maxlen = sizeof(unsigned long),
142+
.mode = 0644,
143+
.proc_handler = proc_dointvec_minmax,
144+
.extra1 = &reconnect_retry_ms_min,
145+
.extra2 = &reconnect_retry_ms_max,
146+
},
147+
{
148+
.procname = "reconnect_max_retries",
149+
.data = &rds_sysctl_reconnect_max_retries,
150+
.maxlen = sizeof(unsigned int),
151+
.mode = 0644,
152+
.proc_handler = proc_dointvec_minmax,
153+
.extra1 = &reconnect_min_retries,
154+
.extra2 = &rds_sysctl_reconnect_max_retries,
129155
},
130156
{ }
131157
};

net/rds/threads.c

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -93,6 +93,8 @@ void rds_connect_path_complete(struct rds_conn_path *cp, int curr)
9393
conn, &conn->c_laddr, &conn->c_faddr, conn->c_tos);
9494

9595
cp->cp_reconnect_jiffies = 0;
96+
cp->cp_reconnect_retry = rds_sysctl_reconnect_retry_ms;
97+
cp->cp_reconnect_retry_count = 0;
9698
set_bit(0, &conn->c_map_queued);
9799
queue_delayed_work(cp->cp_wq, &cp->cp_send_w, 0);
98100
queue_delayed_work(cp->cp_wq, &cp->cp_recv_w, 0);
@@ -146,7 +148,8 @@ void rds_queue_reconnect(struct rds_conn_path *cp)
146148
return;
147149

148150
set_bit(RDS_RECONNECT_PENDING, &cp->cp_flags);
149-
if (cp->cp_reconnect_jiffies == 0) {
151+
if (cp->cp_reconnect_jiffies == 0 ||
152+
test_and_clear_bit(RDS_RECONNECT_TIMEDOUT, &cp->cp_reconn_flags)) {
150153
cp->cp_reconnect_jiffies = rds_sysctl_reconnect_min_jiffies;
151154
queue_delayed_work(cp->cp_wq, &cp->cp_conn_w, 0);
152155
return;
@@ -316,12 +319,28 @@ void rds_reconnect_timeout(struct work_struct *work)
316319
cp_reconn_w.work);
317320
struct rds_connection *conn = cp->cp_conn;
318321

319-
if (!rds_conn_path_up(cp)) {
320-
rds_rtd(RDS_RTD_CM,
321-
"conn <%pI4,%pI4,%d> not up, retry(%d)\n",
322+
if (cp->cp_reconnect_retry_count > rds_sysctl_reconnect_max_retries) {
323+
pr_info("RDS: connection <%pI4,%pI4,%d> reconnect retries(%d) exceeded, stop retry\n",
322324
&conn->c_laddr, &conn->c_faddr, conn->c_tos,
323325
cp->cp_reconnect_retry_count);
324-
rds_conn_path_drop(cp, DR_RECONNECT_TIMEOUT);
326+
return;
327+
}
328+
329+
if (!rds_conn_up(conn)) {
330+
if (rds_conn_state(conn) == RDS_CONN_DISCONNECTING) {
331+
queue_delayed_work(cp->cp_wq, &cp->cp_reconn_w,
332+
msecs_to_jiffies(100));
333+
} else {
334+
cp->cp_reconnect_retry_count++;
335+
rds_rtd(RDS_RTD_CM,
336+
"conn <%pI4,%pI4,%d> not up, retry(%d)\n",
337+
&conn->c_laddr, &conn->c_faddr, conn->c_tos,
338+
cp->cp_reconnect_retry_count);
339+
queue_delayed_work(cp->cp_wq, &cp->cp_reconn_w,
340+
msecs_to_jiffies(cp->cp_reconnect_retry));
341+
set_bit(RDS_RECONNECT_TIMEDOUT, &cp->cp_reconn_flags);
342+
rds_conn_drop(conn, DR_RECONNECT_TIMEOUT);
343+
}
325344
}
326345
}
327346

0 commit comments

Comments
 (0)