Skip to content

Commit

Permalink
zio: Avoid sleeping in the I/O path
Browse files Browse the repository at this point in the history
zio_delay_interrupt(), apparently used for fault injection, is executed
in the I/O pipeline.  It can cause the calling thread to go to sleep,
which is not allowed on FreeBSD.  This happens only for small delays,
though, and there's no apparent reason to avoid deferring to a taskqueue
in that case, as it already does otherwise.

Simply go to sleep unconditionally.  This fixes an occasional panic I
see when running the ZTS on FreeBSD.  Also remove an unhelpful comment
referencing the non-existent timeout_generic().

Reviewed-by: Brian Behlendorf <[email protected]>
Reviewed-by:  Alexander Motin <[email protected]>
Signed-off-by: Mark Johnston <[email protected]>
Closes #16785
  • Loading branch information
markjdb authored Nov 20, 2024
1 parent 457f8b7 commit d76d79f
Showing 1 changed file with 8 additions and 19 deletions.
27 changes: 8 additions & 19 deletions module/zfs/zio.c
Original file line number Diff line number Diff line change
Expand Up @@ -2192,31 +2192,20 @@ zio_delay_interrupt(zio_t *zio)
} else {
taskqid_t tid;
hrtime_t diff = zio->io_target_timestamp - now;
clock_t expire_at_tick = ddi_get_lbolt() +
NSEC_TO_TICK(diff);
int ticks = MAX(1, NSEC_TO_TICK(diff));
clock_t expire_at_tick = ddi_get_lbolt() + ticks;

DTRACE_PROBE3(zio__delay__hit, zio_t *, zio,
hrtime_t, now, hrtime_t, diff);

if (NSEC_TO_TICK(diff) == 0) {
/* Our delay is less than a jiffy - just spin */
zfs_sleep_until(zio->io_target_timestamp);
zio_interrupt(zio);
} else {
tid = taskq_dispatch_delay(system_taskq, zio_interrupt,
zio, TQ_NOSLEEP, expire_at_tick);
if (tid == TASKQID_INVALID) {
/*
* Use taskq_dispatch_delay() in the place of
* OpenZFS's timeout_generic().
* Couldn't allocate a task. Just finish the
* zio without a delay.
*/
tid = taskq_dispatch_delay(system_taskq,
zio_interrupt, zio, TQ_NOSLEEP,
expire_at_tick);
if (tid == TASKQID_INVALID) {
/*
* Couldn't allocate a task. Just
* finish the zio without a delay.
*/
zio_interrupt(zio);
}
zio_interrupt(zio);
}
}
return;
Expand Down

0 comments on commit d76d79f

Please sign in to comment.