diff options
author | Zach Brown <zach.brown@oracle.com> | 2010-07-07 00:09:56 +0200 |
---|---|---|
committer | Andy Grover <andy.grover@oracle.com> | 2010-09-09 03:16:34 +0200 |
commit | 515e079dab19cf774d1eec6e5f4ed65509e31ef1 (patch) | |
tree | 1dcc0f211946c47cd19b6823574aaa1a32982ffa /net/rds/ib_rdma.c | |
parent | RDS/IB: destroy connections on rmmod (diff) | |
download | linux-515e079dab19cf774d1eec6e5f4ed65509e31ef1.tar.xz linux-515e079dab19cf774d1eec6e5f4ed65509e31ef1.zip |
RDS/IB: create a work queue for FMR flushing
This patch moves the FMR flushing work in to its own mult-threaded work queue.
This is to maintain performance in preparation for returning the main krdsd
work queue back to a single threaded work queue to avoid deep-rooted
concurrency bugs.
This is also good because it further separates FMRs, which might be removed
some day, from the rest of the code base.
Signed-off-by: Zach Brown <zach.brown@oracle.com>
Diffstat (limited to 'net/rds/ib_rdma.c')
-rw-r--r-- | net/rds/ib_rdma.c | 25 |
1 files changed, 23 insertions, 2 deletions
diff --git a/net/rds/ib_rdma.c b/net/rds/ib_rdma.c index 00f3995351c8..0eb597670c5b 100644 --- a/net/rds/ib_rdma.c +++ b/net/rds/ib_rdma.c @@ -691,6 +691,26 @@ out_nolock: return ret; } +struct workqueue_struct *rds_ib_fmr_wq; + +int __init rds_ib_fmr_init(void) +{ + rds_ib_fmr_wq = create_workqueue("rds_fmr_flushd"); + if (!rds_ib_fmr_wq) + return -ENOMEM; + return 0; +} + +/* + * By the time this is called all the IB devices should have been torn down and + * had their pools freed. As each pool is freed its work struct is waited on, + * so the pool flushing work queue should be idle by the time we get here. + */ +void __exit rds_ib_fmr_exit(void) +{ + destroy_workqueue(rds_ib_fmr_wq); +} + static void rds_ib_mr_pool_flush_worker(struct work_struct *work) { struct rds_ib_mr_pool *pool = container_of(work, struct rds_ib_mr_pool, flush_worker.work); @@ -718,7 +738,7 @@ void rds_ib_free_mr(void *trans_private, int invalidate) /* If we've pinned too many pages, request a flush */ if (atomic_read(&pool->free_pinned) >= pool->max_free_pinned || atomic_read(&pool->dirty_count) >= pool->max_items / 10) - queue_delayed_work(rds_wq, &pool->flush_worker, 10); + queue_delayed_work(rds_ib_fmr_wq, &pool->flush_worker, 10); if (invalidate) { if (likely(!in_interrupt())) { @@ -726,7 +746,8 @@ void rds_ib_free_mr(void *trans_private, int invalidate) } else { /* We get here if the user created a MR marked * as use_once and invalidate at the same time. */ - queue_delayed_work(rds_wq, &pool->flush_worker, 10); + queue_delayed_work(rds_ib_fmr_wq, + &pool->flush_worker, 10); } } |