Add an exit function for the threadpool which will stop all running threads in 
the
pool. Also clean up the init code a bit.

Signed-off-by: Sasha Levin <levinsasha...@gmail.com>
---
 tools/kvm/builtin-run.c            | 11 ++++++++++-
 tools/kvm/include/kvm/threadpool.h |  3 ++-
 tools/kvm/util/threadpool.c        | 33 +++++++++++++++++++++++++++++----
 3 files changed, 41 insertions(+), 6 deletions(-)

diff --git a/tools/kvm/builtin-run.c b/tools/kvm/builtin-run.c
index b4da06e..d83917f 100644
--- a/tools/kvm/builtin-run.c
+++ b/tools/kvm/builtin-run.c
@@ -1216,7 +1216,12 @@ static int kvm_cmd_run_init(int argc, const char **argv)
                }
        }
 
-       thread_pool__init(nr_online_cpus);
+       r = thread_pool__init(kvm);
+       if (r < 0) {
+               pr_err("thread_pool__init() failed with error %d\n", r);
+               goto fail;
+       }
+
 fail:
        return r;
 }
@@ -1301,6 +1306,10 @@ static void kvm_cmd_run_exit(int guest_ret)
        if (r < 0)
                pr_warning("pci__exit() failed with error %d\n", r);
 
+       r = thread_pool__exit(kvm);
+       if (r < 0)
+               pr_warning("thread_pool__exit() failed with error %d\n", r);
+
        r = kvm__exit(kvm);
        if (r < 0)
                pr_warning("pci__exit() failed with error %d\n", r);
diff --git a/tools/kvm/include/kvm/threadpool.h 
b/tools/kvm/include/kvm/threadpool.h
index 768239f..abe46ea 100644
--- a/tools/kvm/include/kvm/threadpool.h
+++ b/tools/kvm/include/kvm/threadpool.h
@@ -30,7 +30,8 @@ static inline void thread_pool__init_job(struct 
thread_pool__job *job, struct kv
        };
 }
 
-int thread_pool__init(unsigned long thread_count);
+int thread_pool__init(struct kvm *kvm);
+int thread_pool__exit(struct kvm *kvm);
 
 void thread_pool__do_job(struct thread_pool__job *job);
 
diff --git a/tools/kvm/util/threadpool.c b/tools/kvm/util/threadpool.c
index bafbcd7..6c7566d 100644
--- a/tools/kvm/util/threadpool.c
+++ b/tools/kvm/util/threadpool.c
@@ -14,6 +14,7 @@ static LIST_HEAD(head);
 
 static pthread_t       *threads;
 static long            threadcount;
+static bool            running;
 
 static struct thread_pool__job *thread_pool__job_pop_locked(void)
 {
@@ -76,15 +77,16 @@ static void *thread_pool__threadfunc(void *param)
 {
        pthread_cleanup_push(thread_pool__threadfunc_cleanup, NULL);
 
-       for (;;) {
+       while (running) {
                struct thread_pool__job *curjob;
 
                mutex_lock(&job_mutex);
-               while ((curjob = thread_pool__job_pop_locked()) == NULL)
+               while (running && (curjob = thread_pool__job_pop_locked()) == 
NULL)
                        pthread_cond_wait(&job_cond, &job_mutex);
                mutex_unlock(&job_mutex);
 
-               thread_pool__handle_job(curjob);
+               if (running)
+                       thread_pool__handle_job(curjob);
        }
 
        pthread_cleanup_pop(0);
@@ -116,9 +118,12 @@ static int thread_pool__addthread(void)
        return res;
 }
 
-int thread_pool__init(unsigned long thread_count)
+int thread_pool__init(struct kvm *kvm)
 {
        unsigned long i;
+       unsigned int thread_count = sysconf(_SC_NPROCESSORS_ONLN);
+
+       running = true;
 
        for (i = 0; i < thread_count; i++)
                if (thread_pool__addthread() < 0)
@@ -127,6 +132,26 @@ int thread_pool__init(unsigned long thread_count)
        return i;
 }
 
+int thread_pool__exit(struct kvm *kvm)
+{
+       int i;
+       void *NUL = NULL;
+
+       running = false;
+
+       for (i = 0; i < threadcount; i++) {
+               mutex_lock(&job_mutex);
+               pthread_cond_signal(&job_cond);
+               mutex_unlock(&job_mutex);
+       }
+
+       for (i = 0; i < threadcount; i++) {
+               pthread_join(threads[i], NUL);
+       }
+
+       return 0;
+}
+
 void thread_pool__do_job(struct thread_pool__job *job)
 {
        struct thread_pool__job *jobinfo = job;
-- 
1.7.12

--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to