diff options
| author | jdolecek <jdolecek@NetBSD.org> | 2020-05-21 09:11:33 +0000 |
|---|---|---|
| committer | jdolecek <jdolecek@NetBSD.org> | 2020-05-21 09:11:33 +0000 |
| commit | ed63c2f301033a27de79e362ddff27aa12c9dce6 (patch) | |
| tree | ce85aad9730d819b5e94eef70409e1a40080a197 /sys/dev/ata | |
| parent | c9ad31de52f07c700434cf3b2f01d03177a95ea6 (diff) | |
stop timeout handler while scheduling another part of partial I/O,
to avoid race between the timeout and I/O submission; the I/O
submission can sleep with xfer while waiting for the controller to
be ready once it gets to thread context, and timeout might cause
the xfer to be freed, leading to crashes due to use-after-free
this fixes another type of crashes with slow devices under QEMU reported
by Paul Ripke - thanks a lot with extensive debugging help
Diffstat (limited to 'sys/dev/ata')
| -rw-r--r-- | sys/dev/ata/ata_wdc.c | 6 |
1 files changed, 4 insertions, 2 deletions
diff --git a/sys/dev/ata/ata_wdc.c b/sys/dev/ata/ata_wdc.c index 29071ac5f9a..5fc018637a4 100644 --- a/sys/dev/ata/ata_wdc.c +++ b/sys/dev/ata/ata_wdc.c @@ -1,4 +1,4 @@ -/* $NetBSD: ata_wdc.c,v 1.117 2020/05/19 08:08:51 jdolecek Exp $ */ +/* $NetBSD: ata_wdc.c,v 1.118 2020/05/21 09:11:33 jdolecek Exp $ */ /* * Copyright (c) 1998, 2001, 2003 Manuel Bouyer. @@ -54,7 +54,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ata_wdc.c,v 1.117 2020/05/19 08:08:51 jdolecek Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ata_wdc.c,v 1.118 2020/05/21 09:11:33 jdolecek Exp $"); #include "opt_ata.h" #include "opt_wdc.h" @@ -769,6 +769,8 @@ end: if (xfer->c_bcount > 0) { if ((ata_bio->flags & ATA_POLL) == 0) { /* Start the next operation */ + KASSERT((chp->ch_flags & ATACH_IRQ_WAIT) == 0); + callout_stop(&chp->c_timo_callout); ata_xfer_start(xfer); } else { /* Let _wdc_ata_bio_start do the loop */ |
