Skip to content

Conversation

@pull
Copy link

@pull pull bot commented Dec 10, 2021

See Commits and Changes for more details.


Created by pull[bot]

Can you help keep this open source service alive? 💖 Please sponsor : )

ankit-sam and others added 27 commits March 6, 2025 13:58
Ensure that we convert verify_write_sequence option for client/server.

Fixes: 2dd80ee ("fio: Support verify_write_sequence")

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Change the behavior for verify_only mode to not disable
verify_write_sequence unless its explicitly enabled.

Update the fio doc. accordingly.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Add a new option to disable the verify header seed check. The header
seed check is enabled by default.
There have been numerous issues observed with header seed mismatch. Hence
this allows end user to disable this check, and proceed with the checksum
verification. This is similar to option verify_write_sequence, which
allows the capability to disable write sequence number check.

Update the documentation accordingly.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
The existing header seed is overwritten if zone reset frequency is set or
if verify backlog is enabled. Disable verify header seed check for these
scenarios, unless there is an explicit request to enable it.

Note: There is no fio behavior change intended by this patch.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
There are 3 modes where verify can be performed. write, read and
readwrite. The existing readwrite condition prohibits header seed check
for write or read workloads. For write workloads, there shouldn't be any
extra limitation that triggers header seed mismatch which cannot be
triggered with readwrite workloads. Hence modify this condition to only
disable verify header seed checks for read workload.

The subsequent patches fixes header seed mismatch issues.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
For the invoked verify_only job, header seed can match only if it
exactly matches the original write job. This means either randrepeat
should be true, or we must use the same randseed which was used with the
original write job. After write the verify_only workload shouldn't be
changed from sequential to random or vice versa.

Considering these constraints disable verify_header_seed for verify_only
jobs. Users will still be able to enable header seed checking if they
explicitly set the verify_header_sequence option.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
For read jobs, users should have the option to verify header seeds at a
later point of time. Currently for read jobs header seeds are not
generated

Consider the below mentioned write followed by read workloads. Here fio
should allow header seed verification.

fio --name=test --filesize=16k --rw=randwrite --verify=md5
fio --name=test --filesize=16k --rw=randread --verify=md5 --verify_header_seed=1

However there are other scenarios where header seed verification will
fail. These include:
 * randrepeat is set to false, leading to different seed across runs.
 * randseed is different across write and read workloads.
 * Read workload is changed from sequential to random or vice versa
   across runs.
 * Read workloads run in the same invocation as write, i.e. a write job
   followed by a stonewall read job. Header seed verification will fail
   because random seeds vary between jobs. Refer t/jobs/t0029.fio

If verify_header_seed is explicitly enabled, fio will verify header seed
for the workload.

This reverts part of commit mentioned below
Fixes: def41e5 ("verify: decouple seed generation from buffer fill")

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
When norandommap is enabled, fio logs the I/O entries in a RB tree. This
is to account for offset overlaps and overwrites. Then during verify
phase, the I/O entries are picked from the top and in this case the
smallest offset is verified first and so on. This creates a mismatch
during the header verification as the seed generated at the time of read
differs from what was logged during write. Skip seed verification in
this scenario.

fixes #1756

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
With norandommap for async I/O engines specifying I/O depth > 1, it is
possible that two or more writes with the same offset are queued at once.
When fio tries to verify the block, it may find a numberio mismatch
because the writes did not land on the media in the order that they were
queued. Avoid these spurious failures by disabling sequence number
checking. Users will still be able to enable sequence number checking
if they explicitly set the verify_header_sequence option.

fio -name=verify -ioengine=libaio -rw=randwrite -verify=sha512 -direct=1 \
-iodepth=32 -filesize=16M -bs=512 -norandommap=1 -debug=io,verify

Below is the truncated log for the above command demonstrating the issue.
This includes extra log entries when write sequence number is saved and
retrieved.

