mirror of
https://git.proxmox.com/git/mirror_zfs.git
synced 2024-12-27 19:39:35 +03:00
Fix lock inversion in txg_sync_thread()
This patch fixes a lock inversion issue in txg_sync_thread() where the code would attempt hold the spa config lock as a reader while holding tx->tx_sync_lock. This races with spa_vdev_remove() which attempts to hold the tx->tx_sync_lock to assign a new tx (via spa_history_log_internal()) while holding the spa config lock as a writer. Reviewed-by: Serapheim Dimitropoulos <serapheim.dimitro@delphix.com> Reviewed-by: Matthew Ahrens <mahrens@delphix.com> Co-authored-by: Brian Behlendorf <behlendorf1@llnl.gov> Signed-off-by: Tom Caputi <tcaputi@datto.com> Closes #8010
This commit is contained in:
parent
ab4c009e3d
commit
a783dd9684
@ -562,22 +562,22 @@ txg_sync_thread(void *arg)
|
|||||||
tx->tx_quiesced_txg = 0;
|
tx->tx_quiesced_txg = 0;
|
||||||
tx->tx_syncing_txg = txg;
|
tx->tx_syncing_txg = txg;
|
||||||
DTRACE_PROBE2(txg__syncing, dsl_pool_t *, dp, uint64_t, txg);
|
DTRACE_PROBE2(txg__syncing, dsl_pool_t *, dp, uint64_t, txg);
|
||||||
txg_stat_t *ts = spa_txg_history_init_io(spa, txg, dp);
|
|
||||||
cv_broadcast(&tx->tx_quiesce_more_cv);
|
cv_broadcast(&tx->tx_quiesce_more_cv);
|
||||||
|
|
||||||
dprintf("txg=%llu quiesce_txg=%llu sync_txg=%llu\n",
|
dprintf("txg=%llu quiesce_txg=%llu sync_txg=%llu\n",
|
||||||
txg, tx->tx_quiesce_txg_waiting, tx->tx_sync_txg_waiting);
|
txg, tx->tx_quiesce_txg_waiting, tx->tx_sync_txg_waiting);
|
||||||
mutex_exit(&tx->tx_sync_lock);
|
mutex_exit(&tx->tx_sync_lock);
|
||||||
|
|
||||||
|
txg_stat_t *ts = spa_txg_history_init_io(spa, txg, dp);
|
||||||
start = ddi_get_lbolt();
|
start = ddi_get_lbolt();
|
||||||
spa_sync(spa, txg);
|
spa_sync(spa, txg);
|
||||||
delta = ddi_get_lbolt() - start;
|
delta = ddi_get_lbolt() - start;
|
||||||
|
spa_txg_history_fini_io(spa, ts);
|
||||||
|
|
||||||
mutex_enter(&tx->tx_sync_lock);
|
mutex_enter(&tx->tx_sync_lock);
|
||||||
tx->tx_synced_txg = txg;
|
tx->tx_synced_txg = txg;
|
||||||
tx->tx_syncing_txg = 0;
|
tx->tx_syncing_txg = 0;
|
||||||
DTRACE_PROBE2(txg__synced, dsl_pool_t *, dp, uint64_t, txg);
|
DTRACE_PROBE2(txg__synced, dsl_pool_t *, dp, uint64_t, txg);
|
||||||
spa_txg_history_fini_io(spa, ts);
|
|
||||||
cv_broadcast(&tx->tx_sync_done_cv);
|
cv_broadcast(&tx->tx_sync_done_cv);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
Loading…
Reference in New Issue
Block a user