diff options
Diffstat (limited to 'ovsdb/raft.c')
-rw-r--r-- | ovsdb/raft.c | 39 |
1 files changed, 38 insertions, 1 deletions
diff --git a/ovsdb/raft.c b/ovsdb/raft.c index 515eadab3..708b0624c 100644 --- a/ovsdb/raft.c +++ b/ovsdb/raft.c @@ -1421,8 +1421,20 @@ raft_conn_run(struct raft *raft, struct raft_conn *conn) jsonrpc_session_run(conn->js); unsigned int new_seqno = jsonrpc_session_get_seqno(conn->js); - bool just_connected = (new_seqno != conn->js_seqno + bool reconnected = new_seqno != conn->js_seqno; + bool just_connected = (reconnected && jsonrpc_session_is_connected(conn->js)); + + if (reconnected) { + /* Clear 'last_install_snapshot_request' since it might not reach the + * destination or server was restarted. */ + struct raft_server *server = raft_find_server(raft, &conn->sid); + if (server) { + free(server->last_install_snapshot_request); + server->last_install_snapshot_request = NULL; + } + } + conn->js_seqno = new_seqno; if (just_connected) { if (raft->joining) { @@ -3296,6 +3308,31 @@ raft_send_install_snapshot_request(struct raft *raft, .election_timer = raft->election_timer, /* use latest value */ } }; + + if (s->last_install_snapshot_request) { + struct raft_install_snapshot_request *old, *new; + + old = s->last_install_snapshot_request; + new = &rpc.install_snapshot_request; + if ( old->term == new->term + && old->last_index == new->last_index + && old->last_term == new->last_term + && old->last_servers == new->last_servers + && old->data == new->data + && old->election_timer == new->election_timer + && uuid_equals(&old->last_eid, &new->last_eid)) { + static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(5, 5); + + VLOG_WARN_RL(&rl, "not sending exact same install_snapshot_request" + " to server %s again", s->nickname); + return; + } + } + free(s->last_install_snapshot_request); + CONST_CAST(struct raft_server *, s)->last_install_snapshot_request + = xmemdup(&rpc.install_snapshot_request, + sizeof rpc.install_snapshot_request); + raft_send(raft, &rpc); } |