set: io_u->numberio=28489, off=0x5f2400
queue: io_u 0x5b8039e30d40: off=0x5f2400,len=0x200,ddir=1,file=verify.0.0
set: io_u->numberio=28574, off=0x5f2400
iolog: overlap 6235136/512, 6235136/512
queue: io_u 0x5b8039e75500: off=0x5f2400,len=0x200,ddir=1,file=verify.0.0
complete: io_u 0x5b8039e75500: off=0x5f2400,len=0x200,ddir=1,file=verify.0.0
complete: io_u 0x5b8039e30d40: off=0x5f2400,len=0x200,ddir=1,file=verify.0.0

retrieve: io_u->numberio=28574, off=0x5f2400
queue: io_u 0x5b8039e1db40: off=0x5f2400,len=0x200,ddir=0,file=verify.0.0

bad header numberio 28489, wanted 28574 at file verify.0.0 offset 6235136, length 512 (requested block: offset=6235136, length=512)

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
In readwrite mode if specified io_size > size, offsets can overlap.
This will result in verify errors. Add check to handle this case.

Fixes: d782b76 ("Don break too early in readwrite mode")

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Verify offset should swap verification header within the verify interval.
If this is not the case return error. Update the doc. accordingly.

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Offset modifiers such as rw=readwrite:8 or rw=write:4K can create
overlaps. For these cases use RB tree instead of list to log the I/O
entries.

Add a helper function fio_offset_overlap_risk() to decide whether to log
the I/O entry in an RB tree or a list.

Disable header seed verification if there are offset modifiers, unless
its explicitly enabled.

fixes #1503

Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Currently we are using a list to log I/O history if:
 * randommap is enabled and fio manages to allocate memory for it.
 * there are no offset modfiers with any jobs.
For any different scenario we use an RB tree to handle offset overlaps,
which disables header seed checks for them.

This commit expands fio_offset_overlap_risk() such that it covers
file_randommap() cases.
For random workload with this change these are the possible scenarios

 -----------------------------------------------------------------------
|                 |         norandommap=0              |  norandommap=1 |
|-----------------------------------------------------------------------|
| softrandommap=0 |        list (No change)            |    RB tree     |
|                 | (fio was able to allocate memory)  |  (No change)   |
|-----------------|------------------------------------|----------------|
|                 |      RB tree (Now always)          |    RB tree     |
| softrandommap=1 |Even if fio was able to allocate mem|  (No Change)   |
 -----------------------------------------------------------------------

With randommap enabled and softrandommap=1 we now always use an RB tree,
even when fio is able to allocate memory for random map. In this case
verify header seed check will be disabled. If users want to check header
seed they can either disable softrandommap or explicilty enable
verify_header_seed.

Effectively this changes randommap from being a per-file property to
per-job property.

This also fixes rand seed mismatch isues, that have been observed when
multiple files are used, such as for the below mentioned configuration.

[global]
do_verify=1
verify=md5
direct=1
[multi_file]
rw=readwrite
directory=.
nrfiles=2
size=32K

Here is the truncated log with debug=verify flag, and an extra log when
the seed gets generated as well as the mismatch.

verify   368109 file ./multi_file.0.1 seed 46386204153304124 offset=0, length=4096
verify   368109 file ./multi_file.0.0 seed 9852480210356360750 offset=0, length=4096
verify   368109 file ./multi_file.0.1 seed 4726550845720924880 offset=4096, length=4096
verify: bad header rand_seed 9852480210356360750, wanted 46386204153304124 at file ./multi_file.0.0 offset 0, length 4096 (requested block: offset=0, length=4096)

Earlier the I/O entries were getting logged in an RB tree, as we were
relying on file_randommap(), which was false for sequential workloads.
In RB tree, files are prioritized first and then the offset. Thus during
the verify phase the I/O entries are removed from tree in order of file
and then offset which is not how it was originally written. With the new
checks, for sequential workload we now store the entries in the list
instead of RB tree.
Even for sequential workload if the user fortuitously specified
norandommap or softrandommap, then I/Os will be stored in an RB tree.
However in this case header seed checks will be disabled.

fixes #740
fixes #746
fixes #844
fixes #1538

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
Enable Requirements checking for test suites that do not have an
nvmecdev argument. macOS does not support NUMA placement so we need to
skip some tests on that platform when the test suite does not have an
nvmecdev argument. This will be used in an upcoming patch for a set of
verify tests.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Sometimes error/informational messages appear at the end of the JSON
data. Try to parse as JSON only the text between the first { and the
last }.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
The script contains three sets of tests. The first set of tests
exercises fio's decision making about checking the verify header's
sequence number and random seed. The second set of tests is aimed at
making sure that the checksum functions can detect data mismatches. The
final set of tests exercise fio's verify-related options such as
verify_backlog and verify_inteval.

This test script includes two checksum lists. The first list (default)
contains a subset of the checksum methods offered by fio, whereas the
second list contains the full set of checksum methods. The second, full
set can be run by specifying -c or --complete. Testing all of the
checksum methods can take a long time.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Signed-off-by: Ankit Kumar <ankit.kumar@samsung.com>
On Windows the verify test script runs for longer than 10 minutes. Add a
success pattern that accommodates this test.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Add the verify test script to our test runner.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
dfs engine mistakenly used a symbol named 'dfs' to call
dlsym(dlhandle, engine_lib), this symbol points a global
variable in dfs.c file. I change this variable name to
'daosfs' to point to 'ioengine' symbol correctly.

Fixes: #1874
Signed-off-by: fugen <fugen@cstor.cn>
…roact-de/fio

* 'iouring-spellingfix-2025-03-18' of https://github.com/proact-de/fio:
  Fix spelling error in IO uring engine.
The image used by GitHub-hosted runners changed the default kvm device
permissions recently rendering us no longer able to start guest VMs. The
error message:

Could not access KVM kernel module: Permission denied
qemu-system-x86_64: failed to initialize kvm: Permission denied

Working run: https://github.com/fiotestbot/fio/actions/runs/14186873066
Failed run: https://github.com/fiotestbot/fio/actions/runs/14211189491

Explicitly give the GitHub Actions runner user permission to access the
/dev/kvm device following the guide at

https://github.blog/changelog/2024-04-02-github-actions-hardware-accelerated-android-virtualization-now-available/

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Fio has the ability to verify trim operations by running a verify
workload and setting the trim_percentage, trim_backlog, and
trim_verify_zero options. Some of the written blocks will then be
trimmed and then read back to see if they are zeroed out.

This patch changes fio_ro_check to allow trim operations when fio is
running a verify/trim workload.

Fixes: 196ccc4 ("fio.h: also check trim operations in fio_ro_check")
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
The trim bit in td_ddir is not set when trim_percentage/backlog is
enabled yet fio still issues trim operations. Detect these cases and
produce output describing trim operations if we issued any.

This is similar to the fix (615c794)
committed for verify_backlog.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
vincentkfu and others added 30 commits November 24, 2025 17:01
When fio has issued 884 billion IOs it is still aable to recover per
second latencies with less than 0.1% error using a latency value of
13ms. This is evidence that fio's strategy for estimating per second
latency for steady state detection works reasonably well.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
When rate limiting is enabled, do_io() calls usec_for_io() to calculate
delays.

If the current operation is a sync (DDIR_SYNC), using it as an index into
arrays sized DDIR_RWDIR_CNT (such as td->rate_bps) results in an
out-of-bounds access.

Guard the rate limiting check in do_io() with ddir_rw() to ensure it only
applies to READ, WRITE, and TRIM operations.

This fixes a UBSAN out-of-bounds error reported in usec_for_io().

Signed-off-by: Florian Mayer <fmayer@google.com>
* 'patch-1' of https://github.com/fmayer/fio:
  backend: fix OOB access in usec_for_io() with DDIR_SYNC
This commit fixes the build on musl which fails with the following
error:
```
oslib/linux-blkzoned.c: In function 'blkzoned_move_zone_wp':
oslib/linux-blkzoned.c:389:37: error: 'FALLOC_FL_ZERO_RANGE' undeclared (first use in this function)
  389 |                 ret = fallocate(fd, FALLOC_FL_ZERO_RANGE, z->wp, length);
      |                                     ^~~~~~~~~~~~~~~~~~~~
oslib/linux-blkzoned.c:389:37: note: each undeclared identifier is reported only once for each function it appears in
make: *** [Makefile:501: oslib/linux-blkzoned.o] Error 1
make: *** Waiting for unfinished jobs....
```

