hubcio opened a new pull request, #3970:
URL: https://github.com/apache/iggy/pull/3970

   Every journal flush issued two serialized fdatasyncs, log then index,
   so an fsync-gated topic paid two device round trips per ack. Both
   files now persist under one futures::future::join: 13.4k -> 26.1k
   msg/s and p50 5.83 -> 3.01 ms on ext4 with enforce_fsync and
   messages_required_to_save = 1, 8 producers into one partition. The
   cursors advance only after both saves succeed, so a failed half keeps
   its slot and the retry overwrites it; MessagesWriter::rewind lost its
   last caller and is gone.
   
   Recovery had to change first. The old order was a barrier only under
   enforce_fsync = true: with the shipped default the page cache already
   wrote the two inodes back in any order, and recovery's own pass C
   truncates the log before the index, so an index holding entries the
   log does not back was already ordinary. Boot refused it as
   IndexLogDivergence, and on a single-replica node that refusal was a
   permanent tombstone for a partition whose log was healthy.
   
   An index entry is derived from the log, so it is never evidence the
   log lacks. Recovery now steps back to the highest entry the log
   proves and floors the index there; when no entry proves, or the
   entries contradict each other (out of order, or below the segment
   start), it drops the index and rebuilds from the log. Nothing a
   client was promised is lost, since no ack precedes persist, and the
   walk still runs its residue probe, so a survivor past damage refuses
   as before. That walk now checksums every batch it accepts, because
   unordered files mean a durable index entry no longer implies a
   durable chunk and one chunk can hold several batches. The step-back
   is async, yields on refills and charges the shared probe budget, so a
   crafted tail refuses as UnverifiedResidue instead of stalling boot;
   FileScanner::slice_at anchors its backward moves to keep refills
   linear.
   
   An integration test covers the shape: a three-node cluster, one node
   SIGKILLed after an eager flush, its log cut behind the last index
   entry, then restarted. It asserts the floor marker in that node's
   stdout, the exact floored index length while the log is still exactly
   the cut length, the surviving prefix served and the node caught up.
   It is red before the recovery change and green with it.
   
   Measuring this needed three benchmark fixes. Reports took min, max
   and std_dev from the per-bucket moving average series, which averages
   the extremes away while the percentiles beside them used the raw
   samples; all three now come from those same sorted samples. The
   balanced-producer kind refused fewer than two partitions, but one is
   a legal target and the shape a durability benchmark needs. And
   --enforce-fsync claimed to fsync every write while the topic's flush
   threshold (server default 1024) still governed when the journal
   reached disk, so acks were not durability-gated unless it was also 1;
   that threshold is now exposed as --messages-required-to-save, plumbed
   into topic creation, named in the fsync help and shown in an example.
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to