fix(controller): clamp committed_config_tag to own loaded config on promotion
bug-1462: raft_cb_become_leader baselined committed_config_tag to the majority-safe floor across voters, correct for WAL LSN safety but wrong for config tags — a leader's own actively-loaded config isn't speculative like an unacknowledged WAL entry. On a fresh deploy every peer reports tag=0 except the new primary, so the floor stuck at 0 forever and late-joining standbys never received a config push. ha_promotion_config_tag_floor() clamps to max(safe_tag, self_tag), mirroring bug-1060's WAL-truncation clamp pattern. Validated with 20-round sequential (63 jobs, zero loss) and 20-round chaotic overlapping-kill (zero committed divergence, zero committed job loss) HA failover soaks; unit suite 977/977 green.
This commit is contained in:
parent
ee8473bd99
commit
0649e17f62
3 changed files with 106 additions and 2 deletions
|
|
@ -814,6 +814,13 @@ uint64_t ha_promotion_truncate_floor(uint64_t safe_lsn, uint64_t durable_tip)
|
|||
return safe_lsn > durable_tip ? safe_lsn : durable_tip;
|
||||
}
|
||||
|
||||
/* ── bug-1462: never floor committed_config_tag below the leader's own
|
||||
* loaded config — see ha.h for full rationale. */
|
||||
uint64_t ha_promotion_config_tag_floor(uint64_t safe_tag, uint64_t self_tag)
|
||||
{
|
||||
return safe_tag > self_tag ? safe_tag : self_tag;
|
||||
}
|
||||
|
||||
/* ── raft-drive-async task 1.1: peer-scaled liveness reservation ─────────────
|
||||
*
|
||||
* Pure: reserved = max(1, min(n_peers - 1, n_vcpus - 1)). The floor of 1 is
|
||||
|
|
@ -1275,8 +1282,16 @@ static void raft_cb_become_leader(void *ctx, uint64_t term)
|
|||
* Req 2.3 (ha-repl-hardening). */
|
||||
atomic_store_explicit(&ha->last_known_committed_lsn, safe_lsn,
|
||||
memory_order_release);
|
||||
/* Update committed config tag baseline for the post-election decision loop */
|
||||
atomic_store_explicit(&ha->committed_config_tag, safe_tag,
|
||||
/* Update committed config tag baseline for the post-election decision
|
||||
* loop. bug-1462: clamp to the leader's OWN loaded config tag —
|
||||
* unlike WAL LSN, a node's actively-loaded config is never
|
||||
* speculative, so the bare majority floor (correct for LSN) must
|
||||
* not be allowed to strand a real config behind an all-zero floor
|
||||
* reported by voters that never received a live config push.
|
||||
* See ha_promotion_config_tag_floor's doc comment (ha.h). */
|
||||
uint64_t committed_tag_floor =
|
||||
ha_promotion_config_tag_floor(safe_tag, ectx->self_tag);
|
||||
atomic_store_explicit(&ha->committed_config_tag, committed_tag_floor,
|
||||
memory_order_release);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue