From b6c8aca458f60e17ec645e3afa34f91a39bf952a Mon Sep 17 00:00:00 2001 From: Rongsong Shen Date: Fri, 29 May 2026 08:43:36 +0000 Subject: [PATCH] fix(ha-config-bootstrap): wire ha_restore_term in cluster_init_phase1 and store last_known_committed_lsn from CtrlHelloReply (validation fixes) --- src/controller/cluster.c | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/src/controller/cluster.c b/src/controller/cluster.c index 215df77..d24bb28 100644 --- a/src/controller/cluster.c +++ b/src/controller/cluster.c @@ -215,6 +215,21 @@ static int myreq_handler(vtask_t* task) if (request.body_which == Request_body_ctrlhellomsg) { /* Extended OP_ctrlHello with CtrlHelloRequest body — state sync (Req 6.5–6.7) */ rc = handle_ctrlhello(c, ep, &request); + } else if (request.body_which == Request_body_replymsg + && request.body.replymsg + && request.body.replymsg->data_which + == RequestReply_data_ctrlhelloreplymsg) { + /* Standby receives CtrlHelloReply from primary — update last known + * committed LSN and config tag for use in RDHUP failover path. */ + ctrl_hello_reply_t *chrep = request.body.replymsg->data.ctrlhelloreplymsg; + if (chrep) { + atomic_store_explicit(&c->ha.last_known_committed_lsn, + chrep->committed_lsn, memory_order_release); + c->ha.last_known_committed_config_tag = chrep->config_tag; + INFO("HA: CtrlHelloReply from primary: committed_lsn=%lu config_tag=%lu", + (unsigned long)chrep->committed_lsn, + (unsigned long)chrep->config_tag); + } } else { /* Legacy plain OP_hello (nop path) */ reply.status = 0; @@ -651,6 +666,20 @@ int cluster_init_phase1(cluster_t* c) ERROR("ha_init failed: %d", rc); return rc; } + + /* Restore persisted election term + voted_for from ha-term.bin (Req 9.2). + * ha_persist_term() already writes on vote grant; this reads it back at + * startup so the restarted node remembers its last term. */ + if (c->myconf->workdir) { + rc = ha_restore_term(&c->ha, c->myconf->workdir); + if (rc == 0) { + INFO("HA: restored term=%lu from %s/ha-term.bin", + (unsigned long)atomic_load(&c->ha.term), c->myconf->workdir); + } else if (rc != -ENOENT) { + WARN("HA: ha_restore_term failed: %d", rc); + } + } + ha_install_sigusr1(&c->ha); /* Initialize standby endpoint tracking */