Skip to content

DAOS-19820 dtx: resync old DTX after quick engine restart - #19361

Open
liuxuezhao wants to merge 2 commits into
release/2.8from
lxz/quick_restart_DTX_28
Open

liuxuezhao wants to merge 2 commits into
release/2.8from
lxz/quick_restart_DTX_28

Conversation

@liuxuezhao

Copy link
Copy Markdown
Contributor

If the DTX leader engine is killed and restarted quickly without pool map change, the DTX entries that have been replied to the client as committable (only in leader's DRAM CoS cache) but not yet batched committed are never committed:

  • the DTX resync triggered by pool map update on the restarted engine skips the entries whose version equals the resync version (to avoid racing with in-flight IO handlers), but there is no such handler for the entries generated before the engine start;
  • the stand-alone read on the leader ignores the non-committed leader DTX, and DTX refresh from non-leader gets PREPARED from the leader, so all the replicas return the stale data.

Fix:

  • dtx_resync: do not skip the entry with the same version as resync version if its epoch is older than the engine start epoch;
  • vos_dtx_check_availability: for stand-alone read on the leader, if the non-committed DTX version is newer than the container's resync version (resync not yet done), return -DER_INPROGRESS to make the client retry instead of ignoring it.

Verified by daos_test DTX43:
daos_test -n <daos_control.yml> -T -s 3 -u 43

Steps for the author:

  • Commit message follows the guidelines.
  • Appropriate Features or Test-tag pragmas were used.
  • Appropriate Functional Test Stages were run.
  • At least two positive code reviews including at least one code owner from each category referenced in the PR.
  • Testing is complete. If necessary, forced-landing label added and a reason added in a comment.

After all prior steps are complete:

  • Gatekeeper requested (daos-gatekeeper added as a reviewer).

If the DTX leader engine is killed and restarted quickly without pool
map change, the DTX entries that have been replied to the client as
committable (only in leader's DRAM CoS cache) but not yet batched
committed are never committed:

- the DTX resync triggered by pool map update on the restarted engine
  skips the entries whose version equals the resync version (to avoid
  racing with in-flight IO handlers), but there is no such handler for
  the entries generated before the engine start;
- the stand-alone read on the leader ignores the non-committed leader
  DTX, and DTX refresh from non-leader gets PREPARED from the leader,
  so all the replicas return the stale data.

Fix:
- dtx_resync: do not skip the entry with the same version as resync
  version if its epoch is older than the engine start epoch;
- vos_dtx_check_availability: for stand-alone read on the leader, if
  the non-committed DTX version is newer than the container's resync
  version (resync not yet done), return -DER_INPROGRESS to make the
  client retry instead of ignoring it.

Verified by daos_test DTX43:
  daos_test -n <daos_control.yml> -T -s 3 -u 43

Signed-off-by: Xuezhao Liu <xuezhao.liu@hpe.com>
@liuxuezhao
liuxuezhao requested review from a team as code owners October 23, 2026 17:17
Add daos_test DTX43 to reproduce data loss when the DTX leader engine
is killed and restarted quickly without any pool map change:

- disable batched commit on the leader (DAOS_DTX_NO_BATCHED_CMT), so
  the replied updates are only PREPARED on all replicas and their
  committable status exists only in the leader's DRAM CoS cache;
- kill the leader with "dmg system stop --force" and restart it with
  "dmg system start" before it is excluded (pool self_heal=rebuild);
- the pool map version stays unchanged, the restarted leader skips
  those DTX entries in resync (same version as resync version), so
  the subsequent reads (from any replica) return the stale values.

The test also covers the case that a non-leader replica is restarted
quickly while the DTXs are only committable in the leader's CoS cache,
the reads from the restarted replica must get the new values via DTX
refresh with the leader.

Also add the dmg_system_query_rank_state() helper to wait for the
rank state via "dmg system query".

Run only this test with:
  daos_test -n <daos_control.yml> -T -s 3 -u 43

Signed-off-by: Xuezhao Liu <xuezhao.liu@hpe.com>
@github-actions

Copy link
Copy Markdown

Ticket title is 'DTX: data loss when leader engine restarts quickly without pool map change '
Status is 'Open'
https://daosio.atlassian.net/browse/DAOS-19820

@liuxuezhao
liuxuezhao requested a review from a team as a code owner October 23, 2026 17:17

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

1 participant