]> git.proxmox.com Git - mirror_zfs.git/blobdiff - module/zfs/txg.c
Code improvement and bug fixes for QAT support
[mirror_zfs.git] / module / zfs / txg.c
index db0f60cd15a344a0f2526918abab2126c35ce3f4..0fcd569e3b4498f7ae2e328af41a50a6a74c166f 100644 (file)
@@ -242,11 +242,17 @@ txg_thread_wait(tx_state_t *tx, callb_cpr_t *cpr, kcondvar_t *cv, clock_t time)
 {
        CALLB_CPR_SAFE_BEGIN(cpr);
 
-       if (time)
+       /*
+        * cv_wait_sig() is used instead of cv_wait() in order to prevent
+        * this process from incorrectly contributing to the system load
+        * average when idle.
+        */
+       if (time) {
                (void) cv_timedwait_sig(cv, &tx->tx_sync_lock,
                    ddi_get_lbolt() + time);
-       else
+       } else {
                cv_wait_sig(cv, &tx->tx_sync_lock);
+       }
 
        CALLB_CPR_SAFE_END(cpr, &tx->tx_sync_lock);
 }
@@ -689,13 +695,17 @@ txg_wait_synced(dsl_pool_t *dp, uint64_t txg)
                    "tx_synced=%llu waiting=%llu dp=%p\n",
                    tx->tx_synced_txg, tx->tx_sync_txg_waiting, dp);
                cv_broadcast(&tx->tx_sync_more_cv);
-               cv_wait(&tx->tx_sync_done_cv, &tx->tx_sync_lock);
+               cv_wait_io(&tx->tx_sync_done_cv, &tx->tx_sync_lock);
        }
        mutex_exit(&tx->tx_sync_lock);
 }
 
+/*
+ * Wait for the specified open transaction group.  Set should_quiesce
+ * when the current open txg should be quiesced immediately.
+ */
 void
-txg_wait_open(dsl_pool_t *dp, uint64_t txg)
+txg_wait_open(dsl_pool_t *dp, uint64_t txg, boolean_t should_quiesce)
 {
        tx_state_t *tx = &dp->dp_tx;
 
@@ -705,13 +715,23 @@ txg_wait_open(dsl_pool_t *dp, uint64_t txg)
        ASSERT3U(tx->tx_threads, ==, 2);
        if (txg == 0)
                txg = tx->tx_open_txg + 1;
-       if (tx->tx_quiesce_txg_waiting < txg)
+       if (tx->tx_quiesce_txg_waiting < txg && should_quiesce)
                tx->tx_quiesce_txg_waiting = txg;
        dprintf("txg=%llu quiesce_txg=%llu sync_txg=%llu\n",
            txg, tx->tx_quiesce_txg_waiting, tx->tx_sync_txg_waiting);
        while (tx->tx_open_txg < txg) {
                cv_broadcast(&tx->tx_quiesce_more_cv);
-               cv_wait(&tx->tx_quiesce_done_cv, &tx->tx_sync_lock);
+               /*
+                * Callers setting should_quiesce will use cv_wait_io() and
+                * be accounted for as iowait time.  Otherwise, the caller is
+                * understood to be idle and cv_wait_sig() is used to prevent
+                * incorrectly inflating the system load average.
+                */
+               if (should_quiesce == B_TRUE) {
+                       cv_wait_io(&tx->tx_quiesce_done_cv, &tx->tx_sync_lock);
+               } else {
+                       cv_wait_sig(&tx->tx_quiesce_done_cv, &tx->tx_sync_lock);
+               }
        }
        mutex_exit(&tx->tx_sync_lock);
 }