Signed-off-by: Arthur Gautier <arthur.gautier@arista.com>
If fio is run with md_per_io_size but no pi_chk argument,
fio_ioring_io_u_init() passes NULL to strstr(), which segfaults. Use the
struct ioring_options prchk flags instead, which have already been
parsed from pi_chk in parse_prchk_flags().

Signed-off-by: Caleb Sander Mateos <csander@purestorage.com>
* 'fix/prchk-segfault' of https://github.com/calebsander/fio:
  io_uring: don't segfault if pi_chk isn't specified
…m/mcgrof/fio

* '20251023-steady-state-add-latency' of https://github.com/mcgrof/fio:
  mock-tests: assess per second latency recovery
  fio: add mock test framework for isolated unit testing
  fio: add latency steady state detection
  fio: refactor duplicate code in steadystate_*_mean functions
  fio: refactor steady state validation check
  configure: conditionally add gnutls for libnfs >= 6.0.0
For the JSON output latency measurements make the units explicit by
changing the name of the array to lat_ns.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
We have been running out of storage on GitHub-hosted runners in our
automated tests. Add a 'cleanup' option to delete artifacts of
successful tests as we are running.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
We have been running out of storage space on our GitHub-host runners for
our automated tests. Enable the option to delete artifacts for
successful tests as we are running.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Since `td->client_type` is always non-zero (CLI is 1, GUI is 2), the check
`if (td->client_type)` in `init.c` always triggers, causing --write_hist_log
to be unusable when ZLIB is not configured for standalone runs.
By checking if the fio instance `is_backend`, ZLIB availability will be
checked for fio running as server in server/client mode, and the check
will be passed for fio running in standalone mode.
* 'master' of https://github.com/alex310110/fio:
  write_hist_log: do not require ZLIB for non-server instances
Rename in_ramp_time() and ramp_time_over() to in_ramp_period() and
ramp_period_over() respectively. We will be adding other not time-based
methods for determining whether the load is ramping up so the old names
would be confusing.

Reviewed-by: Damien Le Moal <dlemoal@kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Link: https://lore.kernel.org/r/20251219134247.14195-1-jack@suse.cz
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Instead of checking whether ramp_time is specified each time we need to
check whether we are in the ramp period, initialize ramp_period_over
based on the ramp_time option. This will simplify things more
significantly later when ramp up period can be defined in a different
way.

Reviewed-by: Damien Le Moal <dlemoal@kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Link: https://lore.kernel.org/r/20251219134247.14195-2-jack@suse.cz
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Reviewed-by: Damien Le Moal <dlemoal@kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Link: https://lore.kernel.org/r/20251219134247.14195-3-jack@suse.cz
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Instead of evaluating whether ramp up period has finished on each IO
submission and completion evaluate it once per second and set
appropriate state variable in thread_data. Later when ramp up period end
condition will be more complex and would involve stat data from all
threads, it would unnecessarily slow down IO.

Reviewed-by: Damien Le Moal <dlemoal@kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Link: https://lore.kernel.org/r/20251219134247.14195-4-jack@suse.cz
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
In some cases the ramp up period is not easy to define by amount of
time. This is for example a case of buffered writes measurement where we
want to start measuring only once dirty throttling kicks in. The time
until dirty throttling kicks in depends on dirty limit (easy to figure
out) and speed of writes to the page cache (difficult to know in
advance). Add option ramp_size which determines the ramp up period by
the amount of IO written (either by each job or by each group when group
reporting is enabled).

Reviewed-by: Damien Le Moal <dlemoal@kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Link: https://lore.kernel.org/r/20251219134247.14195-5-jack@suse.cz
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Only meant for testing overhead of enabling restrictions, not anything
people should generally use. Defaults to off.

