ocfs2: o2net: set tcp user timeout to max value

When tcp retransmit timeout(15mins), the connection will be closed.
Pending messages may be lost during this time.  So we set tcp user
timeout to override the retransmit timeout to the max value.  This is OK
for ocfs2 since we have disk heartbeat, if peer crash, the disk
heartbeat will timeout and it will be evicted, if disk heartbeat not
timeout and connection idle for a long time, then this means the cluster
enters split-brain state, since fence can't happen, we'd better keep the
connection and wait network recover.

Signed-off-by: Junxiao Bi <junxiao.bi@oracle.com>
Reviewed-by: Srinivas Eeda <srinivas.eeda@oracle.com>
Reviewed-by: Mark Fasheh <mfasheh@suse.de>
Cc: Joel Becker <jlbec@evilplan.org>
Cc: Joseph Qi <joseph.qi@huawei.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
This commit is contained in:
Junxiao Bi 2014-08-29 15:19:02 -07:00 коммит произвёл Linus Torvalds
Родитель c43c363def
Коммит 8e9801dfe3
2 изменённых файлов: 21 добавлений и 0 удалений

Просмотреть файл

@ -1480,6 +1480,14 @@ static int o2net_set_nodelay(struct socket *sock)
return ret; return ret;
} }
static int o2net_set_usertimeout(struct socket *sock)
{
int user_timeout = O2NET_TCP_USER_TIMEOUT;
return kernel_setsockopt(sock, SOL_TCP, TCP_USER_TIMEOUT,
(char *)&user_timeout, sizeof(user_timeout));
}
static void o2net_initialize_handshake(void) static void o2net_initialize_handshake(void)
{ {
o2net_hand->o2hb_heartbeat_timeout_ms = cpu_to_be32( o2net_hand->o2hb_heartbeat_timeout_ms = cpu_to_be32(
@ -1663,6 +1671,12 @@ static void o2net_start_connect(struct work_struct *work)
goto out; goto out;
} }
ret = o2net_set_usertimeout(sock);
if (ret) {
mlog(ML_ERROR, "set TCP_USER_TIMEOUT failed with %d\n", ret);
goto out;
}
o2net_register_callbacks(sc->sc_sock->sk, sc); o2net_register_callbacks(sc->sc_sock->sk, sc);
spin_lock(&nn->nn_lock); spin_lock(&nn->nn_lock);
@ -1844,6 +1858,12 @@ static int o2net_accept_one(struct socket *sock, int *more)
goto out; goto out;
} }
ret = o2net_set_usertimeout(new_sock);
if (ret) {
mlog(ML_ERROR, "set TCP_USER_TIMEOUT failed with %d\n", ret);
goto out;
}
slen = sizeof(sin); slen = sizeof(sin);
ret = new_sock->ops->getname(new_sock, (struct sockaddr *) &sin, ret = new_sock->ops->getname(new_sock, (struct sockaddr *) &sin,
&slen, 1); &slen, 1);

Просмотреть файл

@ -63,6 +63,7 @@ typedef void (o2net_post_msg_handler_func)(int status, void *data,
#define O2NET_KEEPALIVE_DELAY_MS_DEFAULT 2000 #define O2NET_KEEPALIVE_DELAY_MS_DEFAULT 2000
#define O2NET_IDLE_TIMEOUT_MS_DEFAULT 30000 #define O2NET_IDLE_TIMEOUT_MS_DEFAULT 30000
#define O2NET_TCP_USER_TIMEOUT 0x7fffffff
/* TODO: figure this out.... */ /* TODO: figure this out.... */
static inline int o2net_link_down(int err, struct socket *sock) static inline int o2net_link_down(int err, struct socket *sock)