From aa9af22cdf8d16c197974c3a478d2053b3bed498 Mon Sep 17 00:00:00 2001 From: Brian Behlendorf Date: Wed, 3 Jun 2015 11:43:30 -0700 Subject: [PATCH] Update all default taskq settings Over the years the default values for the taskqs used on Linux have differed slightly from illumos. In the vast majority of cases this was done to avoid creating an obnoxious number of idle threads which would pollute the process listing. With the addition of support for dynamic taskqs all multi-threaded queues should be created as dynamic taskqs. This allows us to get the best of both worlds. * The illumos default values for the I/O pipeline can be restored. These values are known to work well for most workloads. The only exception is the zio write interrupt taskq which is changed to ZTI_P(12, 8). At least under Linux more threads has been shown to improve performance, see commit 7e55f4e. * Reduces the number of idle threads on the system when it's not under heavy load. The maximum number of threads will only be created when they are required. * Remove the vdev_file_taskq and rely on the system_taskq instead which is now dynamic and may have up to 64-threads. Again this brings us back inline with upstream. * Tasks dispatched with taskq_dispatch_ent() are allowed to use dynamic taskqs. The Linux taskq implementation supports this. Signed-off-by: Brian Behlendorf Signed-off-by: Tim Chase Closes #3507 --- include/sys/vdev_file.h | 5 ----- lib/libzpool/taskq.c | 1 - module/zfs/arc.c | 2 +- module/zfs/dsl_pool.c | 2 +- module/zfs/metaslab.c | 2 +- module/zfs/spa.c | 8 ++++---- module/zfs/spa_misc.c | 2 -- module/zfs/txg.c | 4 ++-- module/zfs/vdev_file.c | 21 ++------------------- module/zfs/zvol.c | 2 +- 10 files changed, 12 insertions(+), 37 deletions(-) diff --git a/include/sys/vdev_file.h b/include/sys/vdev_file.h index cf38a86afe..aebcf55cfd 100644 --- a/include/sys/vdev_file.h +++ b/include/sys/vdev_file.h @@ -27,8 +27,6 @@ #ifndef _SYS_VDEV_FILE_H #define _SYS_VDEV_FILE_H - - #include #ifdef __cplusplus @@ -39,9 +37,6 @@ typedef struct vdev_file { vnode_t *vf_vnode; } vdev_file_t; -extern void vdev_file_init(void); -extern void vdev_file_fini(void); - #ifdef __cplusplus } #endif diff --git a/lib/libzpool/taskq.c b/lib/libzpool/taskq.c index c6fa2fff72..59b4c7c05f 100644 --- a/lib/libzpool/taskq.c +++ b/lib/libzpool/taskq.c @@ -178,7 +178,6 @@ taskq_dispatch_ent(taskq_t *tq, task_func_t func, void *arg, uint_t flags, taskq_ent_t *t) { ASSERT(func != NULL); - ASSERT(!(tq->tq_flags & TASKQ_DYNAMIC)); /* * Mark it as a prealloc'd task. This is important diff --git a/module/zfs/arc.c b/module/zfs/arc.c index 16d9706729..99fa698722 100644 --- a/module/zfs/arc.c +++ b/module/zfs/arc.c @@ -5002,7 +5002,7 @@ arc_init(void) bzero(&arc_eviction_hdr, sizeof (arc_buf_hdr_t)); arc_prune_taskq = taskq_create("arc_prune", max_ncpus, minclsyspri, - max_ncpus, INT_MAX, TASKQ_PREPOPULATE); + max_ncpus, INT_MAX, TASKQ_PREPOPULATE | TASKQ_DYNAMIC); arc_ksp = kstat_create("zfs", 0, "arcstats", "misc", KSTAT_TYPE_NAMED, sizeof (arc_stats) / sizeof (kstat_named_t), KSTAT_FLAG_VIRTUAL); diff --git a/module/zfs/dsl_pool.c b/module/zfs/dsl_pool.c index 908c44e702..5d804352dd 100644 --- a/module/zfs/dsl_pool.c +++ b/module/zfs/dsl_pool.c @@ -171,7 +171,7 @@ dsl_pool_open_impl(spa_t *spa, uint64_t txg) cv_init(&dp->dp_spaceavail_cv, NULL, CV_DEFAULT, NULL); dp->dp_iput_taskq = taskq_create("z_iput", max_ncpus, minclsyspri, - max_ncpus * 8, INT_MAX, TASKQ_PREPOPULATE); + max_ncpus * 8, INT_MAX, TASKQ_PREPOPULATE | TASKQ_DYNAMIC); return (dp); } diff --git a/module/zfs/metaslab.c b/module/zfs/metaslab.c index 3b556b6dbf..d6ee81c859 100644 --- a/module/zfs/metaslab.c +++ b/module/zfs/metaslab.c @@ -492,7 +492,7 @@ metaslab_group_create(metaslab_class_t *mc, vdev_t *vd) mg->mg_activation_count = 0; mg->mg_taskq = taskq_create("metaslab_group_taskq", metaslab_load_pct, - minclsyspri, 10, INT_MAX, TASKQ_THREADS_CPU_PCT); + minclsyspri, 10, INT_MAX, TASKQ_THREADS_CPU_PCT | TASKQ_DYNAMIC); return (mg); } diff --git a/module/zfs/spa.c b/module/zfs/spa.c index ad109a641c..b5e024c3f2 100644 --- a/module/zfs/spa.c +++ b/module/zfs/spa.c @@ -127,9 +127,9 @@ static const char *const zio_taskq_types[ZIO_TASKQ_TYPES] = { const zio_taskq_info_t zio_taskqs[ZIO_TYPES][ZIO_TASKQ_TYPES] = { /* ISSUE ISSUE_HIGH INTR INTR_HIGH */ { ZTI_ONE, ZTI_NULL, ZTI_ONE, ZTI_NULL }, /* NULL */ - { ZTI_N(8), ZTI_NULL, ZTI_BATCH, ZTI_NULL }, /* READ */ - { ZTI_BATCH, ZTI_N(5), ZTI_N(16), ZTI_N(5) }, /* WRITE */ - { ZTI_P(4, 8), ZTI_NULL, ZTI_ONE, ZTI_NULL }, /* FREE */ + { ZTI_N(8), ZTI_NULL, ZTI_P(12, 8), ZTI_NULL }, /* READ */ + { ZTI_BATCH, ZTI_N(5), ZTI_P(12, 8), ZTI_N(5) }, /* WRITE */ + { ZTI_P(12, 8), ZTI_NULL, ZTI_ONE, ZTI_NULL }, /* FREE */ { ZTI_ONE, ZTI_NULL, ZTI_ONE, ZTI_NULL }, /* CLAIM */ { ZTI_ONE, ZTI_NULL, ZTI_ONE, ZTI_NULL }, /* IOCTL */ }; @@ -844,7 +844,7 @@ spa_taskqs_init(spa_t *spa, zio_type_t t, zio_taskq_type_t q) uint_t count = ztip->zti_count; spa_taskqs_t *tqs = &spa->spa_zio_taskq[t][q]; char name[32]; - uint_t i, flags = 0; + uint_t i, flags = TASKQ_DYNAMIC; boolean_t batch = B_FALSE; if (mode == ZTI_MODE_NULL) { diff --git a/module/zfs/spa_misc.c b/module/zfs/spa_misc.c index 26b6f1731a..ad9f9fe283 100644 --- a/module/zfs/spa_misc.c +++ b/module/zfs/spa_misc.c @@ -1829,7 +1829,6 @@ spa_init(int mode) dmu_init(); zil_init(); vdev_cache_stat_init(); - vdev_file_init(); zfs_prop_init(); zpool_prop_init(); zpool_feature_init(); @@ -1844,7 +1843,6 @@ spa_fini(void) spa_evict_all(); - vdev_file_fini(); vdev_cache_stat_fini(); zil_fini(); dmu_fini(); diff --git a/module/zfs/txg.c b/module/zfs/txg.c index 9accd48df0..7681856ea1 100644 --- a/module/zfs/txg.c +++ b/module/zfs/txg.c @@ -445,8 +445,8 @@ txg_dispatch_callbacks(dsl_pool_t *dp, uint64_t txg) * Commit callback taskq hasn't been created yet. */ tx->tx_commit_cb_taskq = taskq_create("tx_commit_cb", - 100, minclsyspri, max_ncpus, INT_MAX, - TASKQ_THREADS_CPU_PCT | TASKQ_PREPOPULATE); + max_ncpus, minclsyspri, max_ncpus, max_ncpus * 2, + TASKQ_PREPOPULATE | TASKQ_DYNAMIC); } cb_list = kmem_alloc(sizeof (list_t), KM_SLEEP); diff --git a/module/zfs/vdev_file.c b/module/zfs/vdev_file.c index 3c3a139931..e61240fdcc 100644 --- a/module/zfs/vdev_file.c +++ b/module/zfs/vdev_file.c @@ -36,8 +36,6 @@ * Virtual device vector for files. */ -static taskq_t *vdev_file_taskq; - static void vdev_file_hold(vdev_t *vd) { @@ -200,7 +198,7 @@ vdev_file_io_start(zio_t *zio) * the sync must be dispatched to a different context. */ if (spl_fstrans_check()) { - VERIFY3U(taskq_dispatch(vdev_file_taskq, + VERIFY3U(taskq_dispatch(system_taskq, vdev_file_io_fsync, zio, TQ_SLEEP), !=, 0); return; } @@ -216,7 +214,7 @@ vdev_file_io_start(zio_t *zio) return; } - VERIFY3U(taskq_dispatch(vdev_file_taskq, vdev_file_io_strategy, zio, + VERIFY3U(taskq_dispatch(system_taskq, vdev_file_io_strategy, zio, TQ_SLEEP), !=, 0); } @@ -239,21 +237,6 @@ vdev_ops_t vdev_file_ops = { B_TRUE /* leaf vdev */ }; -void -vdev_file_init(void) -{ - vdev_file_taskq = taskq_create("vdev_file_taskq", 100, minclsyspri, - max_ncpus, INT_MAX, TASKQ_PREPOPULATE | TASKQ_THREADS_CPU_PCT); - - VERIFY(vdev_file_taskq); -} - -void -vdev_file_fini(void) -{ - taskq_destroy(vdev_file_taskq); -} - /* * From userland we access disks just like files. */ diff --git a/module/zfs/zvol.c b/module/zfs/zvol.c index d180b5b5b7..8646892ea8 100644 --- a/module/zfs/zvol.c +++ b/module/zfs/zvol.c @@ -1632,7 +1632,7 @@ zvol_init(void) mutex_init(&zvol_state_lock, NULL, MUTEX_DEFAULT, NULL); zvol_taskq = taskq_create(ZVOL_DRIVER, zvol_threads, maxclsyspri, - zvol_threads, INT_MAX, TASKQ_PREPOPULATE); + zvol_threads * 2, INT_MAX, TASKQ_PREPOPULATE | TASKQ_DYNAMIC); if (zvol_taskq == NULL) { printk(KERN_INFO "ZFS: taskq_create() failed\n"); error = -ENOMEM;