Signed-off-by: Jens Axboe <axboe@kernel.dk>
Int32x32To64 macro internally truncates the arguments to int32,
while time_t is 64-bit on most/all modern platforms.
Therefore, usage of this macro creates a Year 2038 bug.

Signed-off-by: Adrian Zdanowicz <zdanio95@gmail.com>
* 'patch-1' of https://github.com/CookiePLMonster/fio:
  windows: fix Y2038 bug caused by 32 bit truncation
* 'sync-fileop' of https://github.com/struschev/fio:
  fio: add sync capability for file operations
There is no need for a 64-bit random generator for fdp_state. The FDP
random generator is only used to randomly select from available
placement IDs. For NVMe FDP devices the placement ID is a 16-bit value.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
The trim_state random generator determines whether to trim an offset or
not with the given probability specified by the trim_percentage option.
There is no need for it to ever be 64 bits. So make it always 32 bits.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
random_state is a random generator that generates the random offsets to
use for I/O operations. Change its name to offset_state to make this
more obvious.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Clarify that this is the state used for generating random offsets. The
bitmap reference must be a holdover from old code.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
If the combination of file size and minimum block size exceeds the
limits of the default tausworthe random generator, switch for real to
the tausworthe64 random generator.

The original code changed the random_generator option to tausworthe64
but by the time the change was made the random generators had already
been initialized. So the original code had no effect on the offsets
generated. This patch re-initializes the relevant random generator after
the switch to tausworthe64 so that this change can actually take effect.

The random generators are initialized as Fio parses the command line and
job files. Later on thread_main() calls init_random_map() which calls
check_rand_gen_limits() which actually carries out the random generator
limits check for each file.

Fixes: #2036
Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
There are no problems when output is directed to the console, but when
--output=somefile is set, child process log messages may not make it to
the file since buffers are not flushed when the child process
terminates. Make sure child process messages appear in the output by
flushing the buffer before exiting.

Also try to make sure the child process starts with an emtpy info log
buffer.

Example: tausworthe64 message does not appear without this patch
----------------------------------------------------------------
root@localhost:~# ./fio-canonical/fio --output=test --name=test --rw=randread --filesize=128T --number_ios=1 --ioengine=null
root@localhost:~# cat test
test: (g=0): rw=randread, bs=(R) 4096B-4096B, (W) 4096B-4096B, (T) 4096B-4096B, ioengine=null, iodepth=1
fio-3.41-77-gadec
Starting 1 process

test: (groupid=0, jobs=1): err= 0: pid=206045: Thu Jan 15 15:46:43 2026
  read: IOPS=1, BW=6860B/s (6860B/s)(4096B/597msec)
...

Example: with this patch tausworthe64 message appears
-----------------------------------------------------
root@localhost:~# ./fio --output=test --name=test --rw=randread --filesize=128T --number_ios=1 --ioengine=null
root@localhost:~# cat test
test: (g=0): rw=randread, bs=(R) 4096B-4096B, (W) 4096B-4096B, (T) 4096B-4096B, ioengine=null, iodepth=1
fio-3.41-82-g7a1b-dirty
Starting 1 process
fio: file test.0.0 exceeds 32-bit tausworthe random generator.
fio: Switching to tausworthe64. Use the random_generator= option to get rid of this warning.

test: (groupid=0, jobs=1): err= 0: pid=206135: Thu Jan 15 15:53:14 2026
  read: IOPS=1, BW=6781B/s (6781B/s)(4096B/604msec)
...

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Move random seed debug prints immediately after they are set. This makes
clearer that the subsequent call to td_fill_rand_seeds does not affect
these random seeds.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Add a test script to confirm that we successfully switch to the
tausworthe64 random generator when the combination of minimum block size
and file size exceeds the limits of the default tausworthe32 random
generator.

Detect a succesful switch by seeing how many duplicate offsets are
generated.

Also add this script to our automated test harness.

To run on Windows there will need to be some changes to the test runner.

Signed-off-by: Vincent Fu <vincent.fu@samsung